[Date Prev][Date Next] [Thread Prev][Thread Next] [Date Index] [Thread Index]

Bug#773212: marked as done (unblock: 0xffff/0.6.1-1)



Your message dated Sat, 14 Mar 2015 11:20:15 +0100
with message-id <55040B5F.5040303@thykier.net>
and subject line Re: Bug#773212: unblock: 0xffff/0.6.1-1
has caused the Debian Bug report #773212,
regarding unblock: 0xffff/0.6.1-1
to be marked as done.

This means that you claim that the problem has been dealt with.
If this is not the case it is now your responsibility to reopen the
Bug report if necessary, and/or fix the problem forthwith.

(NB: If you are a system administrator and have no idea what this
message is talking about, this may indicate a serious mail system
misconfiguration somewhere. Please contact owner@bugs.debian.org
immediately.)


-- 
773212: http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=773212
Debian Bug Tracking System
Contact owner@bugs.debian.org with problems
--- Begin Message ---
Package: release.debian.org
Severity: normal
User: release.debian.org@packages.debian.org
Usertags: unblock

---Please unblock package 0xffff---

Note: I have not yet uploaded 0.6.1-1 to sid, but its available from
experimental. I sent a mail to debian-release, but have been request to
file an unblock bug instead.

So I've uploaded 0xffff 0.6.1-1 to experimental, which is a minor
upstream release with 90% bug fixes (some of them security relevant).
Since the diff is quite big I wanted to make sure, that the release
team is ok with the changes before uploading them to sid (and let them
transition to testing).

-- Sebastian

$ debdiff 0xffff_0.6-1.dsc 0xffff_0.6.1-1.dsc
diff -Nru 0xffff-0.6/config.mk 0xffff-0.6.1/config.mk
--- 0xffff-0.6/config.mk	2014-05-10 22:39:47.000000000 +0200
+++ 0xffff-0.6.1/config.mk	2014-11-18 23:23:23.000000000 +0100
@@ -1,4 +1,4 @@
-VERSION = 0.6
+VERSION = 0.6.1
 PREFIX = /usr/local
 
 # NetBSD stuff
diff -Nru 0xffff-0.6/debian/changelog 0xffff-0.6.1/debian/changelog
--- 0xffff-0.6/debian/changelog	2014-05-12 19:32:47.000000000 +0200
+++ 0xffff-0.6.1/debian/changelog	2014-12-11 21:53:03.000000000 +0100
@@ -1,3 +1,13 @@
+0xffff (0.6.1-1) experimental; urgency=medium
+
+  * New upstream release
+   - Contains a few security related fixes (memory corruptions & leaks)
+   - Support for -t (filter by type) for -e (dump images)
+   - reattach kernel driver
+   - minor fixes
+
+ -- Sebastian Reichel <sre@debian.org>  Thu, 11 Dec 2014 21:52:53 +0100
+
 0xffff (0.6-1) unstable; urgency=low
 
   * New upstream release
diff -Nru 0xffff-0.6/src/cold-flash.c 0xffff-0.6.1/src/cold-flash.c
--- 0xffff-0.6/src/cold-flash.c	2014-05-10 22:39:47.000000000 +0200
+++ 0xffff-0.6.1/src/cold-flash.c	2014-11-18 23:23:23.000000000 +0100
@@ -130,7 +130,7 @@
 	uint32_t size; /* 4 bytes - size of file */
 	uint32_t crc1; /* 4 bytes - crc32 of file */
 	uint32_t crc2; /* 4 bytes - crc32 of first 12 bytes of message */
-};
+} __attribute__((__packed__));
 
 #define XLOADER_MSG_TYPE_PING	0x6301326E
 #define XLOADER_MSG_TYPE_SEND	0x6302326E
diff -Nru 0xffff-0.6/src/fiasco.c 0xffff-0.6.1/src/fiasco.c
--- 0xffff-0.6/src/fiasco.c	2014-05-10 22:39:47.000000000 +0200
+++ 0xffff-0.6.1/src/fiasco.c	2014-11-18 23:23:23.000000000 +0100
@@ -192,9 +192,12 @@
 					if ( ! hwrevs[0] )
 						strcpy(hwrevs, hwrev);
 					else {
-						/* TODO: check if hwrevs has enough size */
-						strcat(hwrevs, ",");
-						strcat(hwrevs, hwrev);
+						size_t len1 = strlen(hwrevs);
+						size_t len2 = strlen(hwrev);
+						if ( len1 + len2 + 2 < sizeof(hwrevs) ) {
+							hwrevs[len1] = ',';
+							memcpy(hwrevs+len1+1, hwrev, len2+1);
+						}
 					}
 					VERBOSE("       hw revision: %s\n", hwrev);
 					pbuf += strlen(hwrev) + 1;
