Print this page
XXXX adding PID information to netstat output


  61 #include <sys/debug.h>
  62 #include <sys/strredir.h>
  63 #include <sys/fs/fifonode.h>
  64 #include <sys/fs/snode.h>
  65 #include <sys/strlog.h>
  66 #include <sys/strsun.h>
  67 #include <sys/project.h>
  68 #include <sys/kbio.h>
  69 #include <sys/msio.h>
  70 #include <sys/tty.h>
  71 #include <sys/ptyvar.h>
  72 #include <sys/vuid_event.h>
  73 #include <sys/modctl.h>
  74 #include <sys/sunddi.h>
  75 #include <sys/sunldi_impl.h>
  76 #include <sys/autoconf.h>
  77 #include <sys/policy.h>
  78 #include <sys/dld.h>
  79 #include <sys/zone.h>
  80 #include <c2/audit.h>

  81 
  82 /*
  83  * This define helps improve the readability of streams code while
  84  * still maintaining a very old streams performance enhancement.  The
  85  * performance enhancement basically involved having all callers
  86  * of straccess() perform the first check that straccess() will do
  87  * locally before actually calling straccess().  (There by reducing
  88  * the number of unnecessary calls to straccess().)
  89  */
  90 #define i_straccess(x, y)       ((stp->sd_sidp == NULL) ? 0 : \
  91                                     (stp->sd_vnode->v_type == VFIFO) ? 0 : \
  92                                     straccess((x), (y)))
  93 
  94 /*
  95  * what is mblk_pull_len?
  96  *
  97  * If a streams message consists of many short messages,
  98  * a performance degradation occurs from copyout overhead.
  99  * To decrease the per mblk overhead, messages that are
 100  * likely to consist of many small mblks are pulled up into


 126  * The "new semantics" are that TIOCGETP returns B38400 for
 127  * sg_[io]speed if the corresponding value is over B38400, and that
 128  * TIOCSET[PN] accept B38400 in these cases to mean "retain current
 129  * bit rate."
 130  */
 131 int sgttyb_handling = 1;
 132 static boolean_t sgttyb_complaint;
 133 
 134 /* don't push drcompat module by default on Style-2 streams */
 135 static int push_drcompat = 0;
 136 
 137 /*
 138  * id value used to distinguish between different ioctl messages
 139  */
 140 static uint32_t ioc_id;
 141 
 142 static void putback(struct stdata *, queue_t *, mblk_t *, int);
 143 static void strcleanall(struct vnode *);
 144 static int strwsrv(queue_t *);
 145 static int strdocmd(struct stdata *, struct strcmd *, cred_t *);

 146 
 147 /*
 148  * qinit and module_info structures for stream head read and write queues
 149  */
 150 struct module_info strm_info = { 0, "strrhead", 0, INFPSZ, STRHIGH, STRLOW };
 151 struct module_info stwm_info = { 0, "strwhead", 0, 0, 0, 0 };
 152 struct qinit strdata = { strrput, NULL, NULL, NULL, NULL, &strm_info };
 153 struct qinit stwdata = { NULL, strwsrv, NULL, NULL, NULL, &stwm_info };
 154 struct module_info fiform_info = { 0, "fifostrrhead", 0, PIPE_BUF, FIFOHIWAT,
 155     FIFOLOWAT };
 156 struct module_info fifowm_info = { 0, "fifostrwhead", 0, 0, 0, 0 };
 157 struct qinit fifo_strdata = { strrput, NULL, NULL, NULL, NULL, &fiform_info };
 158 struct qinit fifo_stwdata = { NULL, strwsrv, NULL, NULL, NULL, &fifowm_info };
 159 
 160 extern kmutex_t strresources;   /* protects global resources */
 161 extern kmutex_t muxifier;       /* single-threads multiplexor creation */
 162 
 163 static boolean_t msghasdata(mblk_t *bp);
 164 #define msgnodata(bp) (!msghasdata(bp))
 165 


 380         stp->sd_sigflags = 0;
 381         stp->sd_mark = NULL;
 382         stp->sd_closetime = STRTIMOUT;
 383         stp->sd_sidp = NULL;
 384         stp->sd_pgidp = NULL;
 385         stp->sd_vnode = vp;
 386         stp->sd_rerror = 0;
 387         stp->sd_werror = 0;
 388         stp->sd_wroff = 0;
 389         stp->sd_tail = 0;
 390         stp->sd_iocblk = NULL;
 391         stp->sd_cmdblk = NULL;
 392         stp->sd_pushcnt = 0;
 393         stp->sd_qn_minpsz = 0;
 394         stp->sd_qn_maxpsz = INFPSZ - 1;      /* used to check for initialization */
 395         stp->sd_maxblk = INFPSZ;
 396         qp->q_ptr = _WR(qp)->q_ptr = stp;
 397         STREAM(qp) = STREAM(_WR(qp)) = stp;
 398         vp->v_stream = stp;
 399         mutex_exit(&vp->v_lock);








 400         if (vp->v_type == VFIFO) {
 401                 stp->sd_flag |= OLDNDELAY;
 402                 /*
 403                  * This means, both for pipes and fifos
 404                  * strwrite will send SIGPIPE if the other
 405                  * end is closed. For putmsg it depends
 406                  * on whether it is a XPG4_2 application
 407                  * or not
 408                  */
 409                 stp->sd_wput_opt = SW_SIGPIPE;
 410 
 411                 /* setq might sleep in kmem_alloc - avoid holding locks. */
 412                 setq(qp, &fifo_strdata, &fifo_stwdata, NULL, QMTSAFE,
 413                     SQ_CI|SQ_CO, B_FALSE);
 414 
 415                 set_qend(qp);
 416                 stp->sd_strtab = fifo_getinfo();
 417                 _WR(qp)->q_nfsrv = _WR(qp);
 418                 qp->q_nfsrv = qp;
 419                 /*


5666                 return (strcopyout(&pgrp, (void *)arg, sizeof (pid_t),
5667                     copyflag));
5668         }
5669 
5670         case TIOCSCTTY:
5671         {
5672                 return (strctty(stp));
5673         }
5674 
5675         case TIOCNOTTY:
5676         {
5677                 /* freectty() always assumes curproc. */
5678                 if (freectty(B_FALSE) != 0)
5679                         return (0);
5680                 return (ENOTTY);
5681         }
5682 
5683         case FIONBIO:
5684         case FIOASYNC:
5685                 return (0);     /* handled by the upper layer */
















