Home | History | Annotate | Download | only in netsmb
      1 /*
      2  * Copyright (c) 2000-2001 Boris Popov
      3  * All rights reserved.
      4  *
      5  * Redistribution and use in source and binary forms, with or without
      6  * modification, are permitted provided that the following conditions
      7  * are met:
      8  * 1. Redistributions of source code must retain the above copyright
      9  *    notice, this list of conditions and the following disclaimer.
     10  * 2. Redistributions in binary form must reproduce the above copyright
     11  *    notice, this list of conditions and the following disclaimer in the
     12  *    documentation and/or other materials provided with the distribution.
     13  * 3. All advertising materials mentioning features or use of this software
     14  *    must display the following acknowledgement:
     15  *    This product includes software developed by Boris Popov.
     16  * 4. Neither the name of the author nor the names of any co-contributors
     17  *    may be used to endorse or promote products derived from this software
     18  *    without specific prior written permission.
     19  *
     20  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
     21  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
     22  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
     23  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
     24  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
     25  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
     26  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
     27  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
     28  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
     29  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
     30  * SUCH DAMAGE.
     31  *
     32  * $Id: smb_iod.c,v 1.32 2005/02/12 00:17:09 lindak Exp $
     33  */
     34 
     35 /*
     36  * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
     37  * Use is subject to license terms.
     38  */
     39 
     40 #ifdef DEBUG
     41 /* See sys/queue.h */
     42 #define	QUEUEDEBUG 1
     43 #endif
     44 
     45 #include <sys/param.h>
     46 #include <sys/systm.h>
     47 #include <sys/atomic.h>
     48 #include <sys/proc.h>
     49 #include <sys/thread.h>
     50 #include <sys/file.h>
     51 #include <sys/kmem.h>
     52 #include <sys/unistd.h>
     53 #include <sys/mount.h>
     54 #include <sys/vnode.h>
     55 #include <sys/types.h>
     56 #include <sys/ddi.h>
     57 #include <sys/sunddi.h>
     58 #include <sys/stream.h>
     59 #include <sys/strsun.h>
     60 #include <sys/time.h>
     61 #include <sys/class.h>
     62 #include <sys/disp.h>
     63 #include <sys/cmn_err.h>
     64 #include <sys/zone.h>
     65 #include <sys/sdt.h>
     66 
     67 #include <netsmb/smb_osdep.h>
     68 
     69 #include <netsmb/smb.h>
     70 #include <netsmb/smb_conn.h>
     71 #include <netsmb/smb_rq.h>
     72 #include <netsmb/smb_subr.h>
     73 #include <netsmb/smb_tran.h>
     74 #include <netsmb/smb_trantcp.h>
     75 
     76 int smb_iod_send_echo(smb_vc_t *);
     77 
     78 /*
     79  * This is set/cleared when smbfs loads/unloads
     80  * No locks should be necessary, because smbfs
     81  * can't unload until all the mounts are gone.
     82  */
     83 static smb_fscb_t *fscb;
     84 void
     85 smb_fscb_set(smb_fscb_t *cb)
     86 {
     87 	fscb = cb;
     88 }
     89 
     90 static void
     91 smb_iod_share_disconnected(smb_share_t *ssp)
     92 {
     93 
     94 	smb_share_invalidate(ssp);
     95 
     96 	/* smbfs_dead() */
     97 	if (fscb && fscb->fscb_disconn) {
     98 		fscb->fscb_disconn(ssp);
     99 	}
    100 }
    101 
    102 /*
    103  * State changes are important and infrequent.
    104  * Make them easily observable via dtrace.
    105  */
    106 void
    107 smb_iod_newstate(struct smb_vc *vcp, int state)
    108 {
    109 	vcp->vc_state = state;
    110 }
    111 
    112 /* Lock Held version of the next function. */
    113 static inline void
    114 smb_iod_rqprocessed_LH(
    115 	struct smb_rq *rqp,
    116 	int error,
    117 	int flags)
    118 {
    119 	rqp->sr_flags |= flags;
    120 	rqp->sr_lerror = error;
    121 	rqp->sr_rpgen++;
    122 	rqp->sr_state = SMBRQ_NOTIFIED;
    123 	cv_broadcast(&rqp->sr_cond);
    124 }
    125 
    126 static void
    127 smb_iod_rqprocessed(
    128 	struct smb_rq *rqp,
    129 	int error,
    130 	int flags)
    131 {
    132 
    133 	SMBRQ_LOCK(rqp);
    134 	smb_iod_rqprocessed_LH(rqp, error, flags);
    135 	SMBRQ_UNLOCK(rqp);
    136 }
    137 
    138 static void
    139 smb_iod_invrq(struct smb_vc *vcp)
    140 {
    141 	struct smb_rq *rqp;
    142 
    143 	/*
    144 	 * Invalidate all outstanding requests for this connection
    145 	 */
    146 	rw_enter(&vcp->iod_rqlock, RW_READER);
    147 	TAILQ_FOREACH(rqp, &vcp->iod_rqlist, sr_link) {
    148 		smb_iod_rqprocessed(rqp, ENOTCONN, SMBR_RESTART);
    149 	}
    150 	rw_exit(&vcp->iod_rqlock);
    151 }
    152 
    153 /*
    154  * Called by smb_vc_rele, smb_vc_kill, and by the driver
    155  * close entry point if the IOD closes its dev handle.
    156  *
    157  * Forcibly kill the connection and IOD.
    158  */
    159 void
    160 smb_iod_disconnect(struct smb_vc *vcp)
    161 {
    162 
    163 	/*
    164 	 * Inform everyone of the state change.
    165 	 */
    166 	SMB_VC_LOCK(vcp);
    167 	if (vcp->vc_state != SMBIOD_ST_DEAD) {
    168 		smb_iod_newstate(vcp, SMBIOD_ST_DEAD);
    169 		cv_broadcast(&vcp->vc_statechg);
    170 	}
    171 	SMB_VC_UNLOCK(vcp);
    172 
    173 	/*
    174 	 * Let's be safe here and avoid doing any
    175 	 * call across the network while trying to
    176 	 * shut things down.  If we just disconnect,
    177 	 * the server will take care of the logoff.
    178 	 */
    179 	SMB_TRAN_DISCONNECT(vcp);
    180 
    181 	/*
    182 	 * If we have an IOD, it should immediately notice
    183 	 * that its connection has closed.  But in case
    184 	 * it doesn't, let's also send it a signal.
    185 	 * (but don't shoot our own foot!)
    186 	 * Note: the iod calls smb_iod_invrq on its way out.
    187 	 */
    188 	if (vcp->iod_thr != NULL &&
    189 	    vcp->iod_thr != curthread) {
    190 		tsignal(vcp->iod_thr, SIGKILL);
    191 	}
    192 }
    193 
    194 /*
    195  * Send one request.
    196  *
    197  * Called by _addrq (for internal requests)
    198  * and _sendall (via _addrq, _multirq, _waitrq)
    199  */
    200 static int
    201 smb_iod_sendrq(struct smb_rq *rqp)
    202 {
    203 	struct smb_vc *vcp = rqp->sr_vc;
    204 	mblk_t *m;
    205 	int error;
    206 
    207 	ASSERT(vcp);
    208 	ASSERT(SEMA_HELD(&vcp->vc_sendlock));
    209 	ASSERT(RW_READ_HELD(&vcp->iod_rqlock));
    210 
    211 	/*
    212 	 * Note: Anything special for SMBR_INTERNAL here?
    213 	 */
    214 	if (vcp->vc_state != SMBIOD_ST_VCACTIVE) {
    215 		SMBIODEBUG("bad vc_state=%d\n", vcp->vc_state);
    216 		return (ENOTCONN);
    217 	}
    218 
    219 
    220 	/*
    221 	 * On the first send, set the MID and (maybe)
    222 	 * the signing sequence numbers.  The increments
    223 	 * here are serialized by vc_sendlock
    224 	 */
    225 	if (rqp->sr_sendcnt == 0) {
    226 
    227 		rqp->sr_mid = vcp->vc_next_mid++;
    228 
    229 		if (rqp->sr_rqflags2 & SMB_FLAGS2_SECURITY_SIGNATURE) {
    230 			/*
    231 			 * We're signing requests and verifying
    232 			 * signatures on responses.  Set the
    233 			 * sequence numbers of the request and
    234 			 * response here, used in smb_rq_verify.
    235 			 */
    236 			rqp->sr_seqno = vcp->vc_next_seq++;
    237 			rqp->sr_rseqno = vcp->vc_next_seq++;
    238 		}
    239 
    240 		/* Fill in UID, TID, MID, etc. */
    241 		smb_rq_fillhdr(rqp);
    242 
    243 		/*
    244 		 * Sign the message now that we're finally done
    245 		 * filling in the SMB header fields, etc.
    246 		 */
    247 		if (rqp->sr_rqflags2 & SMB_FLAGS2_SECURITY_SIGNATURE) {
    248 			smb_rq_sign(rqp);
    249 		}
    250 	}
    251 	if (rqp->sr_sendcnt++ >= 60/SMBSBTIMO) { /* one minute */
    252 		smb_iod_rqprocessed(rqp, rqp->sr_lerror, SMBR_RESTART);
    253 		/*
    254 		 * If all attempts to send a request failed, then
    255 		 * something is seriously hosed.
    256 		 */
    257 		return (ENOTCONN);
    258 	}
    259 
    260 	/*
    261 	 * Replaced m_copym() with Solaris copymsg() which does the same
    262 	 * work when we want to do a M_COPYALL.
    263 	 * m = m_copym(rqp->sr_rq.mb_top, 0, M_COPYALL, 0);
    264 	 */
    265 	m = copymsg(rqp->sr_rq.mb_top);
    266 
    267 #ifdef DTRACE_PROBE
    268 	DTRACE_PROBE2(smb_iod_sendrq,
    269 	    (smb_rq_t *), rqp, (mblk_t *), m);
    270 #else
    271 	SMBIODEBUG("M:%04x, P:%04x, U:%04x, T:%04x\n", rqp->sr_mid, 0, 0, 0);
    272 #endif
    273 	m_dumpm(m);
    274 
    275 	if (m != NULL) {
    276 		error = SMB_TRAN_SEND(vcp, m);
    277 		m = 0; /* consumed by SEND */
    278 	} else
    279 		error = ENOBUFS;
    280 
    281 	rqp->sr_lerror = error;
    282 	if (error == 0) {
    283 		SMBRQ_LOCK(rqp);
    284 		rqp->sr_flags |= SMBR_SENT;
    285 		rqp->sr_state = SMBRQ_SENT;
    286 		if (rqp->sr_flags & SMBR_SENDWAIT)
    287 			cv_broadcast(&rqp->sr_cond);
    288 		SMBRQ_UNLOCK(rqp);
    289 		return (0);
    290 	}
    291 	/*
    292 	 * Check for fatal errors
    293 	 */
    294 	if (SMB_TRAN_FATAL(vcp, error)) {
    295 		/*
    296 		 * No further attempts should be made
    297 		 */
    298 		SMBSDEBUG("TRAN_SEND returned fatal error %d\n", error);
    299 		return (ENOTCONN);
    300 	}
    301 	if (error)
    302 		SMBSDEBUG("TRAN_SEND returned non-fatal error %d\n", error);
    303 
    304 #ifdef APPLE
    305 	/* If proc waiting on rqp was signaled... */
    306 	if (smb_rq_intr(rqp))
    307 		smb_iod_rqprocessed(rqp, EINTR, 0);
    308 #endif
    309 
    310 	return (0);
    311 }
    312 
    313 static int
    314 smb_iod_recv1(struct smb_vc *vcp, mblk_t **mpp)
    315 {
    316 	mblk_t *m;
    317 	uchar_t *hp;
    318 	int error;
    319 
    320 top:
    321 	m = NULL;
    322 	error = SMB_TRAN_RECV(vcp, &m);
    323 	if (error == EAGAIN)
    324 		goto top;
    325 	if (error)
    326 		return (error);
    327 	ASSERT(m);
    328 
    329 	m = m_pullup(m, SMB_HDRLEN);
    330 	if (m == NULL) {
    331 		return (ENOSR);
    332 	}
    333 
    334 	/*
    335 	 * Check the SMB header
    336 	 */
    337 	hp = mtod(m, uchar_t *);
    338 	if (bcmp(hp, SMB_SIGNATURE, SMB_SIGLEN) != 0) {
    339 		m_freem(m);
    340 		return (EPROTO);
    341 	}
    342 
    343 	*mpp = m;
    344 	return (0);
    345 }
    346 
    347 /*
    348  * Process incoming packets
    349  *
    350  * This is the "reader" loop, run by the IOD thread
    351  * while in state SMBIOD_ST_VCACTIVE.  The loop now
    352  * simply blocks in the socket recv until either a
    353  * message arrives, or a disconnect.
    354  *
    355  * Any non-zero error means the IOD should terminate.
    356  */
    357 int
    358 smb_iod_recvall(struct smb_vc *vcp)
    359 {
    360 	struct smb_rq *rqp;
    361 	mblk_t *m;
    362 	uchar_t *hp;
    363 	ushort_t mid;
    364 	int error = 0;
    365 	int etime_count = 0; /* for "server not responding", etc. */
    366 
    367 	for (;;) {
    368 		/*
    369 		 * Check whether someone "killed" this VC,
    370 		 * or is asking the IOD to terminate.
    371 		 */
    372 
    373 		if (vcp->vc_state != SMBIOD_ST_VCACTIVE) {
    374 			SMBIODEBUG("bad vc_state=%d\n", vcp->vc_state);
    375 			error = 0;
    376 			break;
    377 		}
    378 
    379 		if (vcp->iod_flags & SMBIOD_SHUTDOWN) {
    380 			SMBIODEBUG("SHUTDOWN set\n");
    381 			/* This IOD thread will terminate. */
    382 			SMB_VC_LOCK(vcp);
    383 			smb_iod_newstate(vcp, SMBIOD_ST_DEAD);
    384 			cv_broadcast(&vcp->vc_statechg);
    385 			SMB_VC_UNLOCK(vcp);
    386 			error = EINTR;
    387 			break;
    388 		}
    389 
    390 		m = NULL;
    391 		error = smb_iod_recv1(vcp, &m);
    392 
    393 		if (error == ETIME &&
    394 		    vcp->iod_rqlist.tqh_first != NULL) {
    395 			/*
    396 			 * Nothing received for 15 seconds and
    397 			 * we have requests in the queue.
    398 			 */
    399 			etime_count++;
    400 
    401 			/*
    402 			 * Once, at 15 sec. notify callbacks
    403 			 * and print the warning message.
    404 			 */
    405 			if (etime_count == 1) {
    406 				/* Was: smb_iod_notify_down(vcp); */
    407 				if (fscb && fscb->fscb_down)
    408 					smb_vc_walkshares(vcp,
    409 					    fscb->fscb_down);
    410 				zprintf(vcp->vc_zoneid,
    411 				    "SMB server %s not responding\n",
    412 				    vcp->vc_srvname);
    413 			}
    414 
    415 			/*
    416 			 * At 30 sec. try sending an echo, and then
    417 			 * once a minute thereafter.
    418 			 */
    419 			if ((etime_count & 3) == 2) {
    420 				(void) smb_iod_send_echo(vcp);
    421 			}
    422 
    423 			continue;
    424 		} /* ETIME && requests in queue */
    425 
    426 		if (error == ETIME) {
    427 			/*
    428 			 * If the IOD thread holds the last reference
    429 			 * to this VC, let the IOD thread terminate.
    430 			 */
    431 			if (vcp->vc_co.co_usecount > 1)
    432 				continue;
    433 			SMB_VC_LOCK(vcp);
    434 			if (vcp->vc_co.co_usecount == 1) {
    435 				smb_iod_newstate(vcp, SMBIOD_ST_DEAD);
    436 				SMB_VC_UNLOCK(vcp);
    437 				error = 0;
    438 				break;
    439 			}
    440 			SMB_VC_UNLOCK(vcp);
    441 			continue;
    442 		} /* error == ETIME */
    443 
    444 		if (error) {
    445 			/*
    446 			 * The recv. above returned some error
    447 			 * we can't continue from i.e. ENOTCONN.
    448 			 * It's dangerous to continue here.
    449 			 * (possible infinite loop!)
    450 			 *
    451 			 * If we have requests enqueued, next
    452 			 * state is reconnecting, else idle.
    453 			 */
    454 			int state;
    455 			SMB_VC_LOCK(vcp);
    456 			state = (vcp->iod_rqlist.tqh_first != NULL) ?
    457 			    SMBIOD_ST_RECONNECT : SMBIOD_ST_IDLE;
    458 			smb_iod_newstate(vcp, state);
    459 			cv_broadcast(&vcp->vc_statechg);
    460 			SMB_VC_UNLOCK(vcp);
    461 			error = 0;
    462 			break;
    463 		}
    464 
    465 		/*
    466 		 * Received something.  Yea!
    467 		 */
    468 		if (etime_count) {
    469 			etime_count = 0;
    470 
    471 			zprintf(vcp->vc_zoneid, "SMB server %s OK\n",
    472 			    vcp->vc_srvname);
    473 
    474 			/* Was: smb_iod_notify_up(vcp); */
    475 			if (fscb && fscb->fscb_up)
    476 				smb_vc_walkshares(vcp, fscb->fscb_up);
    477 		}
    478 
    479 		/*
    480 		 * Have an SMB packet.  The SMB header was
    481 		 * checked in smb_iod_recv1().
    482 		 * Find the request...
    483 		 */
    484 		hp = mtod(m, uchar_t *);
    485 		/*LINTED*/
    486 		mid = letohs(SMB_HDRMID(hp));
    487 		SMBIODEBUG("mid %04x\n", (uint_t)mid);
    488 
    489 		rw_enter(&vcp->iod_rqlock, RW_READER);
    490 		TAILQ_FOREACH(rqp, &vcp->iod_rqlist, sr_link) {
    491 
    492 			if (rqp->sr_mid != mid)
    493 				continue;
    494 
    495 			DTRACE_PROBE2(smb_iod_recvrq,
    496 			    (smb_rq_t *), rqp, (mblk_t *), m);
    497 			m_dumpm(m);
    498 
    499 			SMBRQ_LOCK(rqp);
    500 			if (rqp->sr_rp.md_top == NULL) {
    501 				md_initm(&rqp->sr_rp, m);
    502 			} else {
    503 				if (rqp->sr_flags & SMBR_MULTIPACKET) {
    504 					md_append_record(&rqp->sr_rp, m);
    505 				} else {
    506 					SMBRQ_UNLOCK(rqp);
    507 					SMBSDEBUG("duplicate response %d "
    508 					    "(ignored)\n", mid);
    509 					break;
    510 				}
    511 			}
    512 			smb_iod_rqprocessed_LH(rqp, 0, 0);
    513 			SMBRQ_UNLOCK(rqp);
    514 			break;
    515 		}
    516 
    517 		if (rqp == NULL) {
    518 			int cmd = SMB_HDRCMD(hp);
    519 
    520 			if (cmd != SMB_COM_ECHO)
    521 				SMBSDEBUG("drop resp: mid %d, cmd %d\n",
    522 				    (uint_t)mid, cmd);
    523 /*			smb_printrqlist(vcp); */
    524 			m_freem(m);
    525 		}
    526 		rw_exit(&vcp->iod_rqlock);
    527 
    528 	}
    529 
    530 	return (error);
    531 }
    532 
    533 /*
    534  * The IOD receiver thread has requests pending and
    535  * has not received anything in a while.  Try to
    536  * send an SMB echo request.  It's tricky to do a
    537  * send from the IOD thread because we can't block.
    538  *
    539  * Using tmo=SMBNOREPLYWAIT in the request
    540  * so smb_rq_reply will skip smb_iod_waitrq.
    541  * The smb_smb_echo call uses SMBR_INTERNAL
    542  * to avoid calling smb_iod_sendall().
    543  */
    544 int
    545 smb_iod_send_echo(smb_vc_t *vcp)
    546 {
    547 	smb_cred_t scred;
    548 	int err;
    549 
    550 	smb_credinit(&scred, NULL);
    551 	err = smb_smb_echo(vcp, &scred, SMBNOREPLYWAIT);
    552 	smb_credrele(&scred);
    553 	return (err);
    554 }
    555 
    556 /*
    557  * The IOD thread is now just a "reader",
    558  * so no more smb_iod_request().  Yea!
    559  */
    560 
    561 /*
    562  * Place request in the queue, and send it now if possible.
    563  * Called with no locks held.
    564  */
    565 int
    566 smb_iod_addrq(struct smb_rq *rqp)
    567 {
    568 	struct smb_vc *vcp = rqp->sr_vc;
    569 	int error, save_newrq;
    570 
    571 	ASSERT(rqp->sr_cred);
    572 
    573 	/*
    574 	 * State should be correct after the check in
    575 	 * smb_rq_enqueue(), but we dropped locks...
    576 	 */
    577 	if (vcp->vc_state != SMBIOD_ST_VCACTIVE) {
    578 		SMBIODEBUG("bad vc_state=%d\n", vcp->vc_state);
    579 		return (ENOTCONN);
    580 	}
    581 
    582 	/*
    583 	 * Requests from the IOD itself are marked _INTERNAL,
    584 	 * and get some special treatment to avoid blocking
    585 	 * the reader thread (so we don't deadlock).
    586 	 * The request is not yet on the queue, so we can
    587 	 * modify it's state here without locks.
    588 	 * Only thing using this now is ECHO.
    589 	 */
    590 	rqp->sr_owner = curthread;
    591 	if (rqp->sr_owner == vcp->iod_thr) {
    592 		rqp->sr_flags |= SMBR_INTERNAL;
    593 
    594 		/*
    595 		 * This is a request from the IOD thread.
    596 		 * Always send directly from this thread.
    597 		 * Note lock order: iod_rqlist, vc_sendlock
    598 		 */
    599 		rw_enter(&vcp->iod_rqlock, RW_WRITER);
    600 		TAILQ_INSERT_HEAD(&vcp->iod_rqlist, rqp, sr_link);
    601 		rw_downgrade(&vcp->iod_rqlock);
    602 
    603 		/*
    604 		 * Note: iod_sendrq expects vc_sendlock,
    605 		 * so take that here, but carefully:
    606 		 * Never block the IOD thread here.
    607 		 */
    608 		if (sema_tryp(&vcp->vc_sendlock) == 0) {
    609 			SMBIODEBUG("sendlock busy\n");
    610 			error = EAGAIN;
    611 		} else {
    612 			/* Have vc_sendlock */
    613 			error = smb_iod_sendrq(rqp);
    614 			sema_v(&vcp->vc_sendlock);
    615 		}
    616 
    617 		rw_exit(&vcp->iod_rqlock);
    618 
    619 		/*
    620 		 * In the non-error case, _removerq
    621 		 * is done by either smb_rq_reply
    622 		 * or smb_iod_waitrq.
    623 		 */
    624 		if (error)
    625 			smb_iod_removerq(rqp);
    626 
    627 		return (error);
    628 	}
    629 
    630 	rw_enter(&vcp->iod_rqlock, RW_WRITER);
    631 
    632 	TAILQ_INSERT_TAIL(&vcp->iod_rqlist, rqp, sr_link);
    633 	/* iod_rqlock/WRITER protects iod_newrq */
    634 	save_newrq = vcp->iod_newrq;
    635 	vcp->iod_newrq++;
    636 
    637 	rw_exit(&vcp->iod_rqlock);
    638 
    639 	/*
    640 	 * Now send any requests that need to be sent,
    641 	 * including the one we just put on the list.
    642 	 * Only the thread that found iod_newrq==0
    643 	 * needs to run the send loop.
    644 	 */
    645 	if (save_newrq == 0)
    646 		smb_iod_sendall(vcp);
    647 
    648 	return (0);
    649 }
    650 
    651 /*
    652  * Mark an SMBR_MULTIPACKET request as
    653  * needing another send.  Similar to the
    654  * "normal" part of smb_iod_addrq.
    655  */
    656 int
    657 smb_iod_multirq(struct smb_rq *rqp)
    658 {
    659 	struct smb_vc *vcp = rqp->sr_vc;
    660 	int save_newrq;
    661 
    662 	ASSERT(rqp->sr_flags & SMBR_MULTIPACKET);
    663 
    664 	if (rqp->sr_flags & SMBR_INTERNAL)
    665 		return (EINVAL);
    666 
    667 	if (vcp->vc_state != SMBIOD_ST_VCACTIVE) {
    668 		SMBIODEBUG("bad vc_state=%d\n", vcp->vc_state);
    669 		return (ENOTCONN);
    670 	}
    671 
    672 	rw_enter(&vcp->iod_rqlock, RW_WRITER);
    673 
    674 	/* Already on iod_rqlist, just reset state. */
    675 	rqp->sr_state = SMBRQ_NOTSENT;
    676 
    677 	/* iod_rqlock/WRITER protects iod_newrq */
    678 	save_newrq = vcp->iod_newrq;
    679 	vcp->iod_newrq++;
    680 
    681 	rw_exit(&vcp->iod_rqlock);
    682 
    683 	/*
    684 	 * Now send any requests that need to be sent,
    685 	 * including the one we just marked NOTSENT.
    686 	 * Only the thread that found iod_newrq==0
    687 	 * needs to run the send loop.
    688 	 */
    689 	if (save_newrq == 0)
    690 		smb_iod_sendall(vcp);
    691 
    692 	return (0);
    693 }
    694 
    695 
    696 void
    697 smb_iod_removerq(struct smb_rq *rqp)
    698 {
    699 	struct smb_vc *vcp = rqp->sr_vc;
    700 
    701 	rw_enter(&vcp->iod_rqlock, RW_WRITER);
    702 #ifdef QUEUEDEBUG
    703 	/*
    704 	 * Make sure we have not already removed it.
    705 	 * See sys/queue.h QUEUEDEBUG_TAILQ_POSTREMOVE
    706 	 * XXX: Don't like the constant 1 here...
    707 	 */
    708 	ASSERT(rqp->sr_link.tqe_next != (void *)1L);
    709 #endif
    710 	TAILQ_REMOVE(&vcp->iod_rqlist, rqp, sr_link);
    711 	rw_exit(&vcp->iod_rqlock);
    712 }
    713 
    714 
    715 
    716 /*
    717  * Wait for a request to complete.
    718  *
    719  * For normal requests, we need to deal with
    720  * ioc_muxcnt dropping below vc_maxmux by
    721  * making arrangements to send more...
    722  */
    723 int
    724 smb_iod_waitrq(struct smb_rq *rqp)
    725 {
    726 	struct smb_vc *vcp = rqp->sr_vc;
    727 	clock_t tr, tmo1, tmo2;
    728 	int error, rc;
    729 
    730 	if (rqp->sr_flags & SMBR_INTERNAL) {
    731 		ASSERT((rqp->sr_flags & SMBR_MULTIPACKET) == 0);
    732 		smb_iod_removerq(rqp);
    733 		return (EAGAIN);
    734 	}
    735 
    736 	/*
    737 	 * Make sure this is NOT the IOD thread,
    738 	 * or the wait below will stop the reader.
    739 	 */
    740 	ASSERT(curthread != vcp->iod_thr);
    741 
    742 	SMBRQ_LOCK(rqp);
    743 
    744 	/*
    745 	 * First, wait for the request to be sent.  Normally the send
    746 	 * has already happened by the time we get here.  However, if
    747 	 * we have more than maxmux entries in the request list, our
    748 	 * request may not be sent until other requests complete.
    749 	 * The wait in this case is due to local I/O demands, so
    750 	 * we don't want the server response timeout to apply.
    751 	 *
    752 	 * If a request is allowed to interrupt this wait, then the
    753 	 * request is cancelled and never sent OTW.  Some kinds of
    754 	 * requests should never be cancelled (i.e. close) and those
    755 	 * are marked SMBR_NOINTR_SEND so they either go eventually,
    756 	 * or a connection close will terminate them with ENOTCONN.
    757 	 */
    758 	while (rqp->sr_state == SMBRQ_NOTSENT) {
    759 		rqp->sr_flags |= SMBR_SENDWAIT;
    760 		if (rqp->sr_flags & SMBR_NOINTR_SEND) {
    761 			cv_wait(&rqp->sr_cond, &rqp->sr_lock);
    762 			rc = 1;
    763 		} else
    764 			rc = cv_wait_sig(&rqp->sr_cond, &rqp->sr_lock);
    765 		rqp->sr_flags &= ~SMBR_SENDWAIT;
    766 		if (rc == 0) {
    767 			SMBIODEBUG("EINTR in sendwait, rqp=%p\n", rqp);
    768 			error = EINTR;
    769 			goto out;
    770 		}
    771 	}
    772 
    773 	/*
    774 	 * The request has been sent.  Now wait for the response,
    775 	 * with the timeout specified for this request.
    776 	 * Compute all the deadlines now, so we effectively
    777 	 * start the timer(s) after the request is sent.
    778 	 */
    779 	if (smb_timo_notice && (smb_timo_notice < rqp->sr_timo))
    780 		tmo1 = SEC_TO_TICK(smb_timo_notice);
    781 	else
    782 		tmo1 = 0;
    783 	tmo2 = ddi_get_lbolt() + SEC_TO_TICK(rqp->sr_timo);
    784 
    785 	/*
    786 	 * As above, we don't want to allow interrupt for some
    787 	 * requests like open, because we could miss a succesful
    788 	 * response and therefore "leak" a FID.  Such requests
    789 	 * are marked SMBR_NOINTR_RECV to prevent that.
    790 	 *
    791 	 * If "slow server" warnings are enabled, wait first
    792 	 * for the "notice" timeout, and warn if expired.
    793 	 */
    794 	if (tmo1 && rqp->sr_rpgen == rqp->sr_rplast) {
    795 		if (rqp->sr_flags & SMBR_NOINTR_RECV)
    796 			tr = cv_reltimedwait(&rqp->sr_cond,
    797 			    &rqp->sr_lock, tmo1, TR_CLOCK_TICK);
    798 		else
    799 			tr = cv_reltimedwait_sig(&rqp->sr_cond,
    800 			    &rqp->sr_lock, tmo1, TR_CLOCK_TICK);
    801 		if (tr == 0) {
    802 			error = EINTR;
    803 			goto out;
    804 		}
    805 		if (tr < 0) {
    806 #ifdef DTRACE_PROBE
    807 			DTRACE_PROBE1(smb_iod_waitrq1,
    808 			    (smb_rq_t *), rqp);
    809 #endif
    810 #ifdef NOT_YET
    811 			/* Want this to go ONLY to the user. */
    812 			uprintf("SMB server %s has not responded"
    813 			    " to request %d after %d seconds..."
    814 			    " (still waiting).\n", vcp->vc_srvname,
    815 			    rqp->sr_mid, smb_timo_notice);
    816 #endif
    817 		}
    818 	}
    819 
    820 	/*
    821 	 * Keep waiting until tmo2 is expired.
    822 	 */
    823 	while (rqp->sr_rpgen == rqp->sr_rplast) {
    824 		if (rqp->sr_flags & SMBR_NOINTR_RECV)
    825 			tr = cv_timedwait(&rqp->sr_cond,
    826 			    &rqp->sr_lock, tmo2);
    827 		else
    828 			tr = cv_timedwait_sig(&rqp->sr_cond,
    829 			    &rqp->sr_lock, tmo2);
    830 		if (tr == 0) {
    831 			error = EINTR;
    832 			goto out;
    833 		}
    834 		if (tr < 0) {
    835 #ifdef DTRACE_PROBE
    836 			DTRACE_PROBE1(smb_iod_waitrq2,
    837 			    (smb_rq_t *), rqp);
    838 #endif
    839 #ifdef NOT_YET
    840 			/* Want this to go ONLY to the user. */
    841 			uprintf("SMB server %s has not responded"
    842 			    " to request %d after %d seconds..."
    843 			    " (giving up).\n", vcp->vc_srvname,
    844 			    rqp->sr_mid, rqp->sr_timo);
    845 #endif
    846 			error = ETIME;
    847 			goto out;
    848 		}
    849 		/* got wakeup */
    850 	}
    851 	error = rqp->sr_lerror;
    852 	rqp->sr_rplast++;
    853 
    854 out:
    855 	SMBRQ_UNLOCK(rqp);
    856 
    857 	/*
    858 	 * MULTIPACKET request must stay in the list.
    859 	 * They may need additional responses.
    860 	 */
    861 	if ((rqp->sr_flags & SMBR_MULTIPACKET) == 0)
    862 		smb_iod_removerq(rqp);
    863 
    864 	/*
    865 	 * Some request has been completed.
    866 	 * If we reached the mux limit,
    867 	 * re-run the send loop...
    868 	 */
    869 	if (vcp->iod_muxfull)
    870 		smb_iod_sendall(vcp);
    871 
    872 	return (error);
    873 }
    874 
    875 /*
    876  * Shutdown all outstanding I/O requests on the specified share with
    877  * ENXIO; used when unmounting a share.  (There shouldn't be any for a
    878  * non-forced unmount; if this is a forced unmount, we have to shutdown
    879  * the requests as part of the unmount process.)
    880  */
    881 void
    882 smb_iod_shutdown_share(struct smb_share *ssp)
    883 {
    884 	struct smb_vc *vcp = SSTOVC(ssp);
    885 	struct smb_rq *rqp;
    886 
    887 	/*
    888 	 * Loop through the list of requests and shutdown the ones
    889 	 * that are for the specified share.
    890 	 */
    891 	rw_enter(&vcp->iod_rqlock, RW_READER);
    892 	TAILQ_FOREACH(rqp, &vcp->iod_rqlist, sr_link) {
    893 		if (rqp->sr_state != SMBRQ_NOTIFIED && rqp->sr_share == ssp)
    894 			smb_iod_rqprocessed(rqp, EIO, 0);
    895 	}
    896 	rw_exit(&vcp->iod_rqlock);
    897 }
    898 
    899 /*
    900  * Send all requests that need sending.
    901  * Called from _addrq, _multirq, _waitrq
    902  */
    903 void
    904 smb_iod_sendall(smb_vc_t *vcp)
    905 {
    906 	struct smb_rq *rqp;
    907 	int error, muxcnt;
    908 
    909 	/*
    910 	 * Clear "newrq" to make sure threads adding
    911 	 * new requests will run this function again.
    912 	 */
    913 	rw_enter(&vcp->iod_rqlock, RW_WRITER);
    914 	vcp->iod_newrq = 0;
    915 
    916 	/*
    917 	 * We only read iod_rqlist, so downgrade rwlock.
    918 	 * This allows the IOD to handle responses while
    919 	 * some requesting thread may be blocked in send.
    920 	 */
    921 	rw_downgrade(&vcp->iod_rqlock);
    922 
    923 	/*
    924 	 * Serialize to prevent multiple senders.
    925 	 * Note lock order: iod_rqlock, vc_sendlock
    926 	 */
    927 	sema_p(&vcp->vc_sendlock);
    928 
    929 	/*
    930 	 * Walk the list of requests and send when possible.
    931 	 * We avoid having more than vc_maxmux requests
    932 	 * outstanding to the server by traversing only
    933 	 * vc_maxmux entries into this list.  Simple!
    934 	 */
    935 	ASSERT(vcp->vc_maxmux > 0);
    936 	error = muxcnt = 0;
    937 	TAILQ_FOREACH(rqp, &vcp->iod_rqlist, sr_link) {
    938 
    939 		if (vcp->vc_state != SMBIOD_ST_VCACTIVE) {
    940 			error = ENOTCONN; /* stop everything! */
    941 			break;
    942 		}
    943 
    944 		if (rqp->sr_state == SMBRQ_NOTSENT) {
    945 			error = smb_iod_sendrq(rqp);
    946 			if (error)
    947 				break;
    948 		}
    949 
    950 		if (++muxcnt == vcp->vc_maxmux) {
    951 			SMBIODEBUG("muxcnt == vc_maxmux\n");
    952 			break;
    953 		}
    954 
    955 	}
    956 
    957 	/*
    958 	 * If we have vc_maxmux requests outstanding,
    959 	 * arrange for _waitrq to call _sendall as
    960 	 * requests are completed.
    961 	 */
    962 	vcp->iod_muxfull =
    963 	    (muxcnt < vcp->vc_maxmux) ? 0 : 1;
    964 
    965 	sema_v(&vcp->vc_sendlock);
    966 	rw_exit(&vcp->iod_rqlock);
    967 }
    968 
    969 int
    970 smb_iod_vc_work(struct smb_vc *vcp, cred_t *cr)
    971 {
    972 	struct file *fp = NULL;
    973 	int err = 0;
    974 
    975 	/*
    976 	 * This is called by the one-and-only
    977 	 * IOD thread for this VC.
    978 	 */
    979 	ASSERT(vcp->iod_thr == curthread);
    980 
    981 	/*
    982 	 * Get the network transport file pointer,
    983 	 * and "loan" it to our transport module.
    984 	 */
    985 	if ((fp = getf(vcp->vc_tran_fd)) == NULL) {
    986 		err = EBADF;
    987 		goto out;
    988 	}
    989 	if ((err = SMB_TRAN_LOAN_FP(vcp, fp, cr)) != 0)
    990 		goto out;
    991 
    992 	/*
    993 	 * In case of reconnect, tell any enqueued requests
    994 	 * then can GO!
    995 	 */
    996 	SMB_VC_LOCK(vcp);
    997 	vcp->vc_genid++;	/* possibly new connection */
    998 	smb_iod_newstate(vcp, SMBIOD_ST_VCACTIVE);
    999 	cv_broadcast(&vcp->vc_statechg);
   1000 	SMB_VC_UNLOCK(vcp);
   1001 
   1002 	/*
   1003 	 * The above cv_broadcast should be sufficient to
   1004 	 * get requests going again.
   1005 	 *
   1006 	 * If we have a callback function, run it.
   1007 	 * Was: smb_iod_notify_connected()
   1008 	 */
   1009 	if (fscb && fscb->fscb_connect)
   1010 		smb_vc_walkshares(vcp, fscb->fscb_connect);
   1011 
   1012 	/*
   1013 	 * Run the "reader" loop.
   1014 	 */
   1015 	err = smb_iod_recvall(vcp);
   1016 
   1017 	/*
   1018 	 * The reader loop returned, so we must have a
   1019 	 * new state.  (disconnected or reconnecting)
   1020 	 *
   1021 	 * Notify shares of the disconnect.
   1022 	 * Was: smb_iod_notify_disconnect()
   1023 	 */
   1024 	smb_vc_walkshares(vcp, smb_iod_share_disconnected);
   1025 
   1026 	/*
   1027 	 * The reader loop function returns only when
   1028 	 * there's been an error on the connection, or
   1029 	 * this VC has no more references.  It also
   1030 	 * updates the state before it returns.
   1031 	 *
   1032 	 * Tell any requests to give up or restart.
   1033 	 */
   1034 	smb_iod_invrq(vcp);
   1035 
   1036 out:
   1037 	/* Recall the file descriptor loan. */
   1038 	(void) SMB_TRAN_LOAN_FP(vcp, NULL, cr);
   1039 	if (fp != NULL) {
   1040 		releasef(vcp->vc_tran_fd);
   1041 	}
   1042 
   1043 	return (err);
   1044 }
   1045 
   1046 /*
   1047  * Wait around for someone to ask to use this VC.
   1048  * If the VC has only the IOD reference, then
   1049  * wait only a minute or so, then drop it.
   1050  */
   1051 int
   1052 smb_iod_vc_idle(struct smb_vc *vcp)
   1053 {
   1054 	clock_t tr, delta = SEC_TO_TICK(15);
   1055 	int err = 0;
   1056 
   1057 	/*
   1058 	 * This is called by the one-and-only
   1059 	 * IOD thread for this VC.
   1060 	 */
   1061 	ASSERT(vcp->iod_thr == curthread);
   1062 
   1063 	SMB_VC_LOCK(vcp);
   1064 	while (vcp->vc_state == SMBIOD_ST_IDLE) {
   1065 		tr = cv_reltimedwait_sig(&vcp->iod_idle, &vcp->vc_lock,
   1066 		    delta, TR_CLOCK_TICK);
   1067 		if (tr == 0) {
   1068 			err = EINTR;
   1069 			break;
   1070 		}
   1071 		if (tr < 0) {
   1072 			/* timeout */
   1073 			if (vcp->vc_co.co_usecount == 1) {
   1074 				/* Let this IOD terminate. */
   1075 				smb_iod_newstate(vcp, SMBIOD_ST_DEAD);
   1076 				/* nobody to cv_broadcast */
   1077 				break;
   1078 			}
   1079 		}
   1080 	}
   1081 	SMB_VC_UNLOCK(vcp);
   1082 
   1083 	return (err);
   1084 }
   1085 
   1086 /*
   1087  * After a failed reconnect attempt, smbiod will
   1088  * call this to make current requests error out.
   1089  */
   1090 int
   1091 smb_iod_vc_rcfail(struct smb_vc *vcp)
   1092 {
   1093 	clock_t tr;
   1094 	int err = 0;
   1095 
   1096 	/*
   1097 	 * This is called by the one-and-only
   1098 	 * IOD thread for this VC.
   1099 	 */
   1100 	ASSERT(vcp->iod_thr == curthread);
   1101 
   1102 	if (vcp->vc_state != SMBIOD_ST_RECONNECT)
   1103 		return (EINVAL);
   1104 
   1105 	SMB_VC_LOCK(vcp);
   1106 
   1107 	smb_iod_newstate(vcp, SMBIOD_ST_RCFAILED);
   1108 	cv_broadcast(&vcp->vc_statechg);
   1109 
   1110 	/*
   1111 	 * Short wait here for two reasons:
   1112 	 * (1) Give requests a chance to error out.
   1113 	 * (2) Prevent immediate retry.
   1114 	 */
   1115 	tr = cv_reltimedwait_sig(&vcp->iod_idle, &vcp->vc_lock,
   1116 	    SEC_TO_TICK(5), TR_CLOCK_TICK);
   1117 	if (tr == 0)
   1118 		err = EINTR;
   1119 
   1120 	smb_iod_newstate(vcp, SMBIOD_ST_IDLE);
   1121 	cv_broadcast(&vcp->vc_statechg);
   1122 
   1123 	SMB_VC_UNLOCK(vcp);
   1124 
   1125 	return (err);
   1126 }
   1127 
   1128 /*
   1129  * Ask the IOD to reconnect (if not already underway)
   1130  * then wait for the reconnect to finish.
   1131  */
   1132 int
   1133 smb_iod_reconnect(struct smb_vc *vcp)
   1134 {
   1135 	int err = 0, rv;
   1136 
   1137 	SMB_VC_LOCK(vcp);
   1138 again:
   1139 	switch (vcp->vc_state) {
   1140 
   1141 	case SMBIOD_ST_IDLE:
   1142 		smb_iod_newstate(vcp, SMBIOD_ST_RECONNECT);
   1143 		cv_signal(&vcp->iod_idle);
   1144 		/* FALLTHROUGH */
   1145 
   1146 	case SMBIOD_ST_RECONNECT:
   1147 		rv = cv_wait_sig(&vcp->vc_statechg, &vcp->vc_lock);
   1148 		if (rv == 0) {
   1149 			err = EINTR;
   1150 			break;
   1151 		}
   1152 		goto again;
   1153 
   1154 	case SMBIOD_ST_VCACTIVE:
   1155 		err = 0; /* success! */
   1156 		break;
   1157 
   1158 	case SMBIOD_ST_RCFAILED:
   1159 	case SMBIOD_ST_DEAD:
   1160 	default:
   1161 		err = ENOTCONN;
   1162 		break;
   1163 	}
   1164 
   1165 	SMB_VC_UNLOCK(vcp);
   1166 	return (err);
   1167 }
   1168