@@ -410,6 +413,7 @@
 			WRITE_OR_FAIL(file, fd, "2", 1); /* 2 - device & hwrevs */
 			WRITE_OR_FAIL(file, fd, &device_hwrevs_bufs[i][0], 1);
 			WRITE_OR_FAIL(file, fd, device_hwrevs_bufs[i]+1, ((uint8_t *)(device_hwrevs_bufs[i]))[0]);
+			/* FIXME: memory leak: device_hwrevs_bufs */
 		}
 		free(device_hwrevs_bufs);
 
@@ -449,9 +453,9 @@
 
 int fiasco_unpack(struct fiasco * fiasco, const char * dir) {
 
-	int fd = -1;
-	char * name = NULL;
-	char * layout_name = NULL;
+	int fd;
+	char * name;
+	char * layout_name;
 	struct image * image;
 	struct image_list * image_list;
 	uint32_t size;
@@ -480,6 +484,10 @@
 
 	while ( image_list ) {
 
+		fd = -1;
+		name = NULL;
+		layout_name = NULL;
+
 		image = image_list->image;
 
 		name = image_name_alloc_from_values(image);
@@ -492,9 +500,11 @@
 
 		if ( image->layout ) {
 
-			layout_name = calloc(1, strlen(name) + strlen(".layout") + 1);
-			if ( ! layout_name )
+			layout_name = calloc(1, strlen(name) + sizeof(".layout")-1 + 1);
+			if ( ! layout_name ) {
+				free(name);
 				ALLOC_ERROR_RETURN(-1);
+			}
 
 			sprintf(layout_name, "%s.layout", name);
 
@@ -508,21 +518,32 @@
 			fd = open(name, O_RDWR|O_CREAT|O_TRUNC, 0644);
 			if ( fd < 0 ) {
 				ERROR_INFO("Cannot create output file %s", name);
+				free(name);
+				free(layout_name);
 				return -1;
 			}
 		}
 
-		free(name);
-
 		image_seek(image, 0);
 		while ( 1 ) {
 			size = image_read(image, buf, sizeof(buf));
 			if ( size == 0 )
 				break;
-			WRITE_OR_FAIL(name, fd, buf, size);
+			if ( ! simulate ) {
+				if ( write(fd, buf, size) != (ssize_t)size ) {
+					ERROR_INFO_STR(name, "Cannot write %d bytes", size);
+					close(fd);
+					free(name);
+					free(layout_name);
+					return -1;
+				}
+			}
 		}
 
-		close(fd);
+		free(name);
+
+		if ( ! simulate )
+			close(fd);
 
 		if ( image->layout ) {
 
@@ -530,15 +551,24 @@
 				fd = open(layout_name, O_RDWR|O_CREAT|O_TRUNC, 0644);
 				if ( fd < 0 ) {
 					ERROR_INFO("Cannot create layout file %s", layout_name);
+					free(layout_name);
+					return -1;
+				}
+
+				size = strlen(image->layout);
+
+				if ( write(fd, image->layout, size) != (ssize_t)size ) {
+					ERROR_INFO_STR(layout_name, "Cannot write %d bytes", size);
+					close(fd);
+					free(layout_name);
 					return -1;
 				}
 			}
 
 			free(layout_name);
 
-			WRITE_OR_FAIL(layout_name, fd, image->layout, (int)strlen(image->layout));
-
-			close(fd);
+			if ( ! simulate )
+				close(fd);
 
 		}
 
diff -Nru 0xffff-0.6/src/image.c 0xffff-0.6.1/src/image.c
--- 0xffff-0.6/src/image.c	2014-05-10 22:39:47.000000000 +0200
+++ 0xffff-0.6.1/src/image.c	2014-11-18 23:23:23.000000000 +0100
@@ -88,14 +88,13 @@
 
 	if ( image->devices && image->devices->device && ! image->devices->hwrevs )
 		image->devices->hwrevs = hwrevs_alloc_from_string(hwrevs);
-	else
-		free(hwrevs);
 
 	if ( ! image->version )
 		image->version = version;
 	else
 		free(version);
 
+	free(hwrevs);
 	free(str);
 
 }
@@ -135,8 +134,10 @@
 		length += 1 + strlen(image->version);
 
 	name = calloc(1, length);
