diff options
author | ken <ken@FreeBSD.org> | 1998-12-16 18:00:39 +0000 |
---|---|---|
committer | ken <ken@FreeBSD.org> | 1998-12-16 18:00:39 +0000 |
commit | 60f9c7106b7f12ec3c2a086e58b2a5b8ff6ae051 (patch) | |
tree | de3b4164bd164ae6a09916de5cb53abbde1cf9e8 /secure/Makefile.inc | |
parent | bae37e638ab1e55f2378c607581f9f7658f23547 (diff) | |
download | FreeBSD-src-60f9c7106b7f12ec3c2a086e58b2a5b8ff6ae051.zip FreeBSD-src-60f9c7106b7f12ec3c2a086e58b2a5b8ff6ae051.tar.gz |
Probable fix for the "cdda2wav" panics that various people have been
reporting since this past summer. (I think Daniel O'Conner was the first.)
The problem appears to have been something like this:
- cdda2wav by default passes in a buffer that is close to the 128K MAXPHYS
limit.
- many times, the buffer is not page aligned
- vmapbuf() truncates the address, so that it is page aligned
- that causes the total size of the buffer to be greater than MAXPHYS,
which of course is a bad thing.
Here's a quote from the PR (kern/9067):
==================
In particular, note bp->b_bufsize = 0x0001f950 and bp->b_data = 0xf2219960
(which does not start on a page boundary). vunmapbuf() loops through all
the pages without any difficulty until addr reaches 0xf2239000, and then
the panic occurs. This seems to indicate that we are exceeding MAXPHYS
since we actually started from the middle of a page (the data is being
transfered to a non page aligned location).
To complete the description, note that the system call originates from
ReadCddaMMC12() (in scsi_cmds.c of cdda2wav) with a request to read 55
audio sectors of 2352 bytes (which is calculated to fall under MAXPHYS).
This in turn ends up calling scsi_send() (in scsi-bsd.c) which calls
cam_fill_csio() and cam_send_ccb(). This results in a CAMIOCOMMAND ioctl
with a ccb function code of XPT_SCSI_IO.
==================
The fix is to change the size check in cam_periph_mapmem() so that it is
like the one in minphys(). In particular, it is something like:
if ((buffer_length + (buf_ptr & PAGE_MASK)) > MAXPHYS)
buffer is too big
My fix is based on the one in the PR, but I cleaned up a fair number of
things in cam_periph_mapmem(). The checks for each buffer to be mapped
are now in a separate loop from the actual mapping operation. With the new
arrangement, we don't have to bother with unmapping any previously mapped
buffers if one of the checks fails.
Many thanks to James Liu for tracking this down. I'd appreciate it if some
vm-savvy folks would look this over. I believe this fix is correct, but I
could be wrong.
PR: kern/9067 (also, kern/8112)
Reviewed by: gibbs
Submitted by: "James T. Liu" <jtliu@phlebas.rockefeller.edu>
Diffstat (limited to 'secure/Makefile.inc')
0 files changed, 0 insertions, 0 deletions