5686         }
5687 }
5688 
5689 /*
5690  * Custom free routine used for M_PASSFP messages.
5691  */
5692 static void
5693 free_passfp(struct k_strrecvfd *srf)
5694 {
5695         (void) closef(srf->fp);
5696         kmem_free(srf, sizeof (struct k_strrecvfd) + sizeof (frtn_t));
5697 }
5698 
5699 /* ARGSUSED */
5700 int
5701 do_sendfp(struct stdata *stp, struct file *fp, struct cred *cr)
5702 {
5703         queue_t *qp, *nextqp;
5704         struct k_strrecvfd *srf;
5705         mblk_t *mp;


8616         if (update) {
8617                 stp->sd_sigflags = 0;
8618                 for (ssp = stp->sd_siglist; ssp; ssp = ssp->ss_next)
8619                         stp->sd_sigflags |= ssp->ss_events;
8620         }
8621         mutex_exit(&stp->sd_lock);
8622 }
8623 
8624 /*
8625  * Return B_TRUE if there is data in the message, B_FALSE otherwise.
8626  */
8627 static boolean_t
8628 msghasdata(mblk_t *bp)
8629 {
8630         for (; bp; bp = bp->b_cont)
8631                 if (bp->b_datap->db_type == M_DATA) {
8632                         ASSERT(bp->b_wptr >= bp->b_rptr);
8633                         if (bp->b_wptr > bp->b_rptr)
8634                                 return (B_TRUE);
8635                 }






























8636         return (B_FALSE);
8637 }


  61 #include <sys/debug.h>
  62 #include <sys/strredir.h>
  63 #include <sys/fs/fifonode.h>
  64 #include <sys/fs/snode.h>
  65 #include <sys/strlog.h>
  66 #include <sys/strsun.h>
  67 #include <sys/project.h>
  68 #include <sys/kbio.h>
  69 #include <sys/msio.h>
  70 #include <sys/tty.h>
  71 #include <sys/ptyvar.h>
  72 #include <sys/vuid_event.h>
  73 #include <sys/modctl.h>
  74 #include <sys/sunddi.h>
  75 #include <sys/sunldi_impl.h>
  76 #include <sys/autoconf.h>
  77 #include <sys/policy.h>
  78 #include <sys/dld.h>
  79 #include <sys/zone.h>
  80 #include <c2/audit.h>
  81 #include <sys/fcntl.h>
  82 
  83 /*
  84  * This define helps improve the readability of streams code while
  85  * still maintaining a very old streams performance enhancement.  The
  86  * performance enhancement basically involved having all callers
  87  * of straccess() perform the first check that straccess() will do
  88  * locally before actually calling straccess().  (There by reducing
  89  * the number of unnecessary calls to straccess().)
  90  */
  91 #define i_straccess(x, y)       ((stp->sd_sidp == NULL) ? 0 : \
  92                                     (stp->sd_vnode->v_type == VFIFO) ? 0 : \
  93                                     straccess((x), (y)))
  94 
  95 /*
  96  * what is mblk_pull_len?
  97  *
  98  * If a streams message consists of many short messages,
  99  * a performance degradation occurs from copyout overhead.
 100  * To decrease the per mblk overhead, messages that are
 101  * likely to consist of many small mblks are pulled up into


 127  * The "new semantics" are that TIOCGETP returns B38400 for
 128  * sg_[io]speed if the corresponding value is over B38400, and that
 129  * TIOCSET[PN] accept B38400 in these cases to mean "retain current
 130  * bit rate."
 131  */
 132 int sgttyb_handling = 1;
 133 static boolean_t sgttyb_complaint;
 134 
 135 /* don't push drcompat module by default on Style-2 streams */
 136 static int push_drcompat = 0;
 137 
 138 /*
 139  * id value used to distinguish between different ioctl messages
 140  */
 141 static uint32_t ioc_id;
 142 
 143 static void putback(struct stdata *, queue_t *, mblk_t *, int);
 144 static void strcleanall(struct vnode *);
 145 static int strwsrv(queue_t *);
 146 static int strdocmd(struct stdata *, struct strcmd *, cred_t *);
 147 static boolean_t is_xti_str(const struct stdata *);
 148 
 149 /*
 150  * qinit and module_info structures for stream head read and write queues
 151  */
 152 struct module_info strm_info = { 0, "strrhead", 0, INFPSZ, STRHIGH, STRLOW };
 153 struct module_info stwm_info = { 0, "strwhead", 0, 0, 0, 0 };
 154 struct qinit strdata = { strrput, NULL, NULL, NULL, NULL, &strm_info };
 155 struct qinit stwdata = { NULL, strwsrv, NULL, NULL, NULL, &stwm_info };
 156 struct module_info fiform_info = { 0, "fifostrrhead", 0, PIPE_BUF, FIFOHIWAT,
 157     FIFOLOWAT };
 158 struct module_info fifowm_info = { 0, "fifostrwhead", 0, 0, 0, 0 };
 159 struct qinit fifo_strdata = { strrput, NULL, NULL, NULL, NULL, &fiform_info };
 160 struct qinit fifo_stwdata = { NULL, strwsrv, NULL, NULL, NULL, &fifowm_info };
 161 
 162 extern kmutex_t strresources;   /* protects global resources */
 163 extern kmutex_t muxifier;       /* single-threads multiplexor creation */
 164 
 165 static boolean_t msghasdata(mblk_t *bp);
 166 #define msgnodata(bp) (!msghasdata(bp))
 167 


 382         stp->sd_sigflags = 0;
 383         stp->sd_mark = NULL;
 384         stp->sd_closetime = STRTIMOUT;
 385         stp->sd_sidp = NULL;
 386         stp->sd_pgidp = NULL;
 387         stp->sd_vnode = vp;
 388         stp->sd_rerror = 0;
 389         stp->sd_werror = 0;
 390         stp->sd_wroff = 0;
 391         stp->sd_tail = 0;
 392         stp->sd_iocblk = NULL;
 393         stp->sd_cmdblk = NULL;
 394         stp->sd_pushcnt = 0;
 395         stp->sd_qn_minpsz = 0;
 396         stp->sd_qn_maxpsz = INFPSZ - 1;      /* used to check for initialization */
 397         stp->sd_maxblk = INFPSZ;
 398         qp->q_ptr = _WR(qp)->q_ptr = stp;
 399         STREAM(qp) = STREAM(_WR(qp)) = stp;
 400         vp->v_stream = stp;
 401         mutex_exit(&vp->v_lock);
 402 
 403         /*
 404          * If this is not a system process, then add it to
 405          * the list associated with the stream head.
 406          */
 407         if (!(curproc->p_flag & SSYS) && is_xti_str(stp))
 408                 sh_insert_pid(stp, curproc->p_pidp->pid_id);
 409 
 410         if (vp->v_type == VFIFO) {
 411                 stp->sd_flag |= OLDNDELAY;
 412                 /*
 413                  * This means, both for pipes and fifos
 414                  * strwrite will send SIGPIPE if the other
 415                  * end is closed. For putmsg it depends
 416                  * on whether it is a XPG4_2 application
 417                  * or not
 418                  */
 419                 stp->sd_wput_opt = SW_SIGPIPE;
 420 
 421                 /* setq might sleep in kmem_alloc - avoid holding locks. */
 422                 setq(qp, &fifo_strdata, &fifo_stwdata, NULL, QMTSAFE,
 423                     SQ_CI|SQ_CO, B_FALSE);
 424 
 425                 set_qend(qp);
 426                 stp->sd_strtab = fifo_getinfo();
 427                 _WR(qp)->q_nfsrv = _WR(qp);
 428                 qp->q_nfsrv = qp;
 429                 /*


5676                 return (strcopyout(&pgrp, (void *)arg, sizeof (pid_t),
5677                     copyflag));
5678         }
5679 
5680         case TIOCSCTTY:
5681         {
5682                 return (strctty(stp));
5683         }
5684 
5685         case TIOCNOTTY:
5686         {
5687                 /* freectty() always assumes curproc. */
5688                 if (freectty(B_FALSE) != 0)
5689                         return (0);
5690                 return (ENOTTY);
5691         }
5692 
5693         case FIONBIO:
5694         case FIOASYNC:
5695                 return (0);     /* handled by the upper layer */
5696         case F_ASSOCI_PID:
5697         {
5698                 if (crp != kcred)
5699                         return (EPERM);
5700                 if (is_xti_str(stp))
5701                         sh_insert_pid(stp, (pid_t)arg);
5702                 return (0);
5703         }
5704         case F_DASSOC_PID:
5705         {
5706                 if (crp != kcred)
5707                         return (EPERM);
5708                 if (is_xti_str(stp))
5709                         sh_remove_pid(stp, (pid_t)arg);
5710                 return (0);
5711         }
5712         }
5713 }
5714 
5715 /*
5716  * Custom free routine used for M_PASSFP messages.
5717  */
5718 static void
5719 free_passfp(struct k_strrecvfd *srf)
5720 {
5721         (void) closef(srf->fp);
5722         kmem_free(srf, sizeof (struct k_strrecvfd) + sizeof (frtn_t));
5723 }
5724 
5725 /* ARGSUSED */
5726 int
5727 do_sendfp(struct stdata *stp, struct file *fp, struct cred *cr)
5728 {
5729         queue_t *qp, *nextqp;
5730         struct k_strrecvfd *srf;
5731         mblk_t *mp;


8642         if (update) {
8643                 stp->sd_sigflags = 0;
8644                 for (ssp = stp->sd_siglist; ssp; ssp = ssp->ss_next)
8645                         stp->sd_sigflags |= ssp->ss_events;
8646         }
8647         mutex_exit(&stp->sd_lock);
8648 }
8649 
8650 /*
8651  * Return B_TRUE if there is data in the message, B_FALSE otherwise.
8652  */
8653 static boolean_t
8654 msghasdata(mblk_t *bp)
8655 {
8656         for (; bp; bp = bp->b_cont)
8657                 if (bp->b_datap->db_type == M_DATA) {
8658                         ASSERT(bp->b_wptr >= bp->b_rptr);
8659                         if (bp->b_wptr > bp->b_rptr)
8660                                 return (B_TRUE);
8661                 }
8662         return (B_FALSE);
8663 }
8664 
8665 /*
8666  * Check whether a stream is an XTI stream or not.
8667  */
8668 static boolean_t
8669 is_xti_str(const struct stdata *stp)
8670 {
8671         struct devnames *dnp;
8672         vnode_t *vn;
8673         major_t major;
8674         if ((vn = stp->sd_vnode) != NULL && vn->v_type == VCHR &&
8675             vn->v_rdev != 0) {
8676                 major = getmajor(vn->v_rdev);
8677                 dnp = (major != DDI_MAJOR_T_NONE && major >= 0 &&
8678                     major < devcnt) ? &devnamesp[major] : NULL;
8679                 if (dnp != NULL && dnp->dn_name != NULL &&
8680                     (strcmp(dnp->dn_name, "ip") == 0 ||
8681                     strcmp(dnp->dn_name, "tcp") == 0 ||
8682                     strcmp(dnp->dn_name, "udp") == 0 ||
8683                     strcmp(dnp->dn_name, "icmp") == 0 ||
8684                     strcmp(dnp->dn_name, "tl") == 0 ||
8685                     strcmp(dnp->dn_name, "ip6") == 0 ||
8686                     strcmp(dnp->dn_name, "tcp6") == 0 ||
8687                     strcmp(dnp->dn_name, "udp6") == 0 ||
8688                     strcmp(dnp->dn_name, "icmp6") == 0)) {
8689                         return (B_TRUE);
8690                 }
8691         }
8692         return (B_FALSE);
8693 }