-	if ( ! name )
+	if ( ! name ) {
+		free(hwrevs);
 		ALLOC_ERROR_RETURN(NULL);
+	}
 
 	strcpy(name, type);
 	ptr = name + strlen(name);
diff -Nru 0xffff-0.6/src/local.c 0xffff-0.6.1/src/local.c
--- 0xffff-0.6/src/local.c	2014-05-10 22:39:47.000000000 +0200
+++ 0xffff-0.6.1/src/local.c	2014-11-18 23:23:23.000000000 +0100
@@ -127,9 +127,9 @@
 
 	while ( fgets(buf, sizeof(buf), file) ) {
 
-		if ( strncmp(buf, "Hardware", strlen("Hardware")) == 0 ) {
+		if ( strncmp(buf, "Hardware", sizeof("Hardware")-1) == 0 ) {
 
-			ptr = buf + strlen("Hardware");
+			ptr = buf + sizeof("Hardware")-1;
 
 			while ( ptr < buf + sizeof(buf) && *ptr > 0 && *ptr <= 32 )
 				++ptr;
@@ -316,21 +316,23 @@
 
 		while ( ( dirent = readdir(dir) ) ) {
 
-			snprintf(buf, sizeof(buf), "/sys/class/mmc_host/%s/slot_name", dirent->d_name);
+			if ( snprintf(buf, sizeof(buf), "/sys/class/mmc_host/%s/slot_name", dirent->d_name) <= 0 )
+				continue;
 
 			fd = open(buf, O_RDONLY);
 			if ( fd < 0 )
 				continue;
 
-			buf[0] = 0;
-			if ( read(fd, buf, sizeof(buf)) < 0 )
+			memset(buf, 0, sizeof(buf));
+			if ( read(fd, buf, sizeof(buf)-1) < 0 )
 				buf[0] = 0;
 			close(fd);
 
-			if ( strncmp(buf, "internal", strlen("internal")) != 0 )
+			if ( strncmp(buf, "internal", sizeof("internal")-1) != 0 )
 				continue;
 
-			snprintf(buf, sizeof(buf), "/sys/class/mmc_host/%s/%s:0001/", dirent->d_name, dirent->d_name);
+			if ( snprintf(buf, sizeof(buf), "/sys/class/mmc_host/%s/%s:0001/", dirent->d_name, dirent->d_name) <= 0 )
+				continue;
 
 			dir2 = opendir(buf);
 			if ( ! dir2 )
@@ -338,10 +340,11 @@
 
 			while ( ( dirent2 = readdir(dir2) ) ) {
 
-				if ( strncmp(dirent2->d_name, "block:mmcblk", strlen("block:mmcblk")) != 0 )
+				if ( strncmp(dirent2->d_name, "block:mmcblk", sizeof("block:mmcblk")-1) != 0 )
 					continue;
 
-				snprintf(buf, sizeof(buf), "/sys/class/mmc_host/%s/%s:0001/%s/dev", dirent->d_name, dirent->d_name, dirent2->d_name);
+				if ( snprintf(buf, sizeof(buf), "/sys/class/mmc_host/%s/%s:0001/%s/dev", dirent->d_name, dirent->d_name, dirent2->d_name) <= 0 )
+					continue;
 
 				f = fopen(buf, "r");
 				if ( ! f )
@@ -385,7 +388,8 @@
 
 		while ( ( dirent = readdir(dir) ) ) {
 
-			snprintf(buf, sizeof(buf), "/dev/%s", dirent->d_name);
+			if ( snprintf(buf, sizeof(buf), "/dev/%s", dirent->d_name) <= 0 )
+				continue;
 
 			if ( stat(buf, &st) != 0 )
 				continue;
@@ -410,7 +414,7 @@
 
 		VERBOSE("Detected internal mmc device: '%s'\n", blk);
 
-		strncat(blk, "p1", sizeof(blk));
+		strncat(blk, "p1", sizeof(blk)-strlen(blk)-1);
 
 		printf("Using MyDocs mmc device: '%s'\n", blk);
 
@@ -457,6 +461,10 @@
 		if ( addr[nlen-1] != 0xFF )
 			break;
 
+	for ( ; nlen > 0; --nlen )
+		if ( addr[nlen-1] != 0x00 )
+			break;
+
 	if ( image == IMAGE_MMC )
 		align = 8;
 	else
@@ -532,7 +540,7 @@
 
 int local_get_rd_mode(void) {
 
-	if ( strncmp(rd_mode, "master", strlen("master")) == 0 )
+	if ( strncmp(rd_mode, "master", sizeof("master")-1) == 0 )
 		return 1;
 	else
 		return 0;
@@ -551,8 +559,8 @@
 
 	const char * ptr;
 
-	if ( strncmp(rd_mode, "master", strlen("master")) == 0 )
-		ptr = rd_mode + strlen("master");
+	if ( strncmp(rd_mode, "master", sizeof("master")-1) == 0 )
+		ptr = rd_mode + sizeof("master")-1;
 	else
 		ptr = rd_mode;
 
diff -Nru 0xffff-0.6/src/main.c 0xffff-0.6.1/src/main.c
--- 0xffff-0.6/src/main.c	2014-05-10 22:39:47.000000000 +0200
+++ 0xffff-0.6.1/src/main.c	2014-11-18 23:23:23.000000000 +0100
@@ -53,8 +53,8 @@
 		" -f              flash all specified images\n"
 		" -c              cold flash 2nd and secondary images\n"
 		" -x [/dev/mtd]   check for bad blocks on mtd device (default: all)\n"
-		" -E file         dump all device images to one fiasco image, see -t\n"
-		" -e [dir]        dump all device images to directory, see -t (default: current)\n"
+		" -E file         dump all device images to one fiasco image\n"
+		" -e [dir]        dump all device images (or one -t) to directory (default: current)\n"
 		"\n"
 
 		"Device configuration:\n"
@@ -84,7 +84,7 @@
 		"\n"
 
 		"Image filters:\n"
-		" -t types        filter images by type\n"
+		" -t type         filter images by type\n"
 		" -d dev          filter images by device\n"
 		" -w hw           filter images by HW revision\n"
 		"\n"
@@ -210,7 +210,7 @@
 			exit(1);
 		}
 		lseek(fd, 0, SEEK_SET);
-		layout = malloc(len);
+		layout = malloc(len+1);
 		if ( ! layout ) {
 			ALLOC_ERROR();
 			exit(1);
@@ -219,6 +219,8 @@
 			ERROR_INFO("Cannot read %lu bytes from layout file %s", len, layout_file);
 			exit(1);
 		}
+		layout[len] = 0;
+		close(fd);
 	}
 
 	image = image_alloc_from_file(file, type, device, hwrevs, version, layout);
@@ -661,6 +663,9 @@
 			goto clean;
 		}
 		filter_images_by_type(type, &image_first);
+		/* make sure that fiasco_in has valid images */
+		if ( fiasco_in )
+			fiasco_in->first = image_first;
 	}
 
 	/* filter images by device */
@@ -672,11 +677,18 @@
 			goto clean;
 		}
 		filter_images_by_device(device, &image_first);
+		/* make sure that fiasco_in has valid images */
+		if ( fiasco_in )
+			fiasco_in->first = image_first;
 	}
 
 	/* filter images by hwrev */
-	if ( filter_hwrev )
+	if ( filter_hwrev ) {
 		filter_images_by_hwrev(atoi(filter_hwrev_arg), &image_first);
+		/* make sure that fiasco_in has valid images */
+		if ( fiasco_in )
+			fiasco_in->first = image_first;
+	}
 
 	/* reorder images for flashing (first x-loader, second secondary) */
 	/* set 2nd and secondary images for cold-flashing */
@@ -740,11 +752,29 @@
 			image_ptr = next;
 		}
 
