xref: /csrg-svn/sys/kern/vfs_cluster.c (revision 2423)
1 /*	vfs_cluster.c	4.11	02/15/81	*/
2 
3 #include "../h/param.h"
4 #include "../h/systm.h"
5 #include "../h/dir.h"
6 #include "../h/user.h"
7 #include "../h/buf.h"
8 #include "../h/conf.h"
9 #include "../h/proc.h"
10 #include "../h/seg.h"
11 #include "../h/pte.h"
12 #include "../h/vm.h"
13 #include "../h/trace.h"
14 
15 /*
16  * The following several routines allocate and free
17  * buffers with various side effects.  In general the
18  * arguments to an allocate routine are a device and
19  * a block number, and the value is a pointer to
20  * to the buffer header; the buffer is marked "busy"
21  * so that no one else can touch it.  If the block was
22  * already in core, no I/O need be done; if it is
23  * already busy, the process waits until it becomes free.
24  * The following routines allocate a buffer:
25  *	getblk
26  *	bread
27  *	breada
28  *	baddr	(if it is incore)
29  * Eventually the buffer must be released, possibly with the
30  * side effect of writing it out, by using one of
31  *	bwrite
32  *	bdwrite
33  *	bawrite
34  *	brelse
35  */
36 
37 #define	BUFHSZ	63
38 struct	bufhd bufhash[BUFHSZ];
39 #define	BUFHASH(dev, dblkno)	\
40 		((struct buf *)&bufhash[((int)(dev)+(int)(dblkno)) % BUFHSZ])
41 
42 /*
43  * Initialize hash links for buffers.
44  */
45 bhinit()
46 {
47 	register int i;
48 	register struct bufhd *bp;
49 
50 	for (bp = bufhash, i = 0; i < BUFHSZ; i++, bp++)
51 		bp->b_forw = bp->b_back = (struct buf *)bp;
52 }
53 
54 /* #define	DISKMON	1 */
55 
56 #ifdef	DISKMON
57 struct {
58 	int	nbuf;
59 	long	nread;
60 	long	nreada;
61 	long	ncache;
62 	long	nwrite;
63 	long	bufcount[NBUF];
64 } io_info;
65 #endif
66 
67 /*
68  * Swap IO headers -
69  * They contain the necessary information for the swap I/O.
70  * At any given time, a swap header can be in three
71  * different lists. When free it is in the free list,
72  * when allocated and the I/O queued, it is on the swap
73  * device list, and finally, if the operation was a dirty
74  * page push, when the I/O completes, it is inserted
75  * in a list of cleaned pages to be processed by the pageout daemon.
76  */
77 struct	buf swbuf[NSWBUF];
78 short	swsize[NSWBUF];		/* CAN WE JUST USE B_BCOUNT? */
79 int	swpf[NSWBUF];
80 
81 
82 #ifdef	FASTVAX
83 #define	notavail(bp) \
84 { \
85 	int s = spl6(); \
86 	(bp)->av_back->av_forw = (bp)->av_forw; \
87 	(bp)->av_forw->av_back = (bp)->av_back; \
88 	(bp)->b_flags |= B_BUSY; \
89 	splx(s); \
90 }
91 #endif
92 
93 /*
94  * Read in (if necessary) the block and return a buffer pointer.
95  */
96 struct buf *
97 bread(dev, blkno)
98 dev_t dev;
99 daddr_t blkno;
100 {
101 	register struct buf *bp;
102 
103 	bp = getblk(dev, blkno);
104 	if (bp->b_flags&B_DONE) {
105 #ifdef	EPAWNJ
106 		trace(TR_BREAD|TR_HIT, dev, blkno);
107 #endif
108 #ifdef	DISKMON
109 		io_info.ncache++;
110 #endif
111 		return(bp);
112 	}
113 	bp->b_flags |= B_READ;
114 	bp->b_bcount = BSIZE;
115 	(*bdevsw[major(dev)].d_strategy)(bp);
116 #ifdef	EPAWNJ
117 	trace(TR_BREAD|TR_MISS, dev, blkno);
118 #endif
119 #ifdef	DISKMON
120 	io_info.nread++;
121 #endif
122 	u.u_vm.vm_inblk++;		/* pay for read */
123 	iowait(bp);
124 	return(bp);
125 }
126 
127 /*
128  * Read in the block, like bread, but also start I/O on the
129  * read-ahead block (which is not allocated to the caller)
130  */
131 struct buf *
132 breada(dev, blkno, rablkno)
133 dev_t dev;
134 daddr_t blkno, rablkno;
135 {
136 	register struct buf *bp, *rabp;
137 
138 	bp = NULL;
139 	if (!incore(dev, blkno)) {
140 		bp = getblk(dev, blkno);
141 		if ((bp->b_flags&B_DONE) == 0) {
142 			bp->b_flags |= B_READ;
143 			bp->b_bcount = BSIZE;
144 			(*bdevsw[major(dev)].d_strategy)(bp);
145 #ifdef	EPAWNJ
146 			trace(TR_BREAD|TR_MISS, dev, blkno);
147 #endif
148 #ifdef	DISKMON
149 			io_info.nread++;
150 #endif
151 			u.u_vm.vm_inblk++;		/* pay for read */
152 		}
153 #ifdef	EPAWNJ
154 		else
155 			trace(TR_BREAD|TR_HIT, dev, blkno);
156 #endif
157 	}
158 	if (rablkno && !incore(dev, rablkno)) {
159 		rabp = getblk(dev, rablkno);
160 		if (rabp->b_flags & B_DONE) {
161 			brelse(rabp);
162 #ifdef	EPAWNJ
163 			trace(TR_BREAD|TR_HIT|TR_RA, dev, blkno);
164 #endif
165 		} else {
166 			rabp->b_flags |= B_READ|B_ASYNC;
167 			rabp->b_bcount = BSIZE;
168 			(*bdevsw[major(dev)].d_strategy)(rabp);
169 #ifdef	EPAWNJ
170 			trace(TR_BREAD|TR_MISS|TR_RA, dev, rablock);
171 #endif
172 #ifdef	DISKMON
173 			io_info.nreada++;
174 #endif
175 			u.u_vm.vm_inblk++;		/* pay in advance */
176 		}
177 	}
178 	if(bp == NULL)
179 		return(bread(dev, blkno));
180 	iowait(bp);
181 	return(bp);
182 }
183 
184 /*
185  * Write the buffer, waiting for completion.
186  * Then release the buffer.
187  */
188 bwrite(bp)
189 register struct buf *bp;
190 {
191 	register flag;
192 
193 	flag = bp->b_flags;
194 	bp->b_flags &= ~(B_READ | B_DONE | B_ERROR | B_DELWRI | B_AGE);
195 	bp->b_bcount = BSIZE;
196 #ifdef	DISKMON
197 	io_info.nwrite++;
198 #endif
199 	if ((flag&B_DELWRI) == 0)
200 		u.u_vm.vm_oublk++;		/* noone paid yet */
201 #ifdef	EPAWNJ
202 	trace(TR_BWRITE, bp->b_dev, dbtofsb(bp->b_blkno));
203 #endif
204 	(*bdevsw[major(bp->b_dev)].d_strategy)(bp);
205 	if ((flag&B_ASYNC) == 0) {
206 		iowait(bp);
207 		brelse(bp);
208 	} else if (flag & B_DELWRI)
209 		bp->b_flags |= B_AGE;
210 	else
211 		geterror(bp);
212 }
213 
214 /*
215  * Release the buffer, marking it so that if it is grabbed
216  * for another purpose it will be written out before being
217  * given up (e.g. when writing a partial block where it is
218  * assumed that another write for the same block will soon follow).
219  * This can't be done for magtape, since writes must be done
220  * in the same order as requested.
221  */
222 bdwrite(bp)
223 register struct buf *bp;
224 {
225 	register int flags;
226 
227 	if ((bp->b_flags&B_DELWRI) == 0)
228 		u.u_vm.vm_oublk++;		/* noone paid yet */
229 	flags = bdevsw[major(bp->b_dev)].d_flags;
230 	if(flags & B_TAPE)
231 		bawrite(bp);
232 	else {
233 		bp->b_flags |= B_DELWRI | B_DONE;
234 		brelse(bp);
235 	}
236 }
237 
238 /*
239  * Release the buffer, start I/O on it, but don't wait for completion.
240  */
241 bawrite(bp)
242 register struct buf *bp;
243 {
244 
245 	bp->b_flags |= B_ASYNC;
246 	bwrite(bp);
247 }
248 
249 /*
250  * release the buffer, with no I/O implied.
251  */
252 brelse(bp)
253 register struct buf *bp;
254 {
255 	register struct buf *flist;
256 	register s;
257 
258 	if (bp->b_flags&B_WANTED)
259 		wakeup((caddr_t)bp);
260 	if (bfreelist[0].b_flags&B_WANTED) {
261 		bfreelist[0].b_flags &= ~B_WANTED;
262 		wakeup((caddr_t)bfreelist);
263 	}
264 	if ((bp->b_flags&B_ERROR) && bp->b_dev != NODEV)
265 		bp->b_dev = NODEV;  /* no assoc. on error */
266 	s = spl6();
267 	if (bp->b_flags & (B_ERROR|B_INVAL)) {
268 		/* block has no info ... put at front of most free list */
269 		flist = &bfreelist[BQUEUES-1];
270 		flist->av_forw->av_back = bp;
271 		bp->av_forw = flist->av_forw;
272 		flist->av_forw = bp;
273 		bp->av_back = flist;
274 	} else {
275 		if (bp->b_flags & B_LOCKED)
276 			flist = &bfreelist[BQ_LOCKED];
277 		else if (bp->b_flags & B_AGE)
278 			flist = &bfreelist[BQ_AGE];
279 		else
280 			flist = &bfreelist[BQ_LRU];
281 		flist->av_back->av_forw = bp;
282 		bp->av_back = flist->av_back;
283 		flist->av_back = bp;
284 		bp->av_forw = flist;
285 	}
286 	bp->b_flags &= ~(B_WANTED|B_BUSY|B_ASYNC|B_AGE);
287 	splx(s);
288 }
289 
290 /*
291  * See if the block is associated with some buffer
292  * (mainly to avoid getting hung up on a wait in breada)
293  */
294 incore(dev, blkno)
295 dev_t dev;
296 daddr_t blkno;
297 {
298 	register struct buf *bp;
299 	register struct buf *dp;
300 	register int dblkno = fsbtodb(blkno);
301 
302 	dp = BUFHASH(dev, dblkno);
303 	for (bp = dp->b_forw; bp != dp; bp = bp->b_forw)
304 		if (bp->b_blkno == dblkno && bp->b_dev == dev &&
305 		    !(bp->b_flags & B_INVAL))
306 			return (1);
307 	return (0);
308 }
309 
310 struct buf *
311 baddr(dev, blkno)
312 dev_t dev;
313 daddr_t blkno;
314 {
315 
316 	if (incore(dev, blkno))
317 		return (bread(dev, blkno));
318 	return (0);
319 }
320 
321 /*
322  * Assign a buffer for the given block.  If the appropriate
323  * block is already associated, return it; otherwise search
324  * for the oldest non-busy buffer and reassign it.
325  */
326 struct buf *
327 getblk(dev, blkno)
328 dev_t dev;
329 daddr_t blkno;
330 {
331 	register struct buf *bp, *dp, *ep;
332 	register int dblkno = fsbtodb(blkno);
333 #ifdef	DISKMON
334 	register int i;
335 #endif
336 
337 	if ((unsigned)blkno >= 1 << (sizeof(int)*NBBY-PGSHIFT))
338 		blkno = 1 << ((sizeof(int)*NBBY-PGSHIFT) + 1);
339 	dblkno = fsbtodb(blkno);
340 	dp = BUFHASH(dev, dblkno);
341     loop:
342 	(void) spl0();
343 	for (bp = dp->b_forw; bp != dp; bp = bp->b_forw) {
344 		if (bp->b_blkno != dblkno || bp->b_dev != dev ||
345 		    bp->b_flags&B_INVAL)
346 			continue;
347 		(void) spl6();
348 		if (bp->b_flags&B_BUSY) {
349 			bp->b_flags |= B_WANTED;
350 			sleep((caddr_t)bp, PRIBIO+1);
351 			goto loop;
352 		}
353 		(void) spl0();
354 #ifdef	DISKMON
355 		i = 0;
356 		dp = bp->av_forw;
357 		while ((dp->b_flags & B_HEAD) == 0) {
358 			i++;
359 			dp = dp->av_forw;
360 		}
361 		if (i<NBUF)
362 			io_info.bufcount[i]++;
363 #endif
364 		notavail(bp);
365 		bp->b_flags |= B_CACHE;
366 		return(bp);
367 	}
368 	if (major(dev) >= nblkdev)
369 		panic("blkdev");
370 	(void) spl6();
371 	for (ep = &bfreelist[BQUEUES-1]; ep > bfreelist; ep--)
372 		if (ep->av_forw != ep)
373 			break;
374 	if (ep == bfreelist) {		/* no free blocks at all */
375 		ep->b_flags |= B_WANTED;
376 		sleep((caddr_t)ep, PRIBIO+1);
377 		goto loop;
378 	}
379 	(void) spl0();
380 	bp = ep->av_forw;
381 	notavail(bp);
382 	if (bp->b_flags & B_DELWRI) {
383 		bp->b_flags |= B_ASYNC;
384 		bwrite(bp);
385 		goto loop;
386 	}
387 #ifdef EPAWNJ
388 	trace(TR_BRELSE, bp->b_dev, dbtofsb(bp->b_blkno));
389 #endif
390 	bp->b_flags = B_BUSY;
391 	bp->b_back->b_forw = bp->b_forw;
392 	bp->b_forw->b_back = bp->b_back;
393 	bp->b_forw = dp->b_forw;
394 	bp->b_back = dp;
395 	dp->b_forw->b_back = bp;
396 	dp->b_forw = bp;
397 	bp->b_dev = dev;
398 	bp->b_blkno = dblkno;
399 	return(bp);
400 }
401 
402 /*
403  * get an empty block,
404  * not assigned to any particular device
405  */
406 struct buf *
407 geteblk()
408 {
409 	register struct buf *bp, *dp;
410 
411 loop:
412 	(void) spl6();
413 	for (dp = &bfreelist[BQUEUES-1]; dp > bfreelist; dp--)
414 		if (dp->av_forw != dp)
415 			break;
416 	if (dp == bfreelist) {		/* no free blocks */
417 		dp->b_flags |= B_WANTED;
418 		sleep((caddr_t)dp, PRIBIO+1);
419 		goto loop;
420 	}
421 	(void) spl0();
422 	bp = dp->av_forw;
423 	notavail(bp);
424 	if (bp->b_flags & B_DELWRI) {
425 		bp->b_flags |= B_ASYNC;
426 		bwrite(bp);
427 		goto loop;
428 	}
429 #ifdef EPAWNJ
430 	trace(TR_BRELSE, bp->b_dev, dbtofsb(bp->b_blkno));
431 #endif
432 	bp->b_flags = B_BUSY|B_INVAL;
433 	bp->b_back->b_forw = bp->b_forw;
434 	bp->b_forw->b_back = bp->b_back;
435 	bp->b_forw = dp->b_forw;
436 	bp->b_back = dp;
437 	dp->b_forw->b_back = bp;
438 	dp->b_forw = bp;
439 	bp->b_dev = (dev_t)NODEV;
440 	return(bp);
441 }
442 
443 /*
444  * Wait for I/O completion on the buffer; return errors
445  * to the user.
446  */
447 iowait(bp)
448 register struct buf *bp;
449 {
450 
451 	(void) spl6();
452 	while ((bp->b_flags&B_DONE)==0)
453 		sleep((caddr_t)bp, PRIBIO);
454 	(void) spl0();
455 	geterror(bp);
456 }
457 
458 #ifndef FASTVAX
459 /*
460  * Unlink a buffer from the available list and mark it busy.
461  * (internal interface)
462  */
463 notavail(bp)
464 register struct buf *bp;
465 {
466 	register s;
467 
468 	s = spl6();
469 	bp->av_back->av_forw = bp->av_forw;
470 	bp->av_forw->av_back = bp->av_back;
471 	bp->b_flags |= B_BUSY;
472 	splx(s);
473 }
474 #endif
475 
476 /*
477  * Mark I/O complete on a buffer. If the header
478  * indicates a dirty page push completion, the
479  * header is inserted into the ``cleaned'' list
480  * to be processed by the pageout daemon. Otherwise
481  * release it if I/O is asynchronous, and wake
482  * up anyone waiting for it.
483  */
484 iodone(bp)
485 register struct buf *bp;
486 {
487 	register int s;
488 
489 	if (bp->b_flags & B_DONE)
490 		panic("dup iodone");
491 	bp->b_flags |= B_DONE;
492 	if (bp->b_flags & B_DIRTY) {
493 		if (bp->b_flags & B_ERROR)
494 			panic("IO err in push");
495 		s = spl6();
496 		cnt.v_pgout++;
497 		bp->av_forw = bclnlist;
498 		bp->b_bcount = swsize[bp - swbuf];
499 		bp->b_pfcent = swpf[bp - swbuf];
500 		bclnlist = bp;
501 		if (bswlist.b_flags & B_WANTED)
502 			wakeup((caddr_t)&proc[2]);
503 		splx(s);
504 		return;
505 	}
506 	if (bp->b_flags&B_ASYNC)
507 		brelse(bp);
508 	else {
509 		bp->b_flags &= ~B_WANTED;
510 		wakeup((caddr_t)bp);
511 	}
512 }
513 
514 /*
515  * Zero the core associated with a buffer.
516  */
517 clrbuf(bp)
518 struct buf *bp;
519 {
520 	register *p;
521 	register c;
522 
523 	p = bp->b_un.b_words;
524 	c = BSIZE/sizeof(int);
525 	do
526 		*p++ = 0;
527 	while (--c);
528 	bp->b_resid = 0;
529 }
530 
531 /*
532  * swap I/O -
533  *
534  * If the flag indicates a dirty page push initiated
535  * by the pageout daemon, we map the page into the i th
536  * virtual page of process 2 (the daemon itself) where i is
537  * the index of the swap header that has been allocated.
538  * We simply initialize the header and queue the I/O but
539  * do not wait for completion. When the I/O completes,
540  * iodone() will link the header to a list of cleaned
541  * pages to be processed by the pageout daemon.
542  */
543 swap(p, dblkno, addr, nbytes, rdflg, flag, dev, pfcent)
544 	struct proc *p;
545 	swblk_t dblkno;
546 	caddr_t addr;
547 	int flag, nbytes;
548 	dev_t dev;
549 	unsigned pfcent;
550 {
551 	register struct buf *bp;
552 	register int c;
553 	int p2dp;
554 	register struct pte *dpte, *vpte;
555 
556 	(void) spl6();
557 	while (bswlist.av_forw == NULL) {
558 		bswlist.b_flags |= B_WANTED;
559 		sleep((caddr_t)&bswlist, PSWP+1);
560 	}
561 	bp = bswlist.av_forw;
562 	bswlist.av_forw = bp->av_forw;
563 	(void) spl0();
564 
565 	bp->b_flags = B_BUSY | B_PHYS | rdflg | flag;
566 	if ((bp->b_flags & (B_DIRTY|B_PGIN)) == 0)
567 		if (rdflg == B_READ)
568 			sum.v_pswpin += btoc(nbytes);
569 		else
570 			sum.v_pswpout += btoc(nbytes);
571 	bp->b_proc = p;
572 	if (flag & B_DIRTY) {
573 		p2dp = ((bp - swbuf) * CLSIZE) * KLMAX;
574 		dpte = dptopte(&proc[2], p2dp);
575 		vpte = vtopte(p, btop(addr));
576 		for (c = 0; c < nbytes; c += NBPG) {
577 			if (vpte->pg_pfnum == 0 || vpte->pg_fod)
578 				panic("swap bad pte");
579 			*dpte++ = *vpte++;
580 		}
581 		bp->b_un.b_addr = (caddr_t)ctob(p2dp);
582 	} else
583 		bp->b_un.b_addr = addr;
584 	while (nbytes > 0) {
585 		c = imin(ctob(120), nbytes);
586 		bp->b_bcount = c;
587 		bp->b_blkno = dblkno;
588 		bp->b_dev = dev;
589 		if (flag & B_DIRTY) {
590 			swpf[bp - swbuf] = pfcent;
591 			swsize[bp - swbuf] = nbytes;
592 		}
593 		(*bdevsw[major(dev)].d_strategy)(bp);
594 		if (flag & B_DIRTY) {
595 			if (c < nbytes)
596 				panic("big push");
597 			return;
598 		}
599 		(void) spl6();
600 		while((bp->b_flags&B_DONE)==0)
601 			sleep((caddr_t)bp, PSWP);
602 		(void) spl0();
603 		bp->b_un.b_addr += c;
604 		bp->b_flags &= ~B_DONE;
605 		if (bp->b_flags & B_ERROR) {
606 			if ((flag & (B_UAREA|B_PAGET)) || rdflg == B_WRITE)
607 				panic("hard IO err in swap");
608 			swkill(p, (char *)0);
609 		}
610 		nbytes -= c;
611 		dblkno += btoc(c);
612 	}
613 	(void) spl6();
614 	bp->b_flags &= ~(B_BUSY|B_WANTED|B_PHYS|B_PAGET|B_UAREA|B_DIRTY);
615 	bp->av_forw = bswlist.av_forw;
616 	bswlist.av_forw = bp;
617 	if (bswlist.b_flags & B_WANTED) {
618 		bswlist.b_flags &= ~B_WANTED;
619 		wakeup((caddr_t)&bswlist);
620 		wakeup((caddr_t)&proc[2]);
621 	}
622 	(void) spl0();
623 }
624 
625 /*
626  * If rout == 0 then killed on swap error, else
627  * rout is the name of the routine where we ran out of
628  * swap space.
629  */
630 swkill(p, rout)
631 	struct proc *p;
632 	char *rout;
633 {
634 
635 	printf("%d: ", p->p_pid);
636 	if (rout)
637 		printf("out of swap space in %s\n", rout);
638 	else
639 		printf("killed on swap error\n");
640 	/*
641 	 * To be sure no looping (e.g. in vmsched trying to
642 	 * swap out) mark process locked in core (as though
643 	 * done by user) after killing it so noone will try
644 	 * to swap it out.
645 	 */
646 	psignal(p, SIGKILL);
647 	p->p_flag |= SULOCK;
648 }
649 
650 /*
651  * make sure all write-behind blocks
652  * on dev (or NODEV for all)
653  * are flushed out.
654  * (from umount and update)
655  */
656 bflush(dev)
657 dev_t dev;
658 {
659 	register struct buf *bp;
660 	register struct buf *flist;
661 
662 loop:
663 	(void) spl6();
664 	for (flist = bfreelist; flist < &bfreelist[BQUEUES]; flist++)
665 	for (bp = flist->av_forw; bp != flist; bp = bp->av_forw) {
666 		if (bp->b_flags&B_DELWRI && (dev == NODEV||dev==bp->b_dev)) {
667 			bp->b_flags |= B_ASYNC;
668 			notavail(bp);
669 			bwrite(bp);
670 			goto loop;
671 		}
672 	}
673 	(void) spl0();
674 }
675 
676 /*
677  * Raw I/O. The arguments are
678  *	The strategy routine for the device
679  *	A buffer, which will always be a special buffer
680  *	  header owned exclusively by the device for this purpose
681  *	The device number
682  *	Read/write flag
683  * Essentially all the work is computing physical addresses and
684  * validating them.
685  * If the user has the proper access privilidges, the process is
686  * marked 'delayed unlock' and the pages involved in the I/O are
687  * faulted and locked. After the completion of the I/O, the above pages
688  * are unlocked.
689  */
690 physio(strat, bp, dev, rw, mincnt)
691 int (*strat)();
692 register struct buf *bp;
693 unsigned (*mincnt)();
694 {
695 	register int c;
696 	char *a;
697 
698 	if (useracc(u.u_base,u.u_count,rw==B_READ?B_WRITE:B_READ) == NULL) {
699 		u.u_error = EFAULT;
700 		return;
701 	}
702 	(void) spl6();
703 	while (bp->b_flags&B_BUSY) {
704 		bp->b_flags |= B_WANTED;
705 		sleep((caddr_t)bp, PRIBIO+1);
706 	}
707 	bp->b_error = 0;
708 	bp->b_proc = u.u_procp;
709 	bp->b_un.b_addr = u.u_base;
710 	while (u.u_count != 0 && bp->b_error==0) {
711 		bp->b_flags = B_BUSY | B_PHYS | rw;
712 		bp->b_dev = dev;
713 		bp->b_blkno = u.u_offset >> PGSHIFT;
714 		bp->b_bcount = u.u_count;
715 		(*mincnt)(bp);
716 		c = bp->b_bcount;
717 		u.u_procp->p_flag |= SPHYSIO;
718 		vslock(a = bp->b_un.b_addr, c);
719 		(*strat)(bp);
720 		(void) spl6();
721 		while ((bp->b_flags&B_DONE) == 0)
722 			sleep((caddr_t)bp, PRIBIO);
723 		vsunlock(a, c, rw);
724 		u.u_procp->p_flag &= ~SPHYSIO;
725 		if (bp->b_flags&B_WANTED)
726 			wakeup((caddr_t)bp);
727 		(void) spl0();
728 		bp->b_un.b_addr += c;
729 		u.u_count -= c;
730 		u.u_offset += c;
731 	}
732 	bp->b_flags &= ~(B_BUSY|B_WANTED|B_PHYS);
733 	u.u_count = bp->b_resid;
734 	geterror(bp);
735 }
736 
737 /*ARGSUSED*/
738 unsigned
739 minphys(bp)
740 struct buf *bp;
741 {
742 
743 	if (bp->b_bcount > 60 * 1024)
744 		bp->b_bcount = 60 * 1024;
745 }
746 
747 /*
748  * Pick up the device's error number and pass it to the user;
749  * if there is an error but the number is 0 set a generalized
750  * code.  Actually the latter is always true because devices
751  * don't yet return specific errors.
752  */
753 geterror(bp)
754 register struct buf *bp;
755 {
756 
757 	if (bp->b_flags&B_ERROR)
758 		if ((u.u_error = bp->b_error)==0)
759 			u.u_error = EIO;
760 }
761 
762 /*
763  * Invalidate in core blocks belonging to closed or umounted filesystem
764  *
765  * This is not nicely done at all - the buffer ought to be removed from the
766  * hash chains & have its dev/blkno fields clobbered, but unfortunately we
767  * can't do that here, as it is quite possible that the block is still
768  * being used for i/o. Eventually, all disc drivers should be forced to
769  * have a close routine, which ought ensure that the queue is empty, then
770  * properly flush the queues. Until that happy day, this suffices for
771  * correctness.						... kre
772  */
773 binval(dev)
774 dev_t dev;
775 {
776 	register struct buf *bp;
777 	register struct bufhd *hp;
778 #define dp ((struct buf *)hp)
779 
780 	for (hp = bufhash; hp < &bufhash[BUFHSZ]; hp++)
781 		for (bp = dp->b_forw; bp != dp; bp = bp->b_forw)
782 			if (bp->b_dev == dev)
783 				bp->b_flags |= B_INVAL;
784 }
785