From 9e0a71c3eebd8d8e34dfa434ee6b139736c61490 Mon Sep 17 00:00:00 2001 From: ache Date: Tue, 30 Jan 1996 13:15:28 +0000 Subject: READTOCENTRYS: protect against stack overflow when incorrect data stored in CD's TOC --- sys/dev/mcd/mcd.c | 20 +++++++++++++------- sys/i386/isa/mcd.c | 20 +++++++++++++------- sys/i386/isa/wcd.c | 7 ++++--- 3 files changed, 30 insertions(+), 17 deletions(-) diff --git a/sys/dev/mcd/mcd.c b/sys/dev/mcd/mcd.c index b77b2ec..30821ef 100644 --- a/sys/dev/mcd/mcd.c +++ b/sys/dev/mcd/mcd.c @@ -40,7 +40,7 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * - * $Id: mcd.c,v 1.60 1996/01/30 10:31:06 ache Exp $ + * $Id: mcd.c,v 1.61 1996/01/30 12:07:06 ache Exp $ */ static char COPYRIGHT[] = "mcd-driver (C)1993 by H.Veit & B.Moore"; @@ -1431,15 +1431,14 @@ mcd_toc_entrys(int unit, struct ioc_read_toc_entry *te) struct mcd_data *cd = mcd_data + unit; struct cd_toc_entry entries[MCD_MAXTOCS]; struct ioc_toc_header th; - int rc, n, trk, len = te->data_len; + int rc, n, trk, len; - if ( len < sizeof(entries[0]) - || (len % sizeof(entries[0])) != 0 + if ( te->data_len < sizeof(entries[0]) + || (te->data_len % sizeof(entries[0])) != 0 + || te->address_format != CD_MSF_FORMAT + && te->address_format != CD_LBA_FORMAT ) return EINVAL; - if (te->address_format != CD_MSF_FORMAT && - te->address_format != CD_LBA_FORMAT) - return EINVAL; /* Copy the toc header */ if ((rc = mcd_toc_header(unit, &th)) != 0) @@ -1454,6 +1453,13 @@ mcd_toc_entrys(int unit, struct ioc_read_toc_entry *te) else if (trk < th.starting_track || trk > th.ending_track + 1) return EINVAL; + len = ((th.ending_track + 1 - trk) + 1) * + sizeof(entries[0]); + if (te->data_len < len) + len = te->data_len; + if (len > sizeof(entries)) + return EINVAL; + /* Make sure we have a valid toc */ if ((rc=mcd_read_toc(unit)) != 0) return rc; diff --git a/sys/i386/isa/mcd.c b/sys/i386/isa/mcd.c index b77b2ec..30821ef 100644 --- a/sys/i386/isa/mcd.c +++ b/sys/i386/isa/mcd.c @@ -40,7 +40,7 @@ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * - * $Id: mcd.c,v 1.60 1996/01/30 10:31:06 ache Exp $ + * $Id: mcd.c,v 1.61 1996/01/30 12:07:06 ache Exp $ */ static char COPYRIGHT[] = "mcd-driver (C)1993 by H.Veit & B.Moore"; @@ -1431,15 +1431,14 @@ mcd_toc_entrys(int unit, struct ioc_read_toc_entry *te) struct mcd_data *cd = mcd_data + unit; struct cd_toc_entry entries[MCD_MAXTOCS]; struct ioc_toc_header th; - int rc, n, trk, len = te->data_len; + int rc, n, trk, len; - if ( len < sizeof(entries[0]) - || (len % sizeof(entries[0])) != 0 + if ( te->data_len < sizeof(entries[0]) + || (te->data_len % sizeof(entries[0])) != 0 + || te->address_format != CD_MSF_FORMAT + && te->address_format != CD_LBA_FORMAT ) return EINVAL; - if (te->address_format != CD_MSF_FORMAT && - te->address_format != CD_LBA_FORMAT) - return EINVAL; /* Copy the toc header */ if ((rc = mcd_toc_header(unit, &th)) != 0) @@ -1454,6 +1453,13 @@ mcd_toc_entrys(int unit, struct ioc_read_toc_entry *te) else if (trk < th.starting_track || trk > th.ending_track + 1) return EINVAL; + len = ((th.ending_track + 1 - trk) + 1) * + sizeof(entries[0]); + if (te->data_len < len) + len = te->data_len; + if (len > sizeof(entries)) + return EINVAL; + /* Make sure we have a valid toc */ if ((rc=mcd_read_toc(unit)) != 0) return rc; diff --git a/sys/i386/isa/wcd.c b/sys/i386/isa/wcd.c index 3821b1c..94c76a5 100644 --- a/sys/i386/isa/wcd.c +++ b/sys/i386/isa/wcd.c @@ -767,11 +767,10 @@ int wcdioctl (dev_t dev, int cmd, caddr_t addr, int flag, struct proc *p) if ( te->data_len < sizeof(toc->tab[0]) || (te->data_len % sizeof(toc->tab[0])) != 0 + || te->address_format != CD_MSF_FORMAT + && te->address_format != CD_LBA_FORMAT ) return EINVAL; - if (te->address_format != CD_MSF_FORMAT && - te->address_format != CD_LBA_FORMAT) - return EINVAL; if (starting_track == 0) starting_track = toc->hdr.starting_track; @@ -785,6 +784,8 @@ int wcdioctl (dev_t dev, int cmd, caddr_t addr, int flag, struct proc *p) sizeof(toc->tab[0]); if (te->data_len < len) len = te->data_len; + if (len > sizeof(toc->tab)) + return EINVAL; /* Convert to MSF format, if needed. */ if (te->address_format == CD_MSF_FORMAT) { -- cgit v1.1