+		/* make sure that fiasco_in has valid images */
+		if ( fiasco_in )
+			fiasco_in->first = image_first;
+
 	}
 
-	/* make sure that fiasco_in has valid images*/
-	if ( fiasco_in )
-		fiasco_in->first = image_first;
+	/* remove 2nd image when doing normal flash */
+	if ( dev_flash ) {
+		image_ptr = image_first;
+		while ( image_ptr ) {
+			struct image_list * next = image_ptr->next;
+			if ( image_ptr->image->type == IMAGE_2ND ) {
+				if ( image_ptr == image_first )
+					image_first = next;
+				image_list_del(image_ptr);
+			}
+			image_ptr = next;
+		}
+
+		/* make sure that fiasco_in has valid images */
+		if ( fiasco_in )
+			fiasco_in->first = image_first;
+	}
 
 	/* identify images */
 	if ( image_ident ) {
@@ -782,8 +812,9 @@
 			WARNING("Removing unknown image (specified by %s %s)", image_ptr->image->orig_filename ? "file" : "fiasco", image_ptr->image->orig_filename ? image_ptr->image->orig_filename : "image");
 			if ( image_ptr == image_first )
 				image_first = next;
-			image_list_unlink(image_ptr);
-			free(image_ptr);
+			if ( fiasco_in && image_ptr == fiasco_in->first )
+				fiasco_in->first = fiasco_in->first->next;
+			image_list_del(image_ptr);
 		}
 		image_ptr = next;
 	}
