NetBSD Problem Report #39904

From www@NetBSD.org  Wed Nov 12 18:33:24 2008
Return-Path: <www@NetBSD.org>
Received: from mail.netbsd.org (mail.netbsd.org [204.152.190.11])
	by narn.NetBSD.org (Postfix) with ESMTP id A000F63B8A9
	for <gnats-bugs@gnats.netbsd.org>; Wed, 12 Nov 2008 18:33:24 +0000 (UTC)
Message-Id: <20081112183324.5DAD663B898@narn.NetBSD.org>
Date: Wed, 12 Nov 2008 18:33:24 +0000 (UTC)
From: svs@ropnet.ru
Reply-To: svs@ropnet.ru
To: gnats-bugs@NetBSD.org
Subject: Unreadable CD may lead to panic (integer divide fault trap in cdstrategy)
X-Send-Pr-Version: www-1.0

>Number:         39904
>Category:       kern
>Synopsis:       Unreadable CD may lead to panic in scsipi/cd.c:cdstrategy()
>Confidential:   no
>Severity:       non-critical
>Priority:       medium
>Responsible:    kern-bug-people
>State:          closed
>Class:          sw-bug
>Submitter-Id:   net
>Arrival-Date:   Wed Nov 12 18:35:00 +0000 2008
>Closed-Date:    Sat Dec 19 02:35:37 +0000 2015
>Last-Modified:  Sat Dec 19 02:35:37 +0000 2015
>Originator:     Sergey Svishchev
>Release:        4.0
>Organization:
>Environment:
>Description:
In scsipi/cd.c, cd_size() exits early (but doesn't return 0 that
cd_get_parms() expects) if read_cd_capacity() fails.  Thus,
cd->params.blksize is left at 0, which leads to trap in cdstrategy()
when it's used as divisor:

                /*
                 * If the xfer is not a multiple of the device block size
                 * or it is not block aligned, we need to bounce it.
                 */
                if ((bp->b_bcount % cd->params.blksize) != 0 ||


>How-To-Repeat:
Try to mount a very old (and unreadable) CD-R.
>Fix:
Make cd_size() return 0 or don't return early at all?

>Release-Note:

>Audit-Trail:
From: jnemeth@victoria.tc.ca (John Nemeth)
To: gnats-bugs@NetBSD.org, kern-bug-people@NetBSD.org, netbsd-bugs@NetBSD.org
Cc: 
Subject: Re: kern/39904: Unreadable CD may lead to panic (integer divide fault trap in cdstrategy)
Date: Wed, 12 Nov 2008 16:39:04 -0800

 On Feb 28,  6:42am, svs@ropnet.ru wrote:
 }
 } >Synopsis:       Unreadable CD may lead to panic (integer divide fault trap in cdstrategy)
 } >Arrival-Date:   Wed Nov 12 18:35:00 +0000 2008
 } >Originator:     Sergey Svishchev
 } >Release:        4.0
 } >Description:
 } cd_size() exits early (but doesn't return 0 that cd_get_parms() expects) if read_cd_capacity() fails.  Thus, cd->params.blksize is left at 0, which leads to trap in cdstrategy():

      Which cd driver is this?

 }-- End of excerpt from svs@ropnet.ru

