/*ARGSUSED*/ int cflrw(dev_t dev, struct uio *uio, int flag) { struct buf *bp; int i; int s; int error; if (uio->uio_resid == 0) return (0); s = splconsmedia(); while (cfltab.cfl_state == BUSY) (void) tsleep(&cfltab, PRIBIO, "cflbusy", 0); cfltab.cfl_state = BUSY; splx(s); bp = cfltab.cfl_buf; error = 0; while ((i = imin(CFL_BYTESPERSEC, uio->uio_resid)) > 0) { bp->b_blkno = uio->uio_offset>>7; if (bp->b_blkno >= CFL_MAXSEC || (uio->uio_offset & 0x7F) != 0) { error = EIO; break; } if (uio->uio_rw == UIO_WRITE) { error = uiomove(bp->b_data, i, uio); if (error) break; } if (uio->uio_rw == UIO_WRITE) { bp->b_oflags &= ~(BO_DONE); bp->b_flags &= ~(B_READ); bp->b_flags |= B_WRITE; } else { bp->b_oflags &= ~(BO_DONE); bp->b_flags &= ~(B_WRITE); bp->b_flags |= B_READ; } s = splconsmedia(); cflstart(); biowait(bp); splx(s); if (bp->b_error != 0) { error = bp->b_error; break; } if (uio->uio_rw == UIO_READ) { error = uiomove(bp->b_data, i, uio); if (error) break; } } cfltab.cfl_state = OPEN; wakeup((void *)&cfltab); return (error); }
/*ARGSUSED*/ int crlrw(dev_t dev, struct uio *uio, int flag) { struct buf *bp; int i; int s; int error; if (uio->uio_resid == 0) return (0); s = splconsmedia(); while (crltab.crl_state & CRL_BUSY) (void) tsleep(&crltab, PRIBIO, "crlbusy", 0); crltab.crl_state |= CRL_BUSY; splx(s); bp = crltab.crl_buf; error = 0; while ((i = imin(CRLBYSEC, uio->uio_resid)) > 0) { bp->b_blkno = uio->uio_offset>>9; if (bp->b_blkno >= MAXSEC || (uio->uio_offset & 0x1FF) != 0) { error = EIO; break; } if (uio->uio_rw == UIO_WRITE) { error = uiomove(bp->b_data, i, uio); if (error) break; } if (uio->uio_rw == UIO_WRITE) { bp->b_oflags &= ~(BO_DONE); bp->b_flags &= ~(B_READ); bp->b_flags |= B_WRITE; } else { bp->b_oflags &= ~(BO_DONE); bp->b_flags &= ~(B_WRITE); bp->b_flags |= B_READ; } s = splconsmedia(); crlstart(); while ((bp->b_oflags & BO_DONE) == 0) (void) tsleep(bp, PRIBIO, "crlxfer", 0); splx(s); if (bp->b_error != 0) { error = bp->b_error; break; } if (uio->uio_rw == UIO_READ) { error = uiomove(bp->b_data, i, uio); if (error) break; } } crltab.crl_state &= ~CRL_BUSY; wakeup((void *)&crltab); return (error); }