From: David Balazic <david.balazic@uni-mb.si>
To: "linux-kernel@vger.kernel.org" <linux-kernel@vger.kernel.org>
Subject: Possible off-by-one errors in CDROM handling code
Date: Wed, 25 Apr 2001 12:26:50 +0200 [thread overview]
Message-ID: <3AE6A66A.A43DCFBA@uni-mb.si> (raw)
There seem to be some off-by-one errors in the cdrom/ide-cd driver,
where CD capacity is handled in the redhat kernel-source-2.4.1-0.1.9
and also in kernel-2.4.3 )
>From the file linux/drivers/ide/ide-cd.c :
(My comments start with '#')
static int cdrom_read_capacity(ide_drive_t *drive, unsigned *capacity,
struct request_sense *sense)
{
struct {
__u32 lba;
__u32 blocklen;
} capbuf;
int stat;
struct packet_command pc;
memset(&pc, 0, sizeof(pc));
pc.sense = sense;
pc.c[0] = GPCMD_READ_CDVD_CAPACITY;
pc.buffer = (char *)&capbuf;
pc.buflen = sizeof(capbuf);
stat = cdrom_queue_packet_command(drive, &pc);
if (stat == 0)
*capacity = 1 + be32_to_cpu(capbuf.lba); # this seems correct , the CD reports the
# address of the last sector , sectors are counted from 0
return stat;
}
...
in function static int cdrom_read_toc() :
/* Now try to get the total cdrom capacity. */
minor = (drive->select.b.unit) << PARTN_BITS;
dev = MKDEV(HWIF(drive)->major, minor);
stat = cdrom_get_last_written(dev, (long *)&toc->capacity); # this returns the last sector number ,
# should add one to get capacity !!!
if (stat)
stat = cdrom_read_capacity(drive, &toc->capacity, sense); # this returns the correct capacity
if (stat)
toc->capacity = 0x1fffff;
HWIF(drive)->gd->sizes[drive->select.b.unit << PARTN_BITS] = (toc->capacity * SECTORS_PER_FRAME) >> (BLOCK_SIZE_BITS - 9);
drive->part[0].nr_sects = toc->capacity * SECTORS_PER_FRAME;
...
-------------------------
from linux/drivers/cdrom/cdrom.c :
/* return the last written block on the CD-R media. this is for the udf
file system. */
int cdrom_get_last_written(kdev_t dev, long *last_written)
{
struct cdrom_device_info *cdi = cdrom_find_device(dev);
struct cdrom_tocentry toc;
disc_information di;
track_information ti;
__u32 last_track;
int ret = -1;
if (!CDROM_CAN(CDC_GENERIC_PACKET))
goto use_toc;
if ((ret = cdrom_get_disc_info(dev, &di)))
goto use_toc;
last_track = (di.last_track_msb << 8) | di.last_track_lsb;
if ((ret = cdrom_get_track_info(dev, last_track, 1, &ti)))
goto use_toc;
/* if this track is blank, try the previous. */
if (ti.blank) {
last_track--;
if ((ret = cdrom_get_track_info(dev, last_track, 1, &ti)))
goto use_toc;
}
/* if last recorded field is valid, return it. */
if (ti.lra_v) {
*last_written = be32_to_cpu(ti.last_rec_address); # seems OK
} else {
/* make it up instead */
*last_written = be32_to_cpu(ti.track_start) + # on a two sector CD ( sectors 0 and 1 ), this returns :
be32_to_cpu(ti.track_size); # 0 + 2 = 2 , instead of 1 !!!
if (ti.free_blocks)
*last_written -= (be32_to_cpu(ti.free_blocks) + 7); # no idea what this does ,
# maybe it fixes the previous error
}
return 0;
/* this is where we end up if the drive either can't do a
GPCMD_READ_DISC_INFO or GPCMD_READ_TRACK_RZONE_INFO or if
it fails. then we return the toc contents. */
use_toc:
toc.cdte_format = CDROM_MSF;
toc.cdte_track = CDROM_LEADOUT;
if (cdi->ops->audio_ioctl(cdi, CDROMREADTOCENTRY, &toc))
return ret;
sanitize_format(&toc.cdte_addr, &toc.cdte_format, CDROM_LBA);
*last_written = toc.cdte_addr.lba; # seems OK
return 0;
}
--
David Balazic
--------------
"Be excellent to each other." - Bill & Ted
- - - - - - - - - - - - - - - - - - - - - -
reply other threads:[~2001-04-25 10:27 UTC|newest]
Thread overview: [no followups] expand[flat|nested] mbox.gz Atom feed
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=3AE6A66A.A43DCFBA@uni-mb.si \
--to=david.balazic@uni-mb.si \
--cc=linux-kernel@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox