Commit 23829607 authored by Dan Carpenter's avatar Dan Carpenter Committed by Brian Norris
Browse files

mtd: docg3: off by one in doc_register_sysfs()



Smatch found a bug in the error handling:

	drivers/mtd/devices/docg3.c:1634 doc_register_sysfs()
	error: buffer overflow 'doc_sys_attrs' 4 <= 4

The problem is that if the very last device_create_file() fails, then we
are beyond the end of the array.  Actually, any time i == 3 then there
is a problem.  We can fix this an simplify the code at the same time by
moving the !ret conditions out of the for loops and using a goto
instead.

Signed-off-by: default avatarDan Carpenter <dan.carpenter@oracle.com>
Acked-by: default avatarRobert Jarzmik <robert.jarzmik@free.fr>
Signed-off-by: default avatarBrian Norris <computersforpeace@gmail.com>
parent 89c1702d
Loading
Loading
Loading
Loading
+16 −6
Original line number Diff line number Diff line
@@ -1620,20 +1620,30 @@ static struct device_attribute doc_sys_attrs[DOC_MAX_NBFLOORS][4] = {
static int doc_register_sysfs(struct platform_device *pdev,
			      struct docg3_cascade *cascade)
{
	int ret = 0, floor, i = 0;
	struct device *dev = &pdev->dev;
	int floor;
	int ret;
	int i;

	for (floor = 0; !ret && floor < DOC_MAX_NBFLOORS &&
		     cascade->floors[floor]; floor++)
		for (i = 0; !ret && i < 4; i++)
	for (floor = 0;
	     floor < DOC_MAX_NBFLOORS && cascade->floors[floor];
	     floor++) {
		for (i = 0; i < 4; i++) {
			ret = device_create_file(dev, &doc_sys_attrs[floor][i]);
	if (!ret)
			if (ret)
				goto remove_files;
		}
	}

	return 0;

remove_files:
	do {
		while (--i >= 0)
			device_remove_file(dev, &doc_sys_attrs[floor][i]);
		i = 4;
	} while (--floor >= 0);

	return ret;
}