From: Sergey Svishchev <svs@ropnet.ru>
To: gnats-bugs@NetBSD.org
Cc: 
Subject: Re: kern/39904
Date: Thu, 13 Nov 2008 08:17:21 +0300

 On Thu, Nov 13, 2008 at 12:40:03AM +0000, John Nemeth wrote:
 >The following reply was made to PR kern/39904; it has been noted by GNATS.
 >
 >From: jnemeth@victoria.tc.ca (John Nemeth)
 >To: gnats-bugs@NetBSD.org, kern-bug-people@NetBSD.org, netbsd-bugs@NetBSD.org
 >Cc: 
 >Subject: Re: kern/39904: Unreadable CD may lead to panic (integer divide fault trap in cdstrategy)
 >Date: Wed, 12 Nov 2008 16:39:04 -0800
 >
 > On Feb 28,  6:42am, svs@ropnet.ru wrote:
 > }
 > } >Synopsis:       Unreadable CD may lead to panic (integer divide fault trap in cdstrategy)
 > } >Arrival-Date:   Wed Nov 12 18:35:00 +0000 2008
 > } >Originator:     Sergey Svishchev
 > } >Release:        4.0
 > } >Description:
 > } cd_size() exits early (but doesn't return 0 that cd_get_parms() expects) if read_cd_capacity() fails.  Thus, cd->params.blksize is left at 0, which leads to trap in cdstrategy():
 > 
 >      Which cd driver is this?

 scsipi/cd.c

 -- 
 Sergey Svishchev

From: Patrick Welche <prlw1@cam.ac.uk>
To: gnats-bugs@netbsd.org
Cc: 
Subject: Re: kern/39904
Date: Sat, 3 Apr 2010 23:49:17 +0100

 I basically just saw the same trouble playing a new DVD with mplayer on
 NetBSD-current/i386 code of 1 Apr 2010 19:27.

 I get a panic because cd_softc contains zeros:

 (gdb) print cd->params
 $5 = {blksize = 0, disksize = 0, disksize512 = 0}

 so bp->b_bcount % cd->params.blksize can't be happy (N mod zero)


 Extras:

 (gdb) bt
 #0  cpu_reboot (howto=260, bootstr=0x0)
     at ../../../../arch/i386/i386/machdep.c:854
 #1  0xc03d82a3 in panic (fmt=0xc055a1f4 "trap")
     at ../../../../kern/subr_prf.c:302
 #2  0xc0409c58 in trap (frame=0xcc9a3a04)
     at ../../../../arch/i386/i386/trap.c:409
 #3  0xc010cb0f in calltrap ()
 #4  0xc0191287 in cdstrategy (bp=0xc1843a58) at ../../../../dev/scsipi/cd.c:637
 #5  0xc03cbb52 in bdev_strategy (bp=0xc1843a58)
     at ../../../../kern/subr_devsw.c:744
 #6  0xc03c0d97 in spec_strategy (v=0xcc9a3b0c)
     at ../../../../miscfs/specfs/spec_vnops.c:909
 #7  0xc04918ff in VOP_STRATEGY (vp=0xcb505f18, bp=0xc1843a58)
     at ../../../../kern/vnode_if.c:1234
 #8  0xc0471acf in bio_doread (vp=0xcb505f18, blkno=<value optimized out>, 
     size=2048, cred=0xffffffff, async=0) at ../../../../kern/vfs_bio.c:694
 #9  0xc0471ca8 in bread (vp=0xcb505f18, blkno=0, size=2048, cred=0xffffffff, 
     flags=0, bpp=0xcc9a3bc8) at ../../../../kern/vfs_bio.c:733
 #10 0xc03c1c91 in spec_read (v=0xcc9a3c04)
     at ../../../../miscfs/specfs/spec_vnops.c:618
 #11 0xc04924de in VOP_READ (vp=0xcb505f18, uio=0xcc9a3c7c, ioflag=0, 
     cred=0xcbc4a900) at ../../../../kern/vnode_if.c:408
 #12 0xc0482d81 in vn_read (fp=0xcc6dc280, offset=0xcc6dc280, uio=0xcc9a3c7c, 
     cred=0xcbc4a900, flags=1) at ../../../../kern/vfs_vnops.c:488
 #13 0xc03df125 in dofileread (fd=11, fp=0x800, buf=0xbfbfb5a3, nbyte=2048, 
     offset=0xcc6dc280, flags=1, retval=0xcc9a3d28)
     at ../../../../kern/sys_generic.c:157
 #14 0xc03df20c in sys_read (l=0xcc7f2540, uap=0xcc9a3d00, retval=0xcc9a3d28)
     at ../../../../kern/sys_generic.c:122
 #15 0xc03eaa87 in syscall (frame=0xcc9a3d48) at ../../../../sys/syscallvar.h:61
 #16 0xc0100504 in syscall1 ()
 (gdb) frame 4
 #4  0xc0191287 in cdstrategy (bp=0xc1843a58) at ../../../../dev/scsipi/cd.c:637
 637                     if ((bp->b_bcount % cd->params.blksize) != 0 ||
 (gdb) print *cd
 $1 = {sc_dev = 0xcb2f1400, sc_dk = {dk_link = {tqe_next = 0x0, 
       tqe_prev = 0x0}, dk_name = 0xcb2f141c "cd0", dk_info = 0xca3b4440, 
     dk_bopenmask = 1, dk_copenmask = 0, dk_openmask = 1, dk_state = 0, 
     dk_blkshift = -1, dk_byteshift = -1, dk_stats = 0xcb2f0e80, 
     dk_driver = 0xc0579f2c, dk_rawlock = {u = {mtxa_owner = 0}}, 
     dk_rawopens = 0, dk_rawvp = 0x0, dk_openlock = {u = {mtxa_owner = 0}}, 
     dk_nwedges = 0, dk_wedges = {lh_first = 0x0}, dk_labelsector = 1, 
     dk_label = 0xcb2f1600, dk_cpulabel = 0xcb2f1800}, sc_lock = {u = {
       mtxa_owner = 0}}, flags = 0, sc_periph = 0xc1175200, params = {
     blksize = 0, disksize = 0, disksize512 = 0}, buf_queue = 0xca39bdb0, 
   sc_callout = {_c_store = {0x0, 0x0, 0x0, 0x0, 0xc05ac800, 0x0, 0x1, 
       0x11deeba1, 0x0, 0x0}}, rnd_source = {list = {le_next = 0xcb2f06e0, 
       le_prev = 0xcb30df78}, data = {name = "cd0", '\0' <repeats 12 times>, 
       last_time = 645649805, last_delta = 0, last_delta2 = 0, total = 0, 
       type = 1, flags = 0, state = 0xc10e4420}}}
 (gdb) print *bp
 $2 = {b_u = {u_actq = {tqe_next = 0x0, tqe_prev = 0x0}, u_work = {
       wk_dummy = 0x0}}, b_iodone = 0, b_error = 0, b_resid = 0, 
   b_flags = 1048576, b_prio = 2, b_bufsize = 2048, b_bcount = 2048, 
   b_dev = 1536, b_data = 0xcdec1800, b_blkno = 0, b_rawblkno = 0, 
   b_proc = 0x0, b_saveaddr = 0x0, b_private = 0x0, b_dcookie = 0, b_busy = {
     cv_opaque = {0x0, 0xc1843aac, 0xc05678a4}}, b_refcnt = 1, b_unused = 0x0, 
   b_hash = {le_next = 0x0, le_prev = 0xca59417c}, b_vnbufs = {le_next = 0x0, 
     le_prev = 0xcb505f94}, b_freelist = {tqe_next = 0xc1840bc0, 
     tqe_prev = 0xc05e6248}, b_wapbllist = {le_next = 0x0, le_prev = 0x0}, 
   b_lblkno = 0, b_freelistindex = 2, b_cflags = 16, b_vp = 0xcb505f18, 
   b_done = {cv_opaque = {0x0, 0xc1843af4, 0xc05678ac}}, b_oflags = 0, 
   b_objlock = 0xcb505f18}
 (gdb) print bp->b_bcount
 $3 = 2048
 (gdb) print cd->params.blksize
 $4 = 0
 (gdb) print cd->params
 $5 = {blksize = 0, disksize = 0, disksize512 = 0}
 (gdb) print *lp
 $6 = {d_magic = 2186691927, d_type = 13, d_subtype = 0, 
   d_typename = "optical media\000\000", d_un = {
     un_d_packname = "fictitious\000\000\000\000\000", un_b = {
       un_d_boot0 = 0x74636966 <Address 0x74636966 out of bounds>, 
       un_d_boot1 = 0x6f697469 <Address 0x6f697469 out of bounds>}}, 
   d_secsize = 512, d_nsectors = 100, d_ntracks = 1, d_ncylinders = 1, 
   d_secpercyl = 100, d_secperunit = 536870911, d_sparespertrack = 0, 
   d_sparespercyl = 0, d_acylinders = 0, d_rpm = 300, d_interleave = 1, 
   d_trackskew = 0, d_cylskew = 0, d_headswitch = 0, d_trkseek = 0, 
   d_flags = 33, d_drivedata = {0, 0, 0, 0, 0}, d_spare = {0, 0, 0, 0, 0}, 
   d_magic2 = 2186691927, d_checksum = 8221, d_npartitions = 4, d_bbsize = 0, 
   d_sbsize = 0, d_partitions = {{p_size = 536870911, p_offset = 0, 
       __partition_u2 = {fsize = 0, cdsession = 0}, p_fstype = 7 '\a', 
       p_frag = 0 '\0', __partition_u1 = {cpg = 0, sgs = 0}}, {p_size = 0, 
       p_offset = 0, __partition_u2 = {fsize = 0, cdsession = 0}, 
       p_fstype = 0 '\0', p_frag = 0 '\0', __partition_u1 = {cpg = 0, 
         sgs = 0}}, {p_size = 0, p_offset = 0, __partition_u2 = {fsize = 0, 
         cdsession = 0}, p_fstype = 0 '\0', p_frag = 0 '\0', __partition_u1 = {
         cpg = 0, sgs = 0}}, {p_size = 536870911, p_offset = 0, 
       __partition_u2 = {fsize = 0, cdsession = 0}, p_fstype = 24 '\030', 
       p_frag = 0 '\0', __partition_u1 = {cpg = 0, sgs = 0}}, {p_size = 0, 
       p_offset = 0, __partition_u2 = {fsize = 0, cdsession = 0}, 
       p_fstype = 0 '\0', p_frag = 0 '\0', __partition_u1 = {cpg = 0, 
         sgs = 0}} <repeats 12 times>}}

From: Martin Husemann <martin@netbsd.org>
To: gnats-bugs@gnats.NetBSD.org
Cc: 
Subject: PR/39904 CVS commit: src/sys/dev/scsipi
Date: Sun, 4 Apr 2010 21:36:22 +0000

 Module Name:	src
 Committed By:	martin
 Date:		Sun Apr  4 21:36:22 UTC 2010

 Modified Files:
 	src/sys/dev/scsipi: cd.c

 Log Message:
 cd_size: if we fake a size (and I realy have no idea why this would be a
 good idea), at least set up all values to the fake values, as the caller
 expects.
 Should fix PR kern/39904, though if noone can find out why the fake value
 would be needed, we should change it to just return 0 as suggested in the PR.


 To generate a diff of this commit:
 cvs rdiff -u -r1.301 -r1.302 src/sys/dev/scsipi/cd.c

 Please note that diffs are not public domain; they are subject to the
 copyright notices on the relevant files.

State-Changed-From-To: open->closed
State-Changed-By: dholland@NetBSD.org
State-Changed-When: Sat, 19 Dec 2015 02:35:37 +0000
State-Changed-Why:
fixed in HEAD after -5 and -5 is now EOL


>Unformatted:

NetBSD Home
NetBSD PR Database Search

(Contact us) $NetBSD: query-full-pr,v 1.39 2013/11/01 18:47:49 spz Exp $
$NetBSD: gnats_config.sh,v 1.8 2006/05/07 09:23:38 tsutsui Exp $
Copyright © 1994-2007 The NetBSD Foundation, Inc. ALL RIGHTS RESERVED.