@@ -983,6 +1014,8 @@
 				filter_images_by_device(dev->detected_device, &image_first);
 			if ( detected_hwrev )
 				filter_images_by_hwrev(dev->detected_hwrev, &image_first);
+			if ( fiasco_in && ( detected_device || detected_hwrev ) )
+				fiasco_in->first = image_first;
 
 			/* set kernel and initfs images for loading */
 			if ( dev_load ) {
@@ -1047,8 +1080,7 @@
 					if ( fiasco_in && image_kernel == fiasco_in->first )
 						fiasco_in->first = fiasco_in->first->next;
 
-					image_list_unlink(image_kernel);
-					free(image_kernel);
+					image_list_del(image_kernel);
 					image_kernel = NULL;
 				}
 
@@ -1059,11 +1091,10 @@
 
 					if ( image_initfs == image_first )
 						image_first = image_first->next;
-					if ( fiasco_in && image_kernel == fiasco_in->first )
+					if ( fiasco_in && image_initfs == fiasco_in->first )
 						fiasco_in->first = fiasco_in->first->next;
 
-					image_list_unlink(image_initfs);
-					free(image_initfs);
+					image_list_del(image_initfs);
 					image_initfs = NULL;
 				}
 			}
@@ -1079,11 +1110,10 @@
 
 					if ( image_ptr == image_first )
 						image_first = image_first->next;
-					if ( fiasco_in && image_kernel == fiasco_in->first )
+					if ( fiasco_in && image_ptr == fiasco_in->first )
 						fiasco_in->first = fiasco_in->first->next;
 
-					image_list_unlink(image_ptr);
-					free(image_ptr);
+					image_list_del(image_ptr);
 					image_ptr = next;
 				}
 			}
@@ -1175,9 +1205,21 @@
 						buf[0] = 0;
 				}
 
-				for ( i = 0; i < IMAGE_COUNT; ++i )
-					if ( image_tmp_name(i) )
-						dev_dump_image(dev, i, image_tmp_name(i));
+				if ( filter_type ) {
+					enum image_type type = image_type_from_string(filter_type_arg);
+					if ( ! type || ! image_tmp_name(type) ) {
+						ERROR("Specified unknown image type for filtering: %s", filter_type_arg);
+						ret = 1;
+						goto clean;
+					}
+					ret = dev_dump_image(dev, type, image_tmp_name(type));
+					if ( ret != 0 )
+						goto clean;
+				} else {
+					for ( i = 0; i < IMAGE_COUNT; ++i )
+						if ( image_tmp_name(i) )
+							dev_dump_image(dev, i, image_tmp_name(i));
+				}
 
 				if ( buf[0] )
 					if ( chdir(buf) < 0 )
@@ -1196,7 +1238,8 @@
 					if ( ! image_tmp_name(i) )
 						continue;
 
-					sprintf(buf, "%hd", dev->detected_hwrev);
+					buf[0] = 0;
+					snprintf(buf, sizeof(buf), "%hd", dev->detected_hwrev);
 
 					switch ( i ) {
 						case IMAGE_2ND:
@@ -1298,14 +1341,16 @@
 							break;
 					}
 
