1 /*
   2  * CDDL HEADER START
   3  *
   4  * The contents of this file are subject to the terms of the
   5  * Common Development and Distribution License (the "License").
   6  * You may not use this file except in compliance with the License.
   7  *
   8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
   9  * or http://www.opensolaris.org/os/licensing.
  10  * See the License for the specific language governing permissions
  11  * and limitations under the License.
  12  *
  13  * When distributing Covered Code, include this CDDL HEADER in each
  14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
  15  * If applicable, add the following below this CDDL HEADER, with the
  16  * fields enclosed by brackets "[]" replaced with your own identifying
  17  * information: Portions Copyright [yyyy] [name of copyright owner]
  18  *
  19  * CDDL HEADER END
  20  */
  21 /*      Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T     */
  22 /*        All rights reserved.          */
  23 
  24 
  25 /*
  26  * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
  27  * Use is subject to license terms.
  28  */
  29 
  30 /*
  31  * Copyright 2015, Joyent, Inc.
  32  */
  33 
  34 /*
  35  * FIFOFS file system vnode operations.  This file system
  36  * type supports STREAMS-based pipes and FIFOs.
  37  */
  38 #include <sys/types.h>
  39 #include <sys/param.h>
  40 #include <sys/systm.h>
  41 #include <sys/sysmacros.h>
  42 #include <sys/cred.h>
  43 #include <sys/errno.h>
  44 #include <sys/time.h>
  45 #include <sys/file.h>
  46 #include <sys/fcntl.h>
  47 #include <sys/kmem.h>
  48 #include <sys/uio.h>
  49 #include <sys/vfs.h>
  50 #include <sys/vnode.h>
  51 #include <sys/vfs_opreg.h>
  52 #include <sys/pathname.h>
  53 #include <sys/signal.h>
  54 #include <sys/user.h>
  55 #include <sys/strsubr.h>
  56 #include <sys/stream.h>
  57 #include <sys/strsun.h>
  58 #include <sys/strredir.h>
  59 #include <sys/fs/fifonode.h>
  60 #include <sys/fs/namenode.h>
  61 #include <sys/stropts.h>
  62 #include <sys/proc.h>
  63 #include <sys/unistd.h>
  64 #include <sys/debug.h>
  65 #include <fs/fs_subr.h>
  66 #include <sys/filio.h>
  67 #include <sys/termio.h>
  68 #include <sys/ddi.h>
  69 #include <sys/vtrace.h>
  70 #include <sys/policy.h>
  71 #include <sys/tsol/label.h>
  72 
  73 /*
  74  * Define the routines/data structures used in this file.
  75  */
  76 static int fifo_read(vnode_t *, uio_t *, int, cred_t *, caller_context_t *);
  77 static int fifo_write(vnode_t *, uio_t *, int, cred_t *, caller_context_t *);
  78 static int fifo_getattr(vnode_t *, vattr_t *, int, cred_t *,
  79         caller_context_t *);
  80 static int fifo_setattr(vnode_t *, vattr_t *, int, cred_t *,
  81         caller_context_t *);
  82 static int fifo_realvp(vnode_t *, vnode_t **, caller_context_t *);
  83 static int fifo_access(vnode_t *, int, int, cred_t *, caller_context_t *);
  84 static int fifo_create(struct vnode *, char *, vattr_t *, enum vcexcl,
  85     int, struct vnode **, struct cred *, int, caller_context_t *,
  86     vsecattr_t *);
  87 static int fifo_fid(vnode_t *, fid_t *, caller_context_t *);
  88 static int fifo_fsync(vnode_t *, int, cred_t *, caller_context_t *);
  89 static int fifo_seek(vnode_t *, offset_t, offset_t *, caller_context_t *);
  90 static int fifo_ioctl(vnode_t *, int, intptr_t, int, cred_t *, int *,
  91         caller_context_t *);
  92 static int fifo_fastioctl(vnode_t *, int, intptr_t, int, cred_t *, int *);
  93 static int fifo_strioctl(vnode_t *, int, intptr_t, int, cred_t *, int *);
  94 static int fifo_poll(vnode_t *, short, int, short *, pollhead_t **,
  95         caller_context_t *);
  96 static int fifo_pathconf(vnode_t *, int, ulong_t *, cred_t *,
  97         caller_context_t *);
  98 static void fifo_inactive(vnode_t *, cred_t *, caller_context_t *);
  99 static int fifo_rwlock(vnode_t *, int, caller_context_t *);
 100 static void fifo_rwunlock(vnode_t *, int, caller_context_t *);
 101 static int fifo_setsecattr(struct vnode *, vsecattr_t *, int, struct cred *,
 102         caller_context_t *);
 103 static int fifo_getsecattr(struct vnode *, vsecattr_t *, int, struct cred *,
 104         caller_context_t *);
 105 
 106 /* functions local to this file */
 107 static boolean_t fifo_stayfast_enter(fifonode_t *);
 108 static void fifo_stayfast_exit(fifonode_t *);
 109 
 110 /*
 111  * Define the data structures external to this file.
 112  */
 113 extern  dev_t   fifodev;
 114 extern struct qinit fifo_stwdata;
 115 extern struct qinit fifo_strdata;
 116 extern kmutex_t ftable_lock;
 117 
 118 struct  streamtab fifoinfo = { &fifo_strdata, &fifo_stwdata, NULL, NULL };
 119 
 120 struct vnodeops *fifo_vnodeops;
 121 
 122 const fs_operation_def_t fifo_vnodeops_template[] = {
 123         VOPNAME_OPEN,           { .vop_open = fifo_open },
 124         VOPNAME_CLOSE,          { .vop_close = fifo_close },
 125         VOPNAME_READ,           { .vop_read = fifo_read },
 126         VOPNAME_WRITE,          { .vop_write = fifo_write },
 127         VOPNAME_IOCTL,          { .vop_ioctl = fifo_ioctl },
 128         VOPNAME_GETATTR,        { .vop_getattr = fifo_getattr },
 129         VOPNAME_SETATTR,        { .vop_setattr = fifo_setattr },
 130         VOPNAME_ACCESS,         { .vop_access = fifo_access },
 131         VOPNAME_CREATE,         { .vop_create = fifo_create },
 132         VOPNAME_FSYNC,          { .vop_fsync = fifo_fsync },
 133         VOPNAME_INACTIVE,       { .vop_inactive = fifo_inactive },
 134         VOPNAME_FID,            { .vop_fid = fifo_fid },
 135         VOPNAME_RWLOCK,         { .vop_rwlock = fifo_rwlock },
 136         VOPNAME_RWUNLOCK,       { .vop_rwunlock = fifo_rwunlock },
 137         VOPNAME_SEEK,           { .vop_seek = fifo_seek },
 138         VOPNAME_REALVP,         { .vop_realvp = fifo_realvp },
 139         VOPNAME_POLL,           { .vop_poll = fifo_poll },
 140         VOPNAME_PATHCONF,       { .vop_pathconf = fifo_pathconf },
 141         VOPNAME_DISPOSE,        { .error = fs_error },
 142         VOPNAME_SETSECATTR,     { .vop_setsecattr = fifo_setsecattr },
 143         VOPNAME_GETSECATTR,     { .vop_getsecattr = fifo_getsecattr },
 144         NULL,                   NULL
 145 };
 146 
 147 /*
 148  * Return the fifoinfo structure.
 149  */
 150 struct streamtab *
 151 fifo_getinfo()
 152 {
 153         return (&fifoinfo);
 154 }
 155 
 156 /*
 157  * Trusted Extensions enforces a restrictive policy for
 158  * writing via cross-zone named pipes. A privileged global
 159  * zone process may expose a named pipe by loopback mounting
 160  * it from a lower-level zone to a higher-level zone. The
 161  * kernel-enforced mount policy for lofs mounts ensures
 162  * that such mounts are read-only in the higher-level
 163  * zone. But this is not sufficient to prevent writing
 164  * down via fifos.  This function prevents writing down
 165  * by comparing the zone of the process which is requesting
 166  * write access with the zone owning the named pipe rendezvous.
 167  * For write access the zone of the named pipe must equal the
 168  * zone of the writing process. Writing up is possible since
 169  * the named pipe can be opened for read by a process in a
 170  * higher level zone.
 171  *
 172  * An exception is made for the global zone to support trusted
 173  * processes which enforce their own data flow policies.
 174  */
 175 static boolean_t
 176 tsol_fifo_access(vnode_t *vp, int flag, cred_t *crp)
 177 {
 178         fifonode_t      *fnp = VTOF(vp);
 179 
 180         if (is_system_labeled() &&
 181             (flag & FWRITE) &&
 182             (!(fnp->fn_flag & ISPIPE))) {
 183                 zone_t  *proc_zone;
 184 
 185                 proc_zone = crgetzone(crp);
 186                 if (proc_zone != global_zone) {
 187                         char            vpath[MAXPATHLEN];
 188                         zone_t          *fifo_zone;
 189 
 190                         /*
 191                          * Get the pathname and use it to find
 192                          * the zone of the fifo.
 193                          */
 194                         if (vnodetopath(rootdir, vp, vpath, sizeof (vpath),
 195                             kcred) == 0) {
 196                                 fifo_zone = zone_find_by_path(vpath);
 197                                 zone_rele(fifo_zone);
 198 
 199                                 if (fifo_zone != global_zone &&
 200                                     fifo_zone != proc_zone) {
 201                                         return (B_FALSE);
 202                                 }
 203                         } else {
 204                                 return (B_FALSE);
 205                         }
 206                 }
 207         }
 208         return (B_TRUE);
 209 }
 210 
 211 /*
 212  * Open and stream a FIFO.
 213  * If this is the first open of the file (FIFO is not streaming),
 214  * initialize the fifonode and attach a stream to the vnode.
 215  *
 216  * Each end of a fifo must be synchronized with the other end.
 217  * If not, the mated end may complete an open, I/O, close sequence
 218  * before the end waiting in open ever wakes up.
 219  * Note: namefs pipes come through this routine too.
 220  */
 221 int
 222 fifo_open(vnode_t **vpp, int flag, cred_t *crp, caller_context_t *ct)
 223 {
 224         vnode_t         *vp             = *vpp;
 225         fifonode_t      *fnp            = VTOF(vp);
 226         fifolock_t      *fn_lock        = fnp->fn_lock;
 227         int             error;
 228 
 229         ASSERT(vp->v_type == VFIFO);
 230         ASSERT(vn_matchops(vp, fifo_vnodeops));
 231 
 232         if (!tsol_fifo_access(vp, flag, crp))
 233                 return (EACCES);
 234 
 235         mutex_enter(&fn_lock->flk_lock);
 236         /*
 237          * If we are the first reader, wake up any writers that
 238          * may be waiting around.  wait for all of them to
 239          * wake up before proceeding (i.e. fn_wsynccnt == 0)
 240          */
 241         if (flag & FREAD) {
 242                 fnp->fn_rcnt++;              /* record reader present */
 243                 if (! (fnp->fn_flag & ISPIPE))
 244                         fnp->fn_rsynccnt++;  /* record reader in open */
 245         }
 246 
 247         /*
 248          * If we are the first writer, wake up any readers that
 249          * may be waiting around.  wait for all of them to
 250          * wake up before proceeding (i.e. fn_rsynccnt == 0)
 251          */
 252         if (flag & FWRITE) {
 253                 fnp->fn_wcnt++;              /* record writer present */
 254                 if (! (fnp->fn_flag & ISPIPE))
 255                         fnp->fn_wsynccnt++;  /* record writer in open */
 256         }
 257         /*
 258          * fifo_stropen will take care of twisting the queues on the first
 259          * open.  The 1 being passed in means twist the queues on the first
 260          * open.
 261          */
 262         error = fifo_stropen(vpp, flag, crp, 1, 1);
 263         /*
 264          * fifo_stropen() could have replaced vpp
 265          * since fifo's are the only thing we need to sync up,
 266          * everything else just returns;
 267          * Note: don't need to hold lock since ISPIPE can't change
 268          * and both old and new vp need to be pipes
 269          */
 270         ASSERT(MUTEX_HELD(&VTOF(*vpp)->fn_lock->flk_lock));
 271         if (fnp->fn_flag & ISPIPE) {
 272                 ASSERT(VTOF(*vpp)->fn_flag & ISPIPE);
 273                 ASSERT(VTOF(*vpp)->fn_rsynccnt == 0);
 274                 ASSERT(VTOF(*vpp)->fn_rsynccnt == 0);
 275                 /*
 276                  * XXX note: should probably hold locks, but
 277                  * These values should not be changing
 278                  */
 279                 ASSERT(fnp->fn_rsynccnt == 0);
 280                 ASSERT(fnp->fn_wsynccnt == 0);
 281                 mutex_exit(&VTOF(*vpp)->fn_lock->flk_lock);
 282                 return (error);
 283         }
 284         /*
 285          * vp can't change for FIFOS
 286          */
 287         ASSERT(vp == *vpp);
 288         /*
 289          * If we are opening for read (or writer)
 290          *   indicate that the reader (or writer) is done with open
 291          *   if there is a writer (or reader) waiting for us, wake them up
 292          *      and indicate that at least 1 read (or write) open has occurred
 293          *      this is need in the event the read (or write) side closes
 294          *      before the writer (or reader) has a chance to wake up
 295          *      i.e. it sees that a reader (or writer) was once there
 296          */
 297         if (flag & FREAD) {
 298                 fnp->fn_rsynccnt--;  /* reader done with open */
 299                 if (fnp->fn_flag & FIFOSYNC) {
 300                         /*
 301                          * This indicates that a read open has occurred
 302                          * Only need to set if writer is actually asleep
 303                          * Flag will be consumed by writer.
 304                          */
 305                         fnp->fn_flag |= FIFOROCR;
 306                         cv_broadcast(&fnp->fn_wait_cv);
 307                 }
 308         }
 309         if (flag & FWRITE) {
 310                 fnp->fn_wsynccnt--;  /* writer done with open */
 311                 if (fnp->fn_flag & FIFOSYNC) {
 312                         /*
 313                          * This indicates that a write open has occurred
 314                          * Only need to set if reader is actually asleep
 315                          * Flag will be consumed by reader.
 316                          */
 317                         fnp->fn_flag |= FIFOWOCR;
 318                         cv_broadcast(&fnp->fn_wait_cv);
 319                 }
 320         }
 321 
 322         fnp->fn_flag &= ~FIFOSYNC;
 323 
 324         /*
 325          * errors don't wait around.. just return
 326          * Note: XXX other end will wake up and continue despite error.
 327          * There is no defined semantic on the correct course of option
 328          * so we do what we've done in the past
 329          */
 330         if (error != 0) {
 331                 mutex_exit(&fnp->fn_lock->flk_lock);
 332                 goto done;
 333         }
 334         ASSERT(fnp->fn_rsynccnt <= fnp->fn_rcnt);
 335         ASSERT(fnp->fn_wsynccnt <= fnp->fn_wcnt);
 336         /*
 337          * FIFOWOCR (or FIFOROCR) indicates that the writer (or reader)
 338          * has woken us up and is done with open (this way, if the other
 339          * end has made it to close, we don't block forever in open)
 340          * fn_wnct == fn_wsynccnt (or fn_rcnt == fn_rsynccnt) indicates
 341          * that no writer (or reader) has yet made it through open
 342          * This has the side benefit of that the first
 343          * reader (or writer) will wait until the other end finishes open
 344          */
 345         if (flag & FREAD) {
 346                 while ((fnp->fn_flag & FIFOWOCR) == 0 &&
 347                     fnp->fn_wcnt == fnp->fn_wsynccnt) {
 348                         if (flag & (FNDELAY|FNONBLOCK)) {
 349                                 mutex_exit(&fnp->fn_lock->flk_lock);
 350                                 goto done;
 351                         }
 352                         fnp->fn_insync++;
 353                         fnp->fn_flag |= FIFOSYNC;
 354                         if (!cv_wait_sig_swap(&fnp->fn_wait_cv,
 355                             &fnp->fn_lock->flk_lock)) {
 356                                 /*
 357                                  * Last reader to wakeup clear writer
 358                                  * Clear both writer and reader open
 359                                  * occurred flag incase other end is O_RDWR
 360                                  */
 361                                 if (--fnp->fn_insync == 0 &&
 362                                     fnp->fn_flag & FIFOWOCR) {
 363                                         fnp->fn_flag &= ~(FIFOWOCR|FIFOROCR);
 364                                 }
 365                                 mutex_exit(&fnp->fn_lock->flk_lock);
 366                                 (void) fifo_close(*vpp, flag, 1, 0, crp, ct);
 367                                 error = EINTR;
 368                                 goto done;
 369                         }
 370                         /*
 371                          * Last reader to wakeup clear writer open occurred flag
 372                          * Clear both writer and reader open occurred flag
 373                          * incase other end is O_RDWR
 374                          */
 375                         if (--fnp->fn_insync == 0 &&
 376                             fnp->fn_flag & FIFOWOCR) {
 377                                 fnp->fn_flag &= ~(FIFOWOCR|FIFOROCR);
 378                                 break;
 379                         }
 380                 }
 381         } else if (flag & FWRITE) {
 382                 while ((fnp->fn_flag & FIFOROCR) == 0 &&
 383                     fnp->fn_rcnt == fnp->fn_rsynccnt) {
 384                         if ((flag & (FNDELAY|FNONBLOCK)) && fnp->fn_rcnt == 0) {
 385                                 mutex_exit(&fnp->fn_lock->flk_lock);
 386                                 (void) fifo_close(*vpp, flag, 1, 0, crp, ct);
 387                                 error = ENXIO;
 388                                 goto done;
 389                         }
 390                         fnp->fn_flag |= FIFOSYNC;
 391                         fnp->fn_insync++;
 392                         if (!cv_wait_sig_swap(&fnp->fn_wait_cv,
 393                             &fnp->fn_lock->flk_lock)) {
 394                                 /*
 395                                  * Last writer to wakeup clear
 396                                  * Clear both writer and reader open
 397                                  * occurred flag in case other end is O_RDWR
 398                                  */
 399                                 if (--fnp->fn_insync == 0 &&
 400                                     (fnp->fn_flag & FIFOROCR) != 0) {
 401                                         fnp->fn_flag &= ~(FIFOWOCR|FIFOROCR);
 402                                 }
 403                                 mutex_exit(&fnp->fn_lock->flk_lock);
 404                                 (void) fifo_close(*vpp, flag, 1, 0, crp, ct);
 405                                 error = EINTR;
 406                                 goto done;
 407                         }
 408                         /*
 409                          * Last writer to wakeup clear reader open occurred flag
 410                          * Clear both writer and reader open
 411                          * occurred flag in case other end is O_RDWR
 412                          */
 413                         if (--fnp->fn_insync == 0 &&
 414                             (fnp->fn_flag & FIFOROCR) != 0) {
 415                                 fnp->fn_flag &= ~(FIFOWOCR|FIFOROCR);
 416                                 break;
 417                         }
 418                 }
 419         }
 420         mutex_exit(&fn_lock->flk_lock);
 421 done:
 422         return (error);
 423 }
 424 
 425 /*
 426  * Close down a stream.
 427  * Call cleanlocks() and strclean() on every close.
 428  * For last close send hangup message and force
 429  * the other end of a named pipe to be unmounted.
 430  * Mount guarantees that the mounted end will only call fifo_close()
 431  * with a count of 1 when the unmount occurs.
 432  * This routine will close down one end of a pipe or FIFO
 433  * and free the stream head via strclose()
 434  */
 435 /*ARGSUSED*/
 436 int
 437 fifo_close(vnode_t *vp, int flag, int count, offset_t offset, cred_t *crp,
 438         caller_context_t *ct)
 439 {
 440         fifonode_t      *fnp            = VTOF(vp);
 441         fifonode_t      *fn_dest        = fnp->fn_dest;
 442         int             error           = 0;
 443         fifolock_t      *fn_lock        = fnp->fn_lock;
 444         queue_t         *sd_wrq;
 445         vnode_t         *fn_dest_vp;
 446         int             senthang = 0;
 447 
 448         ASSERT(vp->v_stream != NULL);
 449         /*
 450          * clean locks and clear events.
 451          */
 452         (void) cleanlocks(vp, ttoproc(curthread)->p_pid, 0);
 453         cleanshares(vp, ttoproc(curthread)->p_pid);
 454         strclean(vp);
 455 
 456         /*
 457          * If a file still has the pipe/FIFO open, return.
 458          */
 459         if (count > 1)
 460                 return (0);
 461 
 462 
 463         sd_wrq = strvp2wq(vp);
 464         mutex_enter(&fn_lock->flk_lock);
 465 
 466         /*
 467          * wait for pending opens to finish up
 468          * note: this also has the side effect of single threading closes
 469          */
 470         while (fn_lock->flk_ocsync)
 471                 cv_wait(&fn_lock->flk_wait_cv, &fn_lock->flk_lock);
 472 
 473         fn_lock->flk_ocsync = 1;
 474 
 475         if (flag & FREAD) {
 476                 fnp->fn_rcnt--;
 477         }
 478         /*
 479          * If we are last writer wake up sleeping readers
 480          * (They'll figure out that there are no more writers
 481          * and do the right thing)
 482          * send hangup down stream so that stream head will do the
 483          * right thing.
 484          */
 485         if (flag & FWRITE) {
 486                 if (--fnp->fn_wcnt == 0 && fn_dest->fn_rcnt > 0) {
 487                         if ((fn_dest->fn_flag & (FIFOFAST | FIFOWANTR)) ==
 488                             (FIFOFAST | FIFOWANTR)) {
 489                                 /*
 490                                  * While we're at it, clear FIFOWANTW too
 491                                  * Wake up any sleeping readers or
 492                                  * writers.
 493                                  */
 494                                 fn_dest->fn_flag &= ~(FIFOWANTR | FIFOWANTW);
 495                                 cv_broadcast(&fn_dest->fn_wait_cv);
 496                         }
 497                         /*
 498                          * This is needed incase the other side
 499                          * was opened non-blocking.  It is the
 500                          * only way we can tell that wcnt is 0 because
 501                          * of close instead of never having a writer
 502                          */
 503                         if (!(fnp->fn_flag & ISPIPE))
 504                                 fnp->fn_flag |= FIFOCLOSE;
 505                         /*
 506                          * Note: sending hangup effectively shuts down
 507                          * both reader and writer at other end.
 508                          */
 509                         (void) putnextctl_wait(sd_wrq, M_HANGUP);
 510                         senthang = 1;
 511                 }
 512         }
 513 
 514         /*
 515          * For FIFOs we need to indicate to stream head that last reader
 516          * has gone away so that an error is generated
 517          * Pipes just need to wake up the other end so that it can
 518          * notice this end has gone away.
 519          */
 520 
 521         if (fnp->fn_rcnt == 0 && fn_dest->fn_wcnt > 0) {
 522                 if ((fn_dest->fn_flag & (FIFOFAST | FIFOWANTW)) ==
 523                     (FIFOFAST | FIFOWANTW)) {
 524                         /*
 525                          * wake up any sleeping writers
 526                          */
 527                         fn_dest->fn_flag &= ~FIFOWANTW;
 528                         cv_broadcast(&fn_dest->fn_wait_cv);
 529                 }
 530         }
 531 
 532         /*
 533          * if there are still processes with this FIFO open
 534          *      clear open/close sync flag
 535          *      and just return;
 536          */
 537         if (--fnp->fn_open > 0) {
 538                 ASSERT((fnp->fn_rcnt + fnp->fn_wcnt) != 0);
 539                 fn_lock->flk_ocsync = 0;
 540                 cv_broadcast(&fn_lock->flk_wait_cv);
 541                 mutex_exit(&fn_lock->flk_lock);
 542                 return (0);
 543         }
 544 
 545         /*
 546          * Need to send HANGUP if other side is still open
 547          * (fnp->fn_rcnt or fnp->fn_wcnt may not be zero (some thread
 548          * on this end of the pipe may still be in fifo_open())
 549          *
 550          * Note: we can get here with fn_rcnt and fn_wcnt != 0 if some
 551          * thread is blocked somewhere in the fifo_open() path prior to
 552          * fifo_stropen() incrementing fn_open.  This can occur for
 553          * normal FIFOs as well as named pipes.  fn_rcnt and
 554          * fn_wcnt only indicate attempts to open. fn_open indicates
 555          * successful opens. Partially opened FIFOs should proceed
 556          * normally; i.e. they will appear to be new opens.  Partially
 557          * opened pipes will probably fail.
 558          */
 559 
 560         if (fn_dest->fn_open && senthang == 0)
 561                 (void) putnextctl_wait(sd_wrq, M_HANGUP);
 562 
 563 
 564         /*
 565          * If this a pipe and this is the first end to close,
 566          * then we have a bit of cleanup work to do.
 567          *      Mark both ends of pipe as closed.
 568          *      Wake up anybody blocked at the other end and for named pipes,
 569          *      Close down this end of the stream
 570          *      Allow other opens/closes to continue
 571          *      force an unmount of other end.
 572          * Otherwise if this is last close,
 573          *      flush messages,
 574          *      close down the stream
 575          *      allow other opens/closes to continue
 576          */
 577         fnp->fn_flag &= ~FIFOISOPEN;
 578         if ((fnp->fn_flag & ISPIPE) && !(fnp->fn_flag & FIFOCLOSE)) {
 579                 fnp->fn_flag |= FIFOCLOSE;
 580                 fn_dest->fn_flag |= FIFOCLOSE;
 581                 if (fnp->fn_flag & FIFOFAST)
 582                         fifo_fastflush(fnp);
 583                 if (vp->v_stream != NULL) {
 584                         mutex_exit(&fn_lock->flk_lock);
 585                         (void) strclose(vp, flag, crp);
 586                         mutex_enter(&fn_lock->flk_lock);
 587                 }
 588                 cv_broadcast(&fn_dest->fn_wait_cv);
 589                 /*
 590                  * allow opens and closes to proceed
 591                  * Since this end is now closed down, any attempt
 592                  * to do anything with this end will fail
 593                  */
 594                 fn_lock->flk_ocsync = 0;
 595                 cv_broadcast(&fn_lock->flk_wait_cv);
 596                 fn_dest_vp = FTOV(fn_dest);
 597                 /*
 598                  * if other end of pipe has been opened and it's
 599                  * a named pipe, unmount it
 600                  */
 601                 if (fn_dest_vp->v_stream &&
 602                     (fn_dest_vp->v_stream->sd_flag & STRMOUNT)) {
 603                         /*
 604                          * We must hold the destination vnode because
 605                          * nm_unmountall() causes close to be called
 606                          * for the other end of named pipe.  This
 607                          * could free the vnode before we are ready.
 608                          */
 609                         VN_HOLD(fn_dest_vp);
 610                         mutex_exit(&fn_lock->flk_lock);
 611                         error = nm_unmountall(fn_dest_vp, crp);
 612                         ASSERT(error == 0);
 613                         VN_RELE(fn_dest_vp);
 614                 } else {
 615                         ASSERT(vp->v_count >= 1);
 616                         mutex_exit(&fn_lock->flk_lock);
 617                 }
 618         } else {
 619                 if (fnp->fn_flag & FIFOFAST)
 620                         fifo_fastflush(fnp);
 621 #if DEBUG
 622                 fn_dest_vp = FTOV(fn_dest);
 623                 if (fn_dest_vp->v_stream)
 624                         ASSERT((fn_dest_vp->v_stream->sd_flag & STRMOUNT) == 0);
 625 #endif
 626                 if (vp->v_stream != NULL) {
 627                         mutex_exit(&fn_lock->flk_lock);
 628                         (void) strclose(vp, flag, crp);
 629                         mutex_enter(&fn_lock->flk_lock);
 630                 }
 631                 fn_lock->flk_ocsync = 0;
 632                 cv_broadcast(&fn_lock->flk_wait_cv);
 633                 cv_broadcast(&fn_dest->fn_wait_cv);
 634                 mutex_exit(&fn_lock->flk_lock);
 635         }
 636         return (error);
 637 }
 638 
 639 /*
 640  * Read from a pipe or FIFO.
 641  * return 0 if....
 642  *    (1) user read request is 0 or no stream
 643  *    (2) broken pipe with no data
 644  *    (3) write-only FIFO with no data
 645  *    (4) no data and FNDELAY flag is set.
 646  * Otherwise return
 647  *      EAGAIN if FNONBLOCK is set and no data to read
 648  *      EINTR if signal received while waiting for data
 649  *
 650  * While there is no data to read....
 651  *   -  if the NDELAY/NONBLOCK flag is set, return 0/EAGAIN.
 652  *   -  wait for a write.
 653  *
 654  */
 655 /*ARGSUSED*/
 656 
 657 static int
 658 fifo_read(struct vnode *vp, struct uio *uiop, int ioflag, struct cred *crp,
 659         caller_context_t *ct)
 660 {
 661         fifonode_t      *fnp            = VTOF(vp);
 662         fifonode_t      *fn_dest;
 663         fifolock_t      *fn_lock        = fnp->fn_lock;
 664         int             error           = 0;
 665         mblk_t          *bp;
 666 
 667         ASSERT(vp->v_stream != NULL);
 668         if (uiop->uio_resid == 0)
 669                 return (0);
 670 
 671         mutex_enter(&fn_lock->flk_lock);
 672 
 673         TRACE_2(TR_FAC_FIFO, TR_FIFOREAD_IN, "fifo_read in:%p fnp %p", vp, fnp);
 674 
 675         if (! (fnp->fn_flag & FIFOFAST))
 676                 goto stream_mode;
 677 
 678         fn_dest = fnp->fn_dest;
 679         /*
 680          * Check for data on our input queue
 681          */
 682 
 683         while (fnp->fn_count == 0) {
 684                 /*
 685                  * No data on first attempt and no writer, then EOF
 686                  */
 687                 if (fn_dest->fn_wcnt == 0 || fn_dest->fn_rcnt == 0) {
 688                         mutex_exit(&fn_lock->flk_lock);
 689                         return (0);
 690                 }
 691                 /*
 692                  * no data found.. if non-blocking, return EAGAIN
 693                  * otherwise 0.
 694                  */
 695                 if (uiop->uio_fmode & (FNDELAY|FNONBLOCK)) {
 696                         mutex_exit(&fn_lock->flk_lock);
 697                         if (uiop->uio_fmode & FNONBLOCK)
 698                                 return (EAGAIN);
 699                         return (0);
 700                 }
 701 
 702                 /*
 703                  * Note: FIFOs can get here with FIFOCLOSE set if
 704                  * write side is in the middle of opeining after
 705                  * it once closed. Pipes better not have FIFOCLOSE set
 706                  */
 707                 ASSERT((fnp->fn_flag & (ISPIPE|FIFOCLOSE)) !=
 708                     (ISPIPE|FIFOCLOSE));
 709                 /*
 710                  * wait for data
 711                  */
 712                 fnp->fn_flag |= FIFOWANTR;
 713 
 714                 TRACE_1(TR_FAC_FIFO, TR_FIFOREAD_WAIT, "fiforead wait: %p", vp);
 715 
 716                 if (!cv_wait_sig_swap(&fnp->fn_wait_cv,
 717                     &fn_lock->flk_lock)) {
 718                         error = EINTR;
 719                         goto done;
 720                 }
 721 
 722                 TRACE_1(TR_FAC_FIFO, TR_FIFOREAD_WAKE,
 723                     "fiforead awake: %p", vp);
 724 
 725                 /*
 726                  * check to make sure we are still in fast mode
 727                  */
 728                 if (!(fnp->fn_flag & FIFOFAST))
 729                         goto stream_mode;
 730         }
 731 
 732         ASSERT(fnp->fn_mp != NULL);
 733 
 734         /* For pipes copy should not bypass cache */
 735         uiop->uio_extflg |= UIO_COPY_CACHED;
 736 
 737         do {
 738                 int bpsize = MBLKL(fnp->fn_mp);
 739                 int uiosize = MIN(bpsize, uiop->uio_resid);
 740 
 741                 error = uiomove(fnp->fn_mp->b_rptr, uiosize, UIO_READ, uiop);
 742                 if (error != 0)
 743                         break;
 744 
 745                 fnp->fn_count -= uiosize;
 746 
 747                 if (bpsize <= uiosize) {
 748                         bp = fnp->fn_mp;
 749                         fnp->fn_mp = fnp->fn_mp->b_cont;
 750                         freeb(bp);
 751 
 752                         if (uiop->uio_resid == 0)
 753                                 break;
 754 
 755                         while (fnp->fn_mp == NULL && fn_dest->fn_wwaitcnt > 0) {
 756                                 ASSERT(fnp->fn_count == 0);
 757 
 758                                 if (uiop->uio_fmode & (FNDELAY|FNONBLOCK))
 759                                         goto trywake;
 760 
 761                                 /*
 762                                  * We've consumed all available data but there
 763                                  * are threads waiting to write more, let them
 764                                  * proceed before bailing.
 765                                  */
 766 
 767                                 fnp->fn_flag |= FIFOWANTR;
 768                                 fifo_wakewriter(fn_dest, fn_lock);
 769 
 770                                 if (!cv_wait_sig(&fnp->fn_wait_cv,
 771                                     &fn_lock->flk_lock))
 772                                         goto trywake;
 773 
 774                                 if (!(fnp->fn_flag & FIFOFAST))
 775                                         goto stream_mode;
 776                         }
 777                 } else {
 778                         fnp->fn_mp->b_rptr += uiosize;
 779                         ASSERT(uiop->uio_resid == 0);
 780                 }
 781         } while (uiop->uio_resid != 0 && fnp->fn_mp != NULL);
 782 
 783 trywake:
 784         ASSERT(msgdsize(fnp->fn_mp) == fnp->fn_count);
 785 
 786         /*
 787          * wake up any blocked writers, processes
 788          * sleeping on POLLWRNORM, or processes waiting for SIGPOLL
 789          * Note: checking for fn_count < Fifohiwat emulates
 790          * STREAMS functionality when low water mark is 0
 791          */
 792         if (fn_dest->fn_flag & (FIFOWANTW | FIFOHIWATW) &&
 793             fnp->fn_count < Fifohiwat) {
 794                 fifo_wakewriter(fn_dest, fn_lock);
 795         }
 796         goto done;
 797 
 798         /*
 799          * FIFO is in streams mode.. let the stream head handle it
 800          */
 801 stream_mode:
 802 
 803         mutex_exit(&fn_lock->flk_lock);
 804         TRACE_1(TR_FAC_FIFO,
 805             TR_FIFOREAD_STREAM, "fifo_read stream_mode:%p", vp);
 806 
 807         error = strread(vp, uiop, crp);
 808 
 809         mutex_enter(&fn_lock->flk_lock);
 810 
 811 done:
 812         /*
 813          * vnode update access time
 814          */
 815         if (error == 0) {
 816                 time_t now = gethrestime_sec();
 817 
 818                 if (fnp->fn_flag & ISPIPE)
 819                         fnp->fn_dest->fn_atime = now;
 820                 fnp->fn_atime = now;
 821         }
 822         TRACE_2(TR_FAC_FIFO, TR_FIFOREAD_OUT,
 823             "fifo_read out:%p error %d", vp, error);
 824         mutex_exit(&fn_lock->flk_lock);
 825         return (error);
 826 }
 827 
 828 /*
 829  * send SIGPIPE and return EPIPE if ...
 830  *   (1) broken pipe (essentially, reader is gone)
 831  *   (2) FIFO is not open for reading
 832  * return 0 if...
 833  *   (1) no stream
 834  *   (2) user write request is for 0 bytes and SW_SNDZERO is not set
 835  *      Note: SW_SNDZERO can't be set in fast mode
 836  * While the stream is flow controlled....
 837  *   -  if the NDELAY/NONBLOCK flag is set, return 0/EAGAIN.
 838  *   -  unlock the fifonode and sleep waiting for a reader.
 839  *   -  if a pipe and it has a mate, sleep waiting for its mate
 840  *      to read.
 841  */
 842 /*ARGSUSED*/
 843 static int
 844 fifo_write(vnode_t *vp, uio_t *uiop, int ioflag, cred_t *crp,
 845         caller_context_t *ct)
 846 {
 847         struct fifonode *fnp, *fn_dest;
 848         fifolock_t      *fn_lock;
 849         struct stdata   *stp;
 850         int             error   = 0;
 851         int             write_size;
 852         int             size;
 853         int             fmode;
 854         mblk_t          *bp;
 855         boolean_t       hotread;
 856 
 857         ASSERT(vp->v_stream);
 858         uiop->uio_loffset = 0;
 859         stp     = vp->v_stream;
 860 
 861         /*
 862          * remember original number of bytes requested. Used to determine if
 863          * we actually have written anything at all
 864          */
 865         write_size = uiop->uio_resid;
 866 
 867         /*
 868          * only send zero-length messages if SW_SNDZERO is set
 869          * Note: we will be in streams mode if SW_SNDZERO is set
 870          * XXX this streams interface should not be exposed
 871          */
 872         if ((write_size == 0) && !(stp->sd_wput_opt & SW_SNDZERO))
 873                 return (0);
 874 
 875         fnp = VTOF(vp);
 876         fn_lock = fnp->fn_lock;
 877         fn_dest = fnp->fn_dest;
 878 
 879         mutex_enter(&fn_lock->flk_lock);
 880 
 881         TRACE_3(TR_FAC_FIFO, TR_FIFOWRITE_IN,
 882             "fifo_write in:%p fnp %p size %d", vp, fnp, write_size);
 883 
 884         /*
 885          * oops, no readers, error
 886          */
 887         if (fn_dest->fn_rcnt == 0 || fn_dest->fn_wcnt == 0) {
 888                 goto epipe;
 889         }
 890 
 891         /*
 892          * if we are not in fast mode, let streams handle it
 893          */
 894         if (!(fnp->fn_flag & FIFOFAST))
 895                 goto stream_mode;
 896 
 897         fmode = uiop->uio_fmode & (FNDELAY|FNONBLOCK);
 898 
 899         /* For pipes copy should not bypass cache */
 900         uiop->uio_extflg |= UIO_COPY_CACHED;
 901 
 902         do  {
 903                 /*
 904                  * check to make sure we are not over high water mark
 905                  */
 906                 while (fn_dest->fn_count >= Fifohiwat) {
 907                         /*
 908                          * Indicate that we have gone over high
 909                          * water mark
 910                          */
 911                         /*
 912                          * if non-blocking, return
 913                          * only happens first time through loop
 914                          */
 915                         if (fmode) {
 916                                 fnp->fn_flag |= FIFOHIWATW;
 917                                 if (uiop->uio_resid == write_size) {
 918                                         mutex_exit(&fn_lock->flk_lock);
 919                                         if (fmode & FNDELAY)
 920                                                 return (0);
 921                                         else
 922                                                 return (EAGAIN);
 923                                 }
 924                                 goto done;
 925                         }
 926 
 927                         /*
 928                          * wait for things to drain
 929                          */
 930                         fnp->fn_flag |= FIFOWANTW;
 931                         fnp->fn_wwaitcnt++;
 932                         TRACE_1(TR_FAC_FIFO, TR_FIFOWRITE_WAIT,
 933                             "fifo_write wait: %p", vp);
 934                         if (!cv_wait_sig_swap(&fnp->fn_wait_cv,
 935                             &fn_lock->flk_lock)) {
 936                                 error = EINTR;
 937                                 fnp->fn_wwaitcnt--;
 938                                 fifo_wakereader(fn_dest, fn_lock);
 939                                 goto done;
 940                         }
 941                         fnp->fn_wwaitcnt--;
 942 
 943                         TRACE_1(TR_FAC_FIFO, TR_FIFOWRITE_WAKE,
 944                             "fifo_write wake: %p", vp);
 945 
 946                         /*
 947                          * check to make sure we're still in fast mode
 948                          */
 949                         if (!(fnp->fn_flag & FIFOFAST))
 950                                 goto stream_mode;
 951 
 952                         /*
 953                          * make sure readers didn't go away
 954                          */
 955                         if (fn_dest->fn_rcnt == 0 || fn_dest->fn_wcnt == 0) {
 956                                 goto epipe;
 957                         }
 958                 }
 959                 /*
 960                  * If the write will put us over the high water mark,
 961                  * then we must break the message up into PIPE_BUF
 962                  * chunks to stay compliant with STREAMS
 963                  */
 964                 if (uiop->uio_resid + fn_dest->fn_count > Fifohiwat)
 965                         size = MIN(uiop->uio_resid, PIPE_BUF);
 966                 else
 967                         size = uiop->uio_resid;
 968 
 969                 /*
 970                  * We don't need to hold flk_lock across the allocb() and
 971                  * uiomove().  However, on a multiprocessor machine where both
 972                  * the reader and writer thread are on cpu's, we must be
 973                  * careful to only drop the lock if there's data to be read.
 974                  * This forces threads entering fifo_read() to spin or block
 975                  * on flk_lock, rather than acquiring flk_lock only to
 976                  * discover there's no data to read and being forced to go
 977                  * back to sleep, only to be woken up microseconds later by
 978                  * this writer thread.
 979                  */
 980                 hotread = fn_dest->fn_count > 0;
 981                 if (hotread) {
 982                         if (!fifo_stayfast_enter(fnp))
 983                                 goto stream_mode;
 984                         mutex_exit(&fn_lock->flk_lock);
 985                 }
 986 
 987                 ASSERT(size != 0);
 988                 /*
 989                  * Align the mblk with the user data so that
 990                  * copying in the data can take advantage of
 991                  * the double word alignment
 992                  */
 993                 if ((bp = allocb(size + 8, BPRI_MED)) == NULL) {
 994                         if (!hotread)
 995                                 mutex_exit(&fn_lock->flk_lock);
 996 
 997                         error = strwaitbuf(size, BPRI_MED);
 998 
 999                         mutex_enter(&fn_lock->flk_lock);
1000 
1001                         if (hotread) {
1002                                 /*
1003                                  * As we dropped the mutex for a moment, we
1004                                  * need to wake up any thread waiting to be
1005                                  * allowed to go from fast mode to stream mode.
1006                                  */
1007                                 fifo_stayfast_exit(fnp);
1008                         }
1009                         if (error != 0) {
1010                                 goto done;
1011                         }
1012                         /*
1013                          * check to make sure we're still in fast mode
1014                          */
1015                         if (!(fnp->fn_flag & FIFOFAST))
1016                                 goto stream_mode;
1017 
1018                         /*
1019                          * make sure readers didn't go away
1020                          */
1021                         if (fn_dest->fn_rcnt == 0 || fn_dest->fn_wcnt == 0) {
1022                                 goto epipe;
1023                         }
1024                         /*
1025                          * some other thread could have gotten in
1026                          * need to go back and check hi water mark
1027                          */
1028                         continue;
1029                 }
1030                 bp->b_rptr += ((uintptr_t)uiop->uio_iov->iov_base & 0x7);
1031                 bp->b_wptr = bp->b_rptr + size;
1032                 error = uiomove((caddr_t)bp->b_rptr, size, UIO_WRITE, uiop);
1033                 if (hotread) {
1034                         mutex_enter(&fn_lock->flk_lock);
1035                         /*
1036                          * As we dropped the mutex for a moment, we need to:
1037                          * - wake up any thread waiting to be allowed to go
1038                          *   from fast mode to stream mode,
1039                          * - make sure readers didn't go away.
1040                          */
1041                         fifo_stayfast_exit(fnp);
1042                         if (fn_dest->fn_rcnt == 0 || fn_dest->fn_wcnt == 0) {
1043                                 freeb(bp);
1044                                 goto epipe;
1045                         }
1046                 }
1047 
1048                 if (error != 0) {
1049                         freeb(bp);
1050                         goto done;
1051                 }
1052 
1053                 fn_dest->fn_count += size;
1054                 if (fn_dest->fn_mp != NULL) {
1055                         fn_dest->fn_tail->b_cont = bp;
1056                         fn_dest->fn_tail = bp;
1057                 } else {
1058                         fn_dest->fn_mp = fn_dest->fn_tail = bp;
1059                         /*
1060                          * This is the first bit of data; wake up any sleeping
1061                          * readers, processes blocked in poll, and those
1062                          * expecting a SIGPOLL.
1063                          */
1064                         fifo_wakereader(fn_dest, fn_lock);
1065                 }
1066         } while (uiop->uio_resid != 0);
1067 
1068         goto done;
1069 
1070 stream_mode:
1071         /*
1072          * streams mode
1073          *  let the stream head handle the write
1074          */
1075         ASSERT(MUTEX_HELD(&fn_lock->flk_lock));
1076 
1077         mutex_exit(&fn_lock->flk_lock);
1078         TRACE_1(TR_FAC_FIFO,
1079             TR_FIFOWRITE_STREAM, "fifo_write stream_mode:%p", vp);
1080 
1081         error = strwrite(vp, uiop, crp);
1082 
1083         mutex_enter(&fn_lock->flk_lock);
1084 
1085 done:
1086         /*
1087          * update vnode modification and change times
1088          * make sure there were no errors and some data was transferred
1089          */
1090         if (error == 0 && write_size != uiop->uio_resid) {
1091                 time_t now = gethrestime_sec();
1092 
1093                 if (fnp->fn_flag & ISPIPE) {
1094                         fn_dest->fn_mtime = fn_dest->fn_ctime = now;
1095                 }
1096                 fnp->fn_mtime = fnp->fn_ctime = now;
1097         } else if (fn_dest->fn_rcnt == 0 || fn_dest->fn_wcnt == 0) {
1098                 goto epipe;
1099         }
1100         TRACE_3(TR_FAC_FIFO, TR_FIFOWRITE_OUT,
1101             "fifo_write out: vp %p error %d fnp %p", vp, error, fnp);
1102         mutex_exit(&fn_lock->flk_lock);
1103         return (error);
1104 epipe:
1105         error = EPIPE;
1106         TRACE_3(TR_FAC_FIFO, TR_FIFOWRITE_OUT,
1107             "fifo_write out: vp %p error %d fnp %p", vp, error, fnp);
1108         mutex_exit(&fn_lock->flk_lock);
1109         tsignal(curthread, SIGPIPE);
1110         return (error);
1111 }
1112 
1113 /*ARGSUSED6*/
1114 static int
1115 fifo_ioctl(vnode_t *vp, int cmd, intptr_t arg, int mode,
1116         cred_t *cr, int *rvalp, caller_context_t *ct)
1117 {
1118         /*
1119          * Just a quick check
1120          * Once we go to streams mode we don't ever revert back
1121          * So we do this quick check so as not to incur the overhead
1122          * associated with acquiring the lock
1123          */
1124         return ((VTOF(vp)->fn_flag & FIFOFAST) ?
1125             fifo_fastioctl(vp, cmd, arg, mode, cr, rvalp) :
1126             fifo_strioctl(vp, cmd, arg, mode, cr, rvalp));
1127 }
1128 
1129 static inline int
1130 fifo_ioctl_getpeercred(fifonode_t *fnp, intptr_t arg, int mode)
1131 {
1132         k_peercred_t *kp = (k_peercred_t *)arg;
1133 
1134         if (mode == FKIOCTL && fnp->fn_pcredp != NULL) {
1135                 crhold(fnp->fn_pcredp);
1136                 kp->pc_cr = fnp->fn_pcredp;
1137                 kp->pc_cpid = fnp->fn_cpid;
1138                 return (0);
1139         } else {
1140                 return (ENOTSUP);
1141         }
1142 }
1143 
1144 static int
1145 fifo_fastioctl(vnode_t *vp, int cmd, intptr_t arg, int mode,
1146         cred_t *cr, int *rvalp)
1147 {
1148         fifonode_t      *fnp            = VTOF(vp);
1149         fifonode_t      *fn_dest;
1150         int             error           = 0;
1151         fifolock_t      *fn_lock        = fnp->fn_lock;
1152         int             cnt;
1153 
1154         /*
1155          * tty operations not allowed
1156          */
1157         if (((cmd & IOCTYPE) == LDIOC) ||
1158             ((cmd & IOCTYPE) == tIOC) ||
1159             ((cmd & IOCTYPE) == TIOC)) {
1160                 return (EINVAL);
1161         }
1162 
1163         mutex_enter(&fn_lock->flk_lock);
1164 
1165         if (!(fnp->fn_flag & FIFOFAST)) {
1166                 goto stream_mode;
1167         }
1168 
1169         switch (cmd) {
1170 
1171         /*
1172          * Things we can't handle
1173          * These will switch us to streams mode.
1174          */
1175         default:
1176         case I_STR:
1177         case I_SRDOPT:
1178         case I_PUSH:
1179         case I_FDINSERT:
1180         case I_SENDFD:
1181         case I_RECVFD:
1182         case I_E_RECVFD:
1183         case I_ATMARK:
1184         case I_CKBAND:
1185         case I_GETBAND:
1186         case I_SWROPT:
1187                 goto turn_fastoff;
1188 
1189         /*
1190          * Things that don't do damage
1191          * These things don't adjust the state of the
1192          * stream head (i_setcltime does, but we don't care)
1193          */
1194         case I_FIND:
1195         case I_GETSIG:
1196         case FIONBIO:
1197         case FIOASYNC:
1198         case I_GRDOPT:  /* probably should not get this, but no harm */
1199         case I_GWROPT:
1200         case I_LIST:
1201         case I_SETCLTIME:
1202         case I_GETCLTIME:
1203                 mutex_exit(&fn_lock->flk_lock);
1204                 return (strioctl(vp, cmd, arg, mode, U_TO_K, cr, rvalp));
1205 
1206         case I_CANPUT:
1207                 /*
1208                  * We can only handle normal band canputs.
1209                  * XXX : We could just always go to stream mode; after all
1210                  * canput is a streams semantics type thing
1211                  */
1212                 if (arg != 0) {
1213                         goto turn_fastoff;
1214                 }
1215                 *rvalp = (fnp->fn_dest->fn_count < Fifohiwat) ? 1 : 0;
1216                 mutex_exit(&fn_lock->flk_lock);
1217                 return (0);
1218 
1219         case I_NREAD:
1220                 /*
1221                  * This may seem a bit silly for non-streams semantics,
1222                  * (After all, if they really want a message, they'll
1223                  * probably use getmsg() anyway). but it doesn't hurt
1224                  */
1225                 error = copyout((caddr_t)&fnp->fn_count, (caddr_t)arg,
1226                     sizeof (cnt));
1227                 if (error == 0) {
1228                         *rvalp = (fnp->fn_count == 0) ? 0 : 1;
1229                 }
1230                 break;
1231 
1232         case FIORDCHK:
1233                 *rvalp = fnp->fn_count;
1234                 break;
1235 
1236         case I_PEEK:
1237         {
1238                 STRUCT_DECL(strpeek, strpeek);
1239                 struct uio      uio;
1240                 struct iovec    iov;
1241                 int             count;
1242                 mblk_t          *bp;
1243                 int             len;
1244 
1245                 STRUCT_INIT(strpeek, mode);
1246 
1247                 if (fnp->fn_count == 0) {
1248                         *rvalp = 0;
1249                         break;
1250                 }
1251 
1252                 error = copyin((caddr_t)arg, STRUCT_BUF(strpeek),
1253                     STRUCT_SIZE(strpeek));
1254                 if (error)
1255                         break;
1256 
1257                 /*
1258                  * can't have any high priority message when in fast mode
1259                  */
1260                 if (STRUCT_FGET(strpeek, flags) & RS_HIPRI) {
1261                         *rvalp = 0;
1262                         break;
1263                 }
1264 
1265                 len = STRUCT_FGET(strpeek, databuf.maxlen);
1266                 if (len <= 0) {
1267                         STRUCT_FSET(strpeek, databuf.len, len);
1268                 } else {
1269                         iov.iov_base = STRUCT_FGETP(strpeek, databuf.buf);
1270                         iov.iov_len = len;
1271                         uio.uio_iov = &iov;
1272                         uio.uio_iovcnt = 1;
1273                         uio.uio_loffset = 0;
1274                         uio.uio_segflg = UIO_USERSPACE;
1275                         uio.uio_fmode = 0;
1276                         /* For pipes copy should not bypass cache */
1277                         uio.uio_extflg = UIO_COPY_CACHED;
1278                         uio.uio_resid = iov.iov_len;
1279                         count = fnp->fn_count;
1280                         bp = fnp->fn_mp;
1281                         while (count > 0 && uio.uio_resid) {
1282                                 cnt = MIN(uio.uio_resid, MBLKL(bp));
1283                                 if ((error = uiomove((char *)bp->b_rptr, cnt,
1284                                     UIO_READ, &uio)) != 0) {
1285                                         break;
1286                                 }
1287                                 count -= cnt;
1288                                 bp = bp->b_cont;
1289                         }
1290                         STRUCT_FSET(strpeek, databuf.len, len - uio.uio_resid);
1291                 }
1292                 STRUCT_FSET(strpeek, flags, 0);
1293                 STRUCT_FSET(strpeek, ctlbuf.len, -1);
1294 
1295                 error = copyout(STRUCT_BUF(strpeek), (caddr_t)arg,
1296                     STRUCT_SIZE(strpeek));
1297                 if (error == 0 && len >= 0)
1298                         *rvalp = 1;
1299                 break;
1300         }
1301 
1302         case FIONREAD:
1303                 /*
1304                  * let user know total number of bytes in message queue
1305                  */
1306                 error = copyout((caddr_t)&fnp->fn_count, (caddr_t)arg,
1307                     sizeof (fnp->fn_count));
1308                 if (error == 0)
1309                         *rvalp = 0;
1310                 break;
1311 
1312         case I_SETSIG:
1313                 /*
1314                  * let streams set up the signal masking for us
1315                  * we just check to see if it's set
1316                  * XXX : this interface should not be visible
1317                  *  i.e. STREAM's framework is exposed.
1318                  */
1319                 error = strioctl(vp, cmd, arg, mode, U_TO_K, cr, rvalp);
1320                 if (vp->v_stream->sd_sigflags & (S_INPUT|S_RDNORM|S_WRNORM))
1321                         fnp->fn_flag |= FIFOSETSIG;
1322                 else
1323                         fnp->fn_flag &= ~FIFOSETSIG;
1324                 break;
1325 
1326         case I_FLUSH:
1327                 /*
1328                  * flush them message queues
1329                  */
1330                 if (arg & ~FLUSHRW) {
1331                         error = EINVAL;
1332                         break;
1333                 }
1334                 if (arg & FLUSHR) {
1335                         fifo_fastflush(fnp);
1336                 }
1337                 fn_dest = fnp->fn_dest;
1338                 if ((arg & FLUSHW)) {
1339                         fifo_fastflush(fn_dest);
1340                 }
1341                 /*
1342                  * wake up any sleeping readers or writers
1343                  * (waking readers probably doesn't make sense, but it
1344                  *  doesn't hurt; i.e. we just got rid of all the data
1345                  *  what's to read ?)
1346                  */
1347                 if (fn_dest->fn_flag & (FIFOWANTW | FIFOWANTR)) {
1348                         fn_dest->fn_flag &= ~(FIFOWANTW | FIFOWANTR);
1349                         cv_broadcast(&fn_dest->fn_wait_cv);
1350                 }
1351                 *rvalp = 0;
1352                 break;
1353 
1354         /*
1355          * Since no band data can ever get on a fifo in fast mode
1356          * just return 0.
1357          */
1358         case I_FLUSHBAND:
1359                 error = 0;
1360                 *rvalp = 0;
1361                 break;
1362 
1363         case _I_GETPEERCRED:
1364                 error = fifo_ioctl_getpeercred(fnp, arg, mode);
1365                 break;
1366 
1367         /*
1368          * invalid calls for stream head or fifos
1369          */
1370 
1371         case I_POP:             /* shouldn't happen */
1372         case I_LOOK:
1373         case I_LINK:
1374         case I_PLINK:
1375         case I_UNLINK:
1376         case I_PUNLINK:
1377 
1378         /*
1379          * more invalid tty type of ioctls
1380          */
1381 
1382         case SRIOCSREDIR:
1383         case SRIOCISREDIR:
1384                 error = EINVAL;
1385                 break;
1386 
1387         }
1388         mutex_exit(&fn_lock->flk_lock);
1389         return (error);
1390 
1391 turn_fastoff:
1392         fifo_fastoff(fnp);
1393 
1394 stream_mode:
1395         /*
1396          * streams mode
1397          */
1398         mutex_exit(&fn_lock->flk_lock);
1399         return (fifo_strioctl(vp, cmd, arg, mode, cr, rvalp));
1400 
1401 }
1402 
1403 /*
1404  * FIFO is in STREAMS mode; STREAMS framework does most of the work.
1405  */
1406 static int
1407 fifo_strioctl(vnode_t *vp, int cmd, intptr_t arg, int mode,
1408         cred_t *cr, int *rvalp)
1409 {
1410         fifonode_t      *fnp = VTOF(vp);
1411         int             error;
1412         fifolock_t      *fn_lock;
1413 
1414         if (cmd == _I_GETPEERCRED)
1415                 return (fifo_ioctl_getpeercred(fnp, arg, mode));
1416 
1417         error = strioctl(vp, cmd, arg, mode, U_TO_K, cr, rvalp);
1418 
1419         switch (cmd) {
1420         /*
1421          * The FIFOSEND flag is set to inform other processes that a file
1422          * descriptor is pending at the stream head of this pipe.
1423          * The flag is cleared and the sending process is awoken when
1424          * this process has completed receiving the file descriptor.
1425          * XXX This could become out of sync if the process does I_SENDFDs
1426          * and opens on connld attached to the same pipe.
1427          */
1428         case I_RECVFD:
1429         case I_E_RECVFD:
1430                 if (error == 0) {
1431                         fn_lock = fnp->fn_lock;
1432                         mutex_enter(&fn_lock->flk_lock);
1433                         if (fnp->fn_flag & FIFOSEND) {
1434                                 fnp->fn_flag &= ~FIFOSEND;
1435                                 cv_broadcast(&fnp->fn_dest->fn_wait_cv);
1436                         }
1437                         mutex_exit(&fn_lock->flk_lock);
1438                 }
1439                 break;
1440         default:
1441                 break;
1442         }
1443 
1444         return (error);
1445 }
1446 
1447 /*
1448  * If shadowing a vnode (FIFOs), apply the VOP_GETATTR to the shadowed
1449  * vnode to Obtain the node information. If not shadowing (pipes), obtain
1450  * the node information from the credentials structure.
1451  */
1452 int
1453 fifo_getattr(vnode_t *vp, vattr_t *vap, int flags, cred_t *crp,
1454         caller_context_t *ct)
1455 {
1456         int             error           = 0;
1457         fifonode_t      *fnp            = VTOF(vp);
1458         queue_t         *qp;
1459         qband_t         *bandp;
1460         fifolock_t      *fn_lock        = fnp->fn_lock;
1461 
1462         if (fnp->fn_realvp) {
1463                 /*
1464                  * for FIFOs or mounted pipes
1465                  */
1466                 if (error = VOP_GETATTR(fnp->fn_realvp, vap, flags, crp, ct))
1467                         return (error);
1468                 mutex_enter(&fn_lock->flk_lock);
1469                 /* set current times from fnode, even if older than vnode */
1470                 vap->va_atime.tv_sec = fnp->fn_atime;
1471                 vap->va_atime.tv_nsec = 0;
1472                 vap->va_mtime.tv_sec = fnp->fn_mtime;
1473                 vap->va_mtime.tv_nsec = 0;
1474                 vap->va_ctime.tv_sec = fnp->fn_ctime;
1475                 vap->va_ctime.tv_nsec = 0;
1476         } else {
1477                 /*
1478                  * for non-attached/ordinary pipes
1479                  */
1480                 vap->va_mode = 0;
1481                 mutex_enter(&fn_lock->flk_lock);
1482                 vap->va_atime.tv_sec = fnp->fn_atime;
1483                 vap->va_atime.tv_nsec = 0;
1484                 vap->va_mtime.tv_sec = fnp->fn_mtime;
1485                 vap->va_mtime.tv_nsec = 0;
1486                 vap->va_ctime.tv_sec = fnp->fn_ctime;
1487                 vap->va_ctime.tv_nsec = 0;
1488                 vap->va_uid = crgetuid(crp);
1489                 vap->va_gid = crgetgid(crp);
1490                 vap->va_nlink = 0;
1491                 vap->va_fsid = fifodev;
1492                 vap->va_nodeid = (ino64_t)fnp->fn_ino;
1493                 vap->va_rdev = 0;
1494         }
1495         vap->va_type = VFIFO;
1496         vap->va_blksize = PIPE_BUF;
1497         /*
1498          * Size is number of un-read bytes at the stream head and
1499          * nblocks is the unread bytes expressed in blocks.
1500          */
1501         if (vp->v_stream && (fnp->fn_flag & FIFOISOPEN)) {
1502                 if ((fnp->fn_flag & FIFOFAST)) {
1503                         vap->va_size = (u_offset_t)fnp->fn_count;
1504                 } else {
1505                         qp = RD((strvp2wq(vp)));
1506                         vap->va_size = (u_offset_t)qp->q_count;
1507                         if (qp->q_nband != 0) {
1508                                 mutex_enter(QLOCK(qp));
1509                                 for (bandp = qp->q_bandp; bandp;
1510                                     bandp = bandp->qb_next)
1511                                         vap->va_size += bandp->qb_count;
1512                                 mutex_exit(QLOCK(qp));
1513                         }
1514                 }
1515                 vap->va_nblocks = (fsblkcnt64_t)btod(vap->va_size);
1516         } else {
1517                 vap->va_size = (u_offset_t)0;
1518                 vap->va_nblocks = (fsblkcnt64_t)0;
1519         }
1520         mutex_exit(&fn_lock->flk_lock);
1521         vap->va_seq = 0;
1522         return (0);
1523 }
1524 
1525 /*
1526  * If shadowing a vnode, apply the VOP_SETATTR to it, and to the fnode.
1527  * Otherwise, set the time and return 0.
1528  */
1529 int
1530 fifo_setattr(
1531         vnode_t                 *vp,
1532         vattr_t                 *vap,
1533         int                     flags,
1534         cred_t                  *crp,
1535         caller_context_t        *ctp)
1536 {
1537         fifonode_t      *fnp    = VTOF(vp);
1538         int             error   = 0;
1539         fifolock_t      *fn_lock;
1540 
1541         if (fnp->fn_realvp)
1542                 error = VOP_SETATTR(fnp->fn_realvp, vap, flags, crp, ctp);
1543         if (error == 0) {
1544                 fn_lock = fnp->fn_lock;
1545                 mutex_enter(&fn_lock->flk_lock);
1546                 if (vap->va_mask & AT_ATIME)
1547                         fnp->fn_atime = vap->va_atime.tv_sec;
1548                 if (vap->va_mask & AT_MTIME)
1549                         fnp->fn_mtime = vap->va_mtime.tv_sec;
1550                 fnp->fn_ctime = gethrestime_sec();
1551                 mutex_exit(&fn_lock->flk_lock);
1552         }
1553         return (error);
1554 }
1555 
1556 /*
1557  * If shadowing a vnode, apply VOP_ACCESS to it.
1558  * Otherwise, return 0 (allow all access).
1559  */
1560 int
1561 fifo_access(vnode_t *vp, int mode, int flags, cred_t *crp, caller_context_t *ct)
1562 {
1563         if (VTOF(vp)->fn_realvp)
1564                 return (VOP_ACCESS(VTOF(vp)->fn_realvp, mode, flags, crp, ct));
1565         else
1566                 return (0);
1567 }
1568 
1569 /*
1570  * This can be called if creat or an open with O_CREAT is done on the root
1571  * of a lofs mount where the mounted entity is a fifo.
1572  */
1573 /*ARGSUSED*/
1574 static int
1575 fifo_create(struct vnode *dvp, char *name, vattr_t *vap, enum vcexcl excl,
1576     int mode, struct vnode **vpp, struct cred *cr, int flag,
1577     caller_context_t *ct, vsecattr_t *vsecp)
1578 {
1579         int error;
1580 
1581         ASSERT(dvp && (dvp->v_flag & VROOT) && *name == '\0');
1582         if (excl == NONEXCL) {
1583                 if (mode && (error = fifo_access(dvp, mode, 0, cr, ct)))
1584                         return (error);
1585                 VN_HOLD(dvp);
1586                 return (0);
1587         }
1588         return (EEXIST);
1589 }
1590 
1591 /*
1592  * If shadowing a vnode, apply the VOP_FSYNC to it.
1593  * Otherwise, return 0.
1594  */
1595 int
1596 fifo_fsync(vnode_t *vp, int syncflag, cred_t *crp, caller_context_t *ct)
1597 {
1598         fifonode_t      *fnp    = VTOF(vp);
1599         vattr_t         va;
1600 
1601         if (fnp->fn_realvp == NULL)
1602                 return (0);
1603 
1604         bzero((caddr_t)&va, sizeof (va));
1605         va.va_mask = AT_MTIME | AT_ATIME;
1606         if (VOP_GETATTR(fnp->fn_realvp, &va, 0, crp, ct) == 0) {
1607                 va.va_mask = 0;
1608                 if (fnp->fn_mtime > va.va_mtime.tv_sec) {
1609                         va.va_mtime.tv_sec = fnp->fn_mtime;
1610                         va.va_mask = AT_MTIME;
1611                 }
1612                 if (fnp->fn_atime > va.va_atime.tv_sec) {
1613                         va.va_atime.tv_sec = fnp->fn_atime;
1614                         va.va_mask |= AT_ATIME;
1615                 }
1616                 if (va.va_mask != 0)
1617                         (void) VOP_SETATTR(fnp->fn_realvp, &va, 0, crp, ct);
1618         }
1619         return (VOP_FSYNC(fnp->fn_realvp, syncflag, crp, ct));
1620 }
1621 
1622 /*
1623  * Called when the upper level no longer holds references to the
1624  * vnode. Sync the file system and free the fifonode.
1625  */
1626 void
1627 fifo_inactive(vnode_t *vp, cred_t *crp, caller_context_t *ct)
1628 {
1629         fifonode_t      *fnp;
1630         fifolock_t      *fn_lock;
1631 
1632         mutex_enter(&ftable_lock);
1633         mutex_enter(&vp->v_lock);
1634         ASSERT(vp->v_count >= 1);
1635         if (--vp->v_count != 0) {
1636                 /*
1637                  * Somebody accessed the fifo before we got a chance to
1638                  * remove it.  They will remove it when they do a vn_rele.
1639                  */
1640                 mutex_exit(&vp->v_lock);
1641                 mutex_exit(&ftable_lock);
1642                 return;
1643         }
1644         mutex_exit(&vp->v_lock);
1645 
1646         fnp = VTOF(vp);
1647 
1648         /*
1649          * remove fifo from fifo list so that no other process
1650          * can grab it.
1651          * Drop the reference count on the fifo node's
1652          * underlying vfs.
1653          */
1654         if (fnp->fn_realvp) {
1655                 (void) fiforemove(fnp);
1656                 mutex_exit(&ftable_lock);
1657                 (void) fifo_fsync(vp, FSYNC, crp, ct);
1658                 VN_RELE(fnp->fn_realvp);
1659                 VFS_RELE(vp->v_vfsp);
1660                 vp->v_vfsp = NULL;
1661         } else
1662                 mutex_exit(&ftable_lock);
1663 
1664         fn_lock = fnp->fn_lock;
1665 
1666         mutex_enter(&fn_lock->flk_lock);
1667         ASSERT(vp->v_stream == NULL);
1668         ASSERT(vp->v_count == 0);
1669         /*
1670          * if this is last reference to the lock, then we can
1671          * free everything up.
1672          */
1673         if (--fn_lock->flk_ref == 0) {
1674                 mutex_exit(&fn_lock->flk_lock);
1675                 ASSERT(fnp->fn_open == 0);
1676                 ASSERT(fnp->fn_dest->fn_open == 0);
1677                 if (fnp->fn_mp) {
1678                         freemsg(fnp->fn_mp);
1679                         fnp->fn_mp = NULL;
1680                         fnp->fn_count = 0;
1681                 }
1682                 if (fnp->fn_pcredp != NULL) {
1683                         crfree(fnp->fn_pcredp);
1684                         fnp->fn_pcredp = NULL;
1685                 }
1686                 if (fnp->fn_flag & ISPIPE) {
1687                         fifonode_t *fn_dest = fnp->fn_dest;
1688 
1689                         vp = FTOV(fn_dest);
1690                         if (fn_dest->fn_mp) {
1691                                 freemsg(fn_dest->fn_mp);
1692                                 fn_dest->fn_mp = NULL;
1693                                 fn_dest->fn_count = 0;
1694                         }
1695                         if (fn_dest->fn_pcredp != NULL) {
1696                                 crfree(fn_dest->fn_pcredp);
1697                                 fn_dest->fn_pcredp = NULL;
1698                         }
1699                         kmem_cache_free(pipe_cache, (fifodata_t *)fn_lock);
1700                 } else
1701                         kmem_cache_free(fnode_cache, (fifodata_t *)fn_lock);
1702         } else {
1703                 mutex_exit(&fn_lock->flk_lock);
1704         }
1705 }
1706 
1707 /*
1708  * If shadowing a vnode, apply the VOP_FID to it.
1709  * Otherwise, return EINVAL.
1710  */
1711 int
1712 fifo_fid(vnode_t *vp, fid_t *fidfnp, caller_context_t *ct)
1713 {
1714         if (VTOF(vp)->fn_realvp)
1715                 return (VOP_FID(VTOF(vp)->fn_realvp, fidfnp, ct));
1716         else
1717                 return (EINVAL);
1718 }
1719 
1720 /*
1721  * Lock a fifonode.
1722  */
1723 /* ARGSUSED */
1724 int
1725 fifo_rwlock(vnode_t *vp, int write_lock, caller_context_t *ctp)
1726 {
1727         return (-1);
1728 }
1729 
1730 /*
1731  * Unlock a fifonode.
1732  */
1733 /* ARGSUSED */
1734 void
1735 fifo_rwunlock(vnode_t *vp, int write_lock, caller_context_t *ctp)
1736 {
1737 }
1738 
1739 /*
1740  * Return error since seeks are not allowed on pipes.
1741  */
1742 /*ARGSUSED*/
1743 int
1744 fifo_seek(vnode_t *vp, offset_t ooff, offset_t *noffp, caller_context_t *ct)
1745 {
1746         return (ESPIPE);
1747 }
1748 
1749 /*
1750  * If there is a realvp associated with vp, return it.
1751  */
1752 int
1753 fifo_realvp(vnode_t *vp, vnode_t **vpp, caller_context_t *ct)
1754 {
1755         vnode_t *rvp;
1756 
1757         if ((rvp = VTOF(vp)->fn_realvp) != NULL) {
1758                 vp = rvp;
1759                 if (VOP_REALVP(vp, &rvp, ct) == 0)
1760                         vp = rvp;
1761         }
1762 
1763         *vpp = vp;
1764         return (0);
1765 }
1766 
1767 /*
1768  * Poll for interesting events on a stream pipe
1769  */
1770 /* ARGSUSED */
1771 int
1772 fifo_poll(vnode_t *vp, short events, int anyyet, short *reventsp,
1773         pollhead_t **phpp, caller_context_t *ct)
1774 {
1775         fifonode_t      *fnp, *fn_dest;
1776         fifolock_t      *fn_lock;
1777         int             retevents;
1778         struct stdata   *stp;
1779 
1780         ASSERT(vp->v_stream != NULL);
1781 
1782         stp = vp->v_stream;
1783         retevents       = 0;
1784         fnp             = VTOF(vp);
1785         fn_dest         = fnp->fn_dest;
1786         fn_lock         = fnp->fn_lock;
1787 
1788         if (polllock(&stp->sd_pollist, &fn_lock->flk_lock) != 0) {
1789                 *reventsp = POLLNVAL;
1790                 return (0);
1791         }
1792 
1793         /*
1794          * see if FIFO/pipe open
1795          */
1796         if ((fnp->fn_flag & FIFOISOPEN) == 0) {
1797                 if (((events & (POLLIN | POLLRDNORM | POLLPRI | POLLRDBAND)) &&
1798                     fnp->fn_rcnt == 0) ||
1799                     ((events & (POLLWRNORM | POLLWRBAND)) &&
1800                     fnp->fn_wcnt == 0)) {
1801                         mutex_exit(&fnp->fn_lock->flk_lock);
1802                         *reventsp = POLLERR;
1803                         return (0);
1804                 }
1805         }
1806 
1807         /*
1808          * if not in fast mode, let the stream head take care of it
1809          */
1810         if (!(fnp->fn_flag & FIFOFAST)) {
1811                 mutex_exit(&fnp->fn_lock->flk_lock);
1812                 goto stream_mode;
1813         }
1814 
1815         /*
1816          * If this is a pipe.. check to see if the other
1817          * end is gone.  If we are a fifo, check to see
1818          * if write end is gone.
1819          */
1820 
1821         if ((fnp->fn_flag & ISPIPE) && (fn_dest->fn_open == 0)) {
1822                 retevents = POLLHUP;
1823         } else if ((fnp->fn_flag & (FIFOCLOSE | ISPIPE)) == FIFOCLOSE &&
1824             (fn_dest->fn_wcnt == 0)) {
1825                 /*
1826                  * no writer at other end.
1827                  * it was closed (versus yet to be opened)
1828                  */
1829                         retevents = POLLHUP;
1830         } else if (events & (POLLWRNORM | POLLWRBAND)) {
1831                 if (events & POLLWRNORM) {
1832                         if (fn_dest->fn_count < Fifohiwat)
1833                                 retevents = POLLWRNORM;
1834                         else
1835                                 fnp->fn_flag |= FIFOHIWATW;
1836                 }
1837                 /*
1838                  * This is always true for fast pipes
1839                  * (Note: will go to STREAMS mode if band data is written)
1840                  */
1841                 if (events & POLLWRBAND)
1842                         retevents |= POLLWRBAND;
1843         }
1844         if (events & (POLLIN | POLLRDNORM)) {
1845                 if (fnp->fn_count)
1846                         retevents |= (events & (POLLIN | POLLRDNORM));
1847         }
1848 
1849         /*
1850          * if we happened to get something and we're not edge-triggered, return
1851          */
1852         if ((*reventsp = (short)retevents) != 0 && !(events & POLLET)) {
1853                 mutex_exit(&fnp->fn_lock->flk_lock);
1854                 return (0);
1855         }
1856 
1857         /*
1858          * If poll() has not found any events yet or we're edge-triggered, set
1859          * up event cell to wake up the poll if a requested event occurs on this
1860          * pipe/fifo.
1861          */
1862         if (!anyyet) {
1863                 if (events & POLLWRNORM)
1864                         fnp->fn_flag |= FIFOPOLLW;
1865                 if (events & (POLLIN | POLLRDNORM))
1866                         fnp->fn_flag |= FIFOPOLLR;
1867                 if (events & POLLRDBAND)
1868                         fnp->fn_flag |= FIFOPOLLRBAND;
1869                 /*
1870                  * XXX Don't like exposing this from streams
1871                  */
1872                 *phpp = &stp->sd_pollist;
1873         }
1874         mutex_exit(&fnp->fn_lock->flk_lock);
1875         return (0);
1876 stream_mode:
1877         return (strpoll(stp, events, anyyet, reventsp, phpp));
1878 }
1879 
1880 /*
1881  * POSIX pathconf() support.
1882  */
1883 /* ARGSUSED */
1884 int
1885 fifo_pathconf(vnode_t *vp, int cmd, ulong_t *valp, cred_t *cr,
1886         caller_context_t *ct)
1887 {
1888         ulong_t val;
1889         int error = 0;
1890 
1891         switch (cmd) {
1892 
1893         case _PC_LINK_MAX:
1894                 val = MAXLINK;
1895                 break;
1896 
1897         case _PC_MAX_CANON:
1898                 val = MAX_CANON;
1899                 break;
1900 
1901         case _PC_MAX_INPUT:
1902                 val = MAX_INPUT;
1903                 break;
1904 
1905         case _PC_NAME_MAX:
1906                 error = EINVAL;
1907                 break;
1908 
1909         case _PC_PATH_MAX:
1910         case _PC_SYMLINK_MAX:
1911                 val = MAXPATHLEN;
1912                 break;
1913 
1914         case _PC_PIPE_BUF:
1915                 val = PIPE_BUF;
1916                 break;
1917 
1918         case _PC_NO_TRUNC:
1919                 if (vp->v_vfsp->vfs_flag & VFS_NOTRUNC)
1920                         val = 1;        /* NOTRUNC is enabled for vp */
1921                 else
1922                         val = (ulong_t)-1;
1923                 break;
1924 
1925         case _PC_VDISABLE:
1926                 val = _POSIX_VDISABLE;
1927                 break;
1928 
1929         case _PC_CHOWN_RESTRICTED:
1930                 if (rstchown)
1931                         val = rstchown;         /* chown restricted enabled */
1932                 else
1933                         val = (ulong_t)-1;
1934                 break;
1935 
1936         case _PC_FILESIZEBITS:
1937                 val = (ulong_t)-1;
1938                 break;
1939 
1940         default:
1941                 if (VTOF(vp)->fn_realvp)
1942                         error = VOP_PATHCONF(VTOF(vp)->fn_realvp, cmd,
1943                             &val, cr, ct);
1944                 else
1945                         error = EINVAL;
1946                 break;
1947         }
1948 
1949         if (error == 0)
1950                 *valp = val;
1951         return (error);
1952 }
1953 
1954 /*
1955  * If shadowing a vnode, apply VOP_SETSECATTR to it.
1956  * Otherwise, return NOSYS.
1957  */
1958 int
1959 fifo_setsecattr(struct vnode *vp, vsecattr_t *vsap, int flag, struct cred *crp,
1960         caller_context_t *ct)
1961 {
1962         int error;
1963 
1964         /*
1965          * The acl(2) system call tries to grab the write lock on the
1966          * file when setting an ACL, but fifofs does not implement
1967          * VOP_RWLOCK or VOP_RWUNLOCK, so we do it here instead.
1968          */
1969         if (VTOF(vp)->fn_realvp) {
1970                 (void) VOP_RWLOCK(VTOF(vp)->fn_realvp, V_WRITELOCK_TRUE, ct);
1971                 error = VOP_SETSECATTR(VTOF(vp)->fn_realvp, vsap, flag,
1972                     crp, ct);
1973                 VOP_RWUNLOCK(VTOF(vp)->fn_realvp, V_WRITELOCK_TRUE, ct);
1974                 return (error);
1975         } else
1976                 return (fs_nosys());
1977 }
1978 
1979 /*
1980  * If shadowing a vnode, apply VOP_GETSECATTR to it. Otherwise, fabricate
1981  * an ACL from the permission bits that fifo_getattr() makes up.
1982  */
1983 int
1984 fifo_getsecattr(struct vnode *vp, vsecattr_t *vsap, int flag, struct cred *crp,
1985         caller_context_t *ct)
1986 {
1987         if (VTOF(vp)->fn_realvp)
1988                 return (VOP_GETSECATTR(VTOF(vp)->fn_realvp, vsap, flag,
1989                     crp, ct));
1990         else
1991                 return (fs_fab_acl(vp, vsap, flag, crp, ct));
1992 }
1993 
1994 
1995 /*
1996  * Set the FIFOSTAYFAST flag so nobody can turn the fifo into stream mode.
1997  * If the flag is already set then wait until it is removed - releasing
1998  * the lock.
1999  * If the fifo switches into stream mode while we are waiting, return failure.
2000  */
2001 static boolean_t
2002 fifo_stayfast_enter(fifonode_t *fnp)
2003 {
2004         ASSERT(MUTEX_HELD(&fnp->fn_lock->flk_lock));
2005         while (fnp->fn_flag & FIFOSTAYFAST) {
2006                 fnp->fn_flag |= FIFOWAITMODE;
2007                 cv_wait(&fnp->fn_wait_cv, &fnp->fn_lock->flk_lock);
2008                 fnp->fn_flag &= ~FIFOWAITMODE;
2009         }
2010         if (!(fnp->fn_flag & FIFOFAST))
2011                 return (B_FALSE);
2012 
2013         fnp->fn_flag |= FIFOSTAYFAST;
2014         return (B_TRUE);
2015 }
2016 
2017 /*
2018  * Unset the FIFOSTAYFAST flag and notify anybody waiting for this flag
2019  * to be removed:
2020  *      - threads wanting to turn into stream mode waiting in fifo_fastoff(),
2021  *      - other writers threads waiting in fifo_stayfast_enter().
2022  */
2023 static void
2024 fifo_stayfast_exit(fifonode_t *fnp)
2025 {
2026         fifonode_t *fn_dest = fnp->fn_dest;
2027 
2028         ASSERT(MUTEX_HELD(&fnp->fn_lock->flk_lock));
2029 
2030         fnp->fn_flag &= ~FIFOSTAYFAST;
2031 
2032         if (fnp->fn_flag & FIFOWAITMODE)
2033                 cv_broadcast(&fnp->fn_wait_cv);
2034 
2035         if ((fnp->fn_flag & ISPIPE) && (fn_dest->fn_flag & FIFOWAITMODE))
2036                 cv_broadcast(&fn_dest->fn_wait_cv);
2037 }