From 21a8b9c2ac453dce1cfe26cca6f2ba14964c29f5 Mon Sep 17 00:00:00 2001 From: Artem Bityutskiy Date: Mon, 11 May 2009 19:22:34 +0300 Subject: ubi-utils: fix memory corruptions This patch contains changes similar to the ones in the previous patch. Also, it changes all invocations of memset and makes sure the argument is 0, not '\0', because memset expects int, not char. Signed-off-by: Artem Bityutskiy --- ubi-utils/src/libmtd.c | 21 +++++++++++++++------ ubi-utils/src/libubi.c | 17 ++++++++++++----- ubi-utils/src/libubigen.c | 6 +++--- 3 files changed, 30 insertions(+), 14 deletions(-) diff --git a/ubi-utils/src/libmtd.c b/ubi-utils/src/libmtd.c index 046beea..b050bea 100644 --- a/ubi-utils/src/libmtd.c +++ b/ubi-utils/src/libmtd.c @@ -89,6 +89,14 @@ static int read_data(const char *file, void *buf, int buf_len) goto out_error; } + if (rd == buf_len) { + errmsg("contents of \"%s\" is too long", file); + errno = EINVAL; + goto out_error; + } + + ((char *)buf)[rd] = '\0'; + /* Make sure all data is read */ tmp1 = read(fd, &tmp, 1); if (tmp1 == 1) { @@ -199,16 +207,17 @@ static int read_hex_ll(const char *file, long long *value) if (fd == -1) return -1; - rd = read(fd, buf, 50); + rd = read(fd, buf, sizeof(buf)); if (rd == -1) { sys_errmsg("cannot read \"%s\"", file); goto out_error; } - if (rd == 50) { + if (rd == sizeof(buf)) { errmsg("contents of \"%s\" is too long", file); errno = EINVAL; goto out_error; } + buf[rd] = '\0'; if (sscanf(buf, "%llx\n", value) != 1) { errmsg("cannot read integer from \"%s\"\n", file); @@ -571,7 +580,7 @@ int mtd_get_info(libmtd_t desc, struct mtd_info *info) struct dirent *dirent; struct libmtd *lib = (struct libmtd *)desc; - memset(info, '\0', sizeof(struct mtd_info)); + memset(info, 0, sizeof(struct mtd_info)); if (!lib->sysfs_supported) return legacy_mtd_get_info(info); @@ -643,7 +652,7 @@ int mtd_get_dev_info1(libmtd_t desc, int dev_num, struct mtd_dev_info *mtd) struct stat st; struct libmtd *lib = (struct libmtd *)desc; - memset(mtd, '\0', sizeof(struct mtd_dev_info)); + memset(mtd, 0, sizeof(struct mtd_dev_info)); mtd->dev_num = dev_num; if (!lib->sysfs_supported) @@ -663,13 +672,13 @@ int mtd_get_dev_info1(libmtd_t desc, int dev_num, struct mtd_dev_info *mtd) return -1; ret = dev_read_data(lib->mtd_name, dev_num, &mtd->name, - MTD_NAME_MAX); + MTD_NAME_MAX + 1); if (ret < 0) return -1; ((char *)mtd->name)[ret - 1] = '\0'; ret = dev_read_data(lib->mtd_type, dev_num, &mtd->type_str, - MTD_TYPE_MAX); + MTD_TYPE_MAX + 1); if (ret < 0) return -1; ((char *)mtd->type_str)[ret - 1] = '\0'; diff --git a/ubi-utils/src/libubi.c b/ubi-utils/src/libubi.c index 6f9228e..a4313ab 100644 --- a/ubi-utils/src/libubi.c +++ b/ubi-utils/src/libubi.c @@ -166,6 +166,13 @@ static int read_data(const char *file, void *buf, int buf_len) sys_errmsg("cannot read \"%s\"", file); goto out_error; } + + if (rd == buf_len) { + errmsg("contents of \"%s\" is too long", file); + errno = EINVAL; + goto out_error; + } + ((char *)buf)[rd] = '\0'; /* Make sure all data is read */ @@ -676,7 +683,7 @@ int ubi_attach_mtd(libubi_t desc, const char *node, int fd, ret; struct ubi_attach_req r; - memset(&r, sizeof(struct ubi_attach_req), '\0'); + memset(&r, 0, sizeof(struct ubi_attach_req)); desc = desc; r.ubi_num = req->dev_num; @@ -806,7 +813,7 @@ int ubi_get_info(libubi_t desc, struct ubi_info *info) struct dirent *dirent; struct libubi *lib = (struct libubi *)desc; - memset(info, '\0', sizeof(struct ubi_info)); + memset(info, 0, sizeof(struct ubi_info)); if (read_major(lib->ctrl_dev, &info->ctrl_major, &info->ctrl_minor)) { /* @@ -881,7 +888,7 @@ int ubi_mkvol(libubi_t desc, const char *node, struct ubi_mkvol_request *req) struct ubi_mkvol_req r; size_t n; - memset(&r, sizeof(struct ubi_mkvol_req), '\0'); + memset(&r, 0, sizeof(struct ubi_mkvol_req)); desc = desc; r.vol_id = req->vol_id; @@ -1034,7 +1041,7 @@ int ubi_get_dev_info1(libubi_t desc, int dev_num, struct ubi_dev_info *info) struct dirent *dirent; struct libubi *lib = (struct libubi *)desc; - memset(info, '\0', sizeof(struct ubi_dev_info)); + memset(info, 0, sizeof(struct ubi_dev_info)); info->dev_num = dev_num; if (!dev_present(lib, dev_num)) @@ -1137,7 +1144,7 @@ int ubi_get_vol_info1(libubi_t desc, int dev_num, int vol_id, struct libubi *lib = (struct libubi *)desc; char buf[50]; - memset(info, '\0', sizeof(struct ubi_vol_info)); + memset(info, 0, sizeof(struct ubi_vol_info)); info->dev_num = dev_num; info->vol_id = vol_id; diff --git a/ubi-utils/src/libubigen.c b/ubi-utils/src/libubigen.c index fddc1d8..a34963e 100644 --- a/ubi-utils/src/libubigen.c +++ b/ubi-utils/src/libubigen.c @@ -122,7 +122,7 @@ int ubigen_add_volume(const struct ubigen_info *ui, return errmsg("too large alignment %d, max is %d (LEB size)", vi->alignment, ui->leb_size); - memset(vtbl_rec, '\0', sizeof(struct ubi_vtbl_record)); + memset(vtbl_rec, 0, sizeof(struct ubi_vtbl_record)); tmp = (vi->bytes + ui->leb_size - 1) / ui->leb_size; vtbl_rec->reserved_pebs = cpu_to_be32(tmp); vtbl_rec->alignment = cpu_to_be32(vi->alignment); @@ -151,7 +151,7 @@ void ubigen_init_ec_hdr(const struct ubigen_info *ui, { uint32_t crc; - memset(hdr, '\0', sizeof(struct ubi_ec_hdr)); + memset(hdr, 0, sizeof(struct ubi_ec_hdr)); hdr->magic = cpu_to_be32(UBI_EC_HDR_MAGIC); hdr->version = ui->ubi_ver; @@ -183,7 +183,7 @@ static void init_vid_hdr(const struct ubigen_info *ui, { uint32_t crc; - memset(hdr, '\0', sizeof(struct ubi_vid_hdr)); + memset(hdr, 0, sizeof(struct ubi_vid_hdr)); hdr->magic = cpu_to_be32(UBI_VID_HDR_MAGIC); hdr->version = ui->ubi_ver; -- cgit v1.2.3