-					sprintf(buf, "%s-%s:%hd_%s", image_type_to_string(i), device_to_string(dev->detected_device), dev->detected_hwrev, ptr);
+					buf[0] = 0;
+					snprintf(buf, sizeof(buf), "%s-%s:%hd_%s", image_type_to_string(i), device_to_string(dev->detected_device), dev->detected_hwrev, ptr);
 					printf("Renaming %s image file to %s...\n", image_type_to_string(i), buf);
 
 					if ( rename(image_tmp_name(i), buf) < 0 ) {
 
 						ERROR_INFO("Renaming failed");
 
-						sprintf(buf, "%s-%s_%s", image_type_to_string(i), device_to_string(dev->detected_device), ptr);
+						buf[0] = 0;
+						snprintf(buf, sizeof(buf), "%s-%s_%s", image_type_to_string(i), device_to_string(dev->detected_device), ptr);
 						printf("Trying to rename %s image file to %s...\n", image_type_to_string(i), buf);
 
 						if ( rename(image_tmp_name(i), buf) < 0 )
diff -Nru 0xffff-0.6/src/Makefile 0xffff-0.6.1/src/Makefile
--- 0xffff-0.6/src/Makefile	2014-05-10 22:39:47.000000000 +0200
+++ 0xffff-0.6.1/src/Makefile	2014-11-18 23:23:23.000000000 +0100
@@ -31,10 +31,10 @@
 	mv $@.tmp $@
 
 libusb-sniff-32.so: libusb-sniff.c $(DEPENDS)
-	$(CC) $(CFLAGS) $(LDFLAGS) -fPIC -ldl -shared -m32 -o $@ $<
+	$(CC) $(CFLAGS) $(LDFLAGS) -fPIC $< -ldl -shared -m32 -o $@
 
 libusb-sniff-64.so: libusb-sniff.c $(DEPENDS)
-	$(CC) $(CFLAGS) $(LDFLAGS) -fPIC -ldl -shared -m64 -o $@ $<
+	$(CC) $(CFLAGS) $(LDFLAGS) -fPIC $< -ldl -shared -m64 -o $@
 
 %.o: %.c $(DEPENDS)
 	$(CROSS_CC) $(CFLAGS) $(CPPFLAGS) -c -o $@ $<
diff -Nru 0xffff-0.6/src/nolo.c 0xffff-0.6.1/src/nolo.c
--- 0xffff-0.6/src/nolo.c	2014-05-10 22:39:47.000000000 +0200
+++ 0xffff-0.6.1/src/nolo.c	2014-11-18 23:23:23.000000000 +0100
@@ -84,12 +84,14 @@
 
 	char buf[2048];
 	size_t i, count;
+	int ret;
 
 	for ( count = 0; count < 20; ++count ) {
 
 		memset(buf, 0, sizeof(buf));
 
-		if ( usb_control_msg(dev->udev, NOLO_QUERY, NOLO_ERROR_LOG, 0, 0, buf, sizeof(buf), 2000) <= 0 )
+		ret = usb_control_msg(dev->udev, NOLO_QUERY, NOLO_ERROR_LOG, 0, 0, buf, sizeof(buf), 2000);
+		if ( ret < 0 )
 			break;
 
 		if ( ! only_clear ) {
@@ -103,6 +105,9 @@
 
 		}
 
+		if ( (size_t)ret < sizeof(buf) )
+			break;
+
 	}
 
 }
@@ -176,14 +181,14 @@
 	if ( strlen(str) > 500 )
 		return -1;
 
-	sprintf(buf, "version:%s", str);
+	if ( sprintf(buf, "version:%s", str) <= 0 )
+		return -1;
 
 	ret = nolo_get_string(dev, buf, out, size);
-
-	nolo_error_log(dev, 1);
-
-	if ( ret < 0 )
+	if ( ret < 0 ) {
+		nolo_error_log(dev, 1);
 		return ret;
+	}
 
 	if ( ! out[0] )
 		return -1;
@@ -311,7 +316,7 @@
 		if ( bufs ) {
 
 			memset(buf, 0, sizeof(buf));
-			snprintf(buf, 8, "%d", dev->hwrev);
+			snprintf(buf, 8+1, "%d", dev->hwrev);
 
 			for ( i = 0; bufs[i]; ++i ) {
 				len = ((uint8_t*)bufs[i])[0];
@@ -418,8 +423,8 @@
 	unsigned long long int part;
 	unsigned long long int total;
 	unsigned long long int last_total;
-	char status[20];
 	char buf[128];
+	char * ptr;
 
 	if ( image->type == IMAGE_ROOTFS )
 		flash = 1;
@@ -463,7 +468,7 @@
 		if ( nolo_get_string(dev, "cmt:status", buf, sizeof(buf)) < 0 )
 			NOLO_ERROR_RETURN("cmt:status failed", -1);
 
-		if ( strncmp(buf, "idle", strlen("idle")) == 0 )
+		if ( strncmp(buf, "idle", sizeof("idle")-1) == 0 )
 			state = 4;
 		else
 			printf("Erasing CMT...\n");
@@ -475,7 +480,7 @@
 				NOLO_ERROR_RETURN("cmt:status failed", -1);
 			}
 
-			if ( strncmp(buf, "finished", strlen("finished")) == 0 ) {
+			if ( strncmp(buf, "finished", sizeof("finished")-1) == 0 ) {
 
 				if ( state <= 0 ) {
 					printf_progressbar(last_total, last_total);
@@ -490,18 +495,29 @@
 
 				state = 4;
 
+			} else if ( strncmp(buf, "error", sizeof("error")-1) == 0 ) {
+
+				PRINTF_ERROR_RETURN("cmt:status error", -1);
+
 			} else {
 
-				if ( sscanf(buf, "%s:%llu/%llu", status, &part, &total) != 3 )
+				ptr = strchr(buf, ':');
+				if ( ! ptr )
+					PRINTF_ERROR_RETURN("cmt:status unknown", -1);
+
+				*ptr = 0;
+				ptr++;
+
+				if ( sscanf(ptr, "%llu/%llu", &part, &total) != 2 )
 					PRINTF_ERROR_RETURN("cmt:status unknown", -1);
 
-				if ( strcmp(status, "program") == 0 && state <= 0 ) {
+				if ( strcmp(buf, "program") == 0 && state <= 0 ) {
 					printf_progressbar(last_total, last_total);
 					printf("Done\n");
 					state = 1;
 				}
 
-				if ( strcmp(status, "program") == 0 && state <= 1 ) {
+				if ( strcmp(buf, "program") == 0 && state <= 1 ) {
 					printf("Programming CMT...\n");
 					state = 2;
 				}
@@ -509,12 +525,12 @@
 				printf_progressbar(part, total);
 				last_total = total;
 
-				if ( strcmp(status, "erase") == 0 && state <= 0 && part == total ) {
+				if ( strcmp(buf, "erase") == 0 && state <= 0 && part == total ) {
 					printf("Done\n");
 					state = 1;
 				}
 
-				if ( strcmp(status, "program") == 0 && state <= 2 && part == total ) {
+				if ( strcmp(buf, "program") == 0 && state <= 2 && part == total ) {
 					printf("Done\n");
 					state = 3;
 				}
@@ -536,9 +552,9 @@
 	int size = 0;
 	int mode = NOLO_BOOT_MODE_NORMAL;
 
-	if ( cmdline && strncmp(cmdline, "update", strlen("update")) == 0 && cmdline[strlen("update")] <= 32 ) {
+	if ( cmdline && strncmp(cmdline, "update", sizeof("update")-1) == 0 && cmdline[sizeof("update")-1] <= 32 ) {
 		mode = NOLO_BOOT_MODE_UPDATE;
-		cmdline += strlen("update");
+		cmdline += sizeof("update")-1;
 		if ( *cmdline ) ++cmdline;
 		while ( *cmdline && *cmdline <= 32 )
 			++cmdline;
@@ -763,7 +779,7 @@
 
 	char buf[9];
 	memset(buf, 0, sizeof(buf));
-	snprintf(buf, 8, "%d", hwrev);
+	snprintf(buf, sizeof(buf), "%d", hwrev);
 	printf("Setting HW revision to: %s\n", buf);
 	return nolo_set_string(dev, "hw_rev", buf);
 
diff -Nru 0xffff-0.6/src/printf-utils.c 0xffff-0.6.1/src/printf-utils.c
--- 0xffff-0.6/src/printf-utils.c	2014-05-10 22:39:47.000000000 +0200
+++ 0xffff-0.6.1/src/printf-utils.c	2014-11-18 23:23:23.000000000 +0100
@@ -39,7 +39,7 @@
 	int tmp, cols = 80;
 
 	/* percentage calculation */
-	pc = (int)(part*100/total);
+	pc = total==0?100:(int)(part*100/total);
 	(pc<0)?pc=0:(pc>100)?pc=100:0;
 
 	PRINTF_BACK();
diff -Nru 0xffff-0.6/src/usb-device.c 0xffff-0.6.1/src/usb-device.c
--- 0xffff-0.6/src/usb-device.c	2014-05-10 22:39:47.000000000 +0200
+++ 0xffff-0.6.1/src/usb-device.c	2014-11-18 23:23:23.000000000 +0100
@@ -27,6 +27,10 @@
 
 #include <usb.h>
 
+#ifdef LIBUSB_HAS_DETACH_KERNEL_DRIVER_NP
+#include <sys/ioctl.h>
+#endif
+
 #include "global.h"
 #include "device.h"
 #include "usb-device.h"
@@ -73,6 +77,25 @@
 
 }
 
+static void usb_reattach_kernel_driver(usb_dev_handle * udev, int interface) {
+
+#ifdef LIBUSB_HAS_DETACH_KERNEL_DRIVER_NP
+	struct {
+		int ifno;
+		int ioctl_code;
+		void * data;
+	} command = {
+		.ifno = interface,
+		.ioctl_code = _IO('U', 23),
+		.data = NULL,
+	};
+
+	usb_release_interface(udev, interface);
+	ioctl(*((int *)udev), _IOWR('U', 18, command), &command);
+#endif
+
+}
+
 static void usb_descriptor_info_print(usb_dev_handle * udev, struct usb_device * dev, char * product, size_t size) {
 
 	char buf[1024];
@@ -145,6 +168,7 @@
 			if ( usb_claim_interface(udev, usb_devices[i].interface) < 0 ) {
 				PRINTF_ERROR("usb_claim_interface failed");
 				fprintf(stderr, "\n");
+				usb_reattach_kernel_driver(udev, usb_devices[i].interface);
 				usb_close(udev);
 				return NULL;
 			}
@@ -154,6 +178,7 @@
 				if ( usb_set_altinterface(udev, usb_devices[i].alternate) < 0 ) {
 					PRINTF_ERROR("usb_claim_interface failed");
 					fprintf(stderr, "\n");
+					usb_reattach_kernel_driver(udev, usb_devices[i].interface);
 					usb_close(udev);
 					return NULL;
 				}
@@ -164,6 +189,7 @@
 				if ( usb_set_configuration(udev, usb_devices[i].configuration) < 0 ) {
 					PRINTF_ERROR("usb_set_configuration failed");
 					fprintf(stderr, "\n");
+					usb_reattach_kernel_driver(udev, usb_devices[i].interface);
 					usb_close(udev);
 					return NULL;
 				}
@@ -172,6 +198,7 @@
 			ret = calloc(1, sizeof(struct usb_device_info));
 			if ( ! ret ) {
 				ALLOC_ERROR();
+				usb_reattach_kernel_driver(udev, usb_devices[i].interface);
 				usb_close(udev);
 				return NULL;
 			}
@@ -197,7 +224,9 @@
 				if ( ! *device ) {
 					ERROR("Device mishmash");
 					fprintf(stderr, "\n");
+					usb_reattach_kernel_driver(udev, usb_devices[i].interface);
 					usb_close(udev);
+					free(ret);
 					return NULL;
 				}
 			}
@@ -308,6 +337,7 @@
 
 void usb_close_device(struct usb_device_info * dev) {
 
+	usb_reattach_kernel_driver(dev->udev, dev->flash_device->interface);
 	usb_close(dev->udev);
 	free(dev);
 
diff -Nru 0xffff-0.6/.travis.yml 0xffff-0.6.1/.travis.yml
--- 0xffff-0.6/.travis.yml	1970-01-01 01:00:00.000000000 +0100
+++ 0xffff-0.6.1/.travis.yml	2014-11-18 23:23:23.000000000 +0100
@@ -0,0 +1,20 @@
+language: c
+compiler:
+  - gcc
+before_install:
+  - sudo apt-get update -qq
+  - sudo apt-get install -qq -y libusb-dev
+script: if [ ${COVERITY_SCAN_BRANCH} != 1 ]; then make ; fi
+
+env:
+  global:
+   - secure: "JdUp+xFykPZoYA4aRfmYk2CtilLapniQllWPKo2dDdJd1vzdawfTvVxIAKjy7ac9RKwZzg3Chq3RsMEXPv8BtaLbssw266C7RDLMgjacl1eFLcmGRj/Gkk9peDSZ6vVdGEcA2j+6KDSfpCa/XjFjvOufZOgKw6m+3+d0A4G45SI="
+
+addons:
+  coverity_scan:
+    project:
+      name: "pali/0xFFFF"
+      description: "Build submitted via Travis CI"
+    notification_email: pali.rohar@gmail.com
+    build_command: "make"
+    branch_pattern: master

--- End Message ---
--- Begin Message ---
On 2014-12-30 00:20, Jonathan Wiltshire wrote:
> I have almost no familiarity with this package, so as maintainer and upstream
> you have the advantage of me. I suggest you work it out between
> yourselves and come back to me with a plan.
> 
> For the sake of clarity your options are:
> 
>  - migrate the new upstream if it's more practical than backporting, which
>    is an option I'm certainly open to
>  - backport actual fixes
>  - remove the package from Jessie
> 

Hi,

There has been no updates on this, so I am now closing this on the
assumption that it timed out / is no longer relevant.  If it is still
relevant, please reopen it with additional information as requested above.

Thanks,
~Niels

--- End Message ---

Reply to: