[flashrom] [commit] r769 - trunk

svn at flashrom.org svn at flashrom.org
Sun Nov 22 02:33:40 CET 2009


Author: hailfinger
Date: 2009-11-22 02:33:40 +0100 (Sun, 22 Nov 2009)
New Revision: 769

Modified:
   trunk/ft2232_spi.c
Log:
Pretty much everybody who used the FT2232 SPI driver in flashrom had
problems with incorrect reads from time to time.
One reason was that the hardware is pretty timing sensitive even for
reads.

The other reason was that the code silently ignored errors. This patch
doesn't add any error recovery, but it will emit error messages if
FT2232 communication goes wrong. That allows us to track down errors
without investing hours in driver debugging.

Thanks to Jeremy Buseman <naviathan at gmail.com> for testing. He found
out that certain libftdi/libusb/kernel/hardware combinations drop
some bytes without returning any error codes.

Signed-off-by: Carl-Daniel Hailfinger <c-d.hailfinger.devel.2006 at gmx.net>
Acked-by: Paul Fox <pgf at laptop.org>


Modified: trunk/ft2232_spi.c
===================================================================
--- trunk/ft2232_spi.c	2009-11-21 11:02:48 UTC (rev 768)
+++ trunk/ft2232_spi.c	2009-11-22 01:33:40 UTC (rev 769)
@@ -198,7 +198,8 @@
 {
 	struct ftdi_context *ftdic = &ftdic_context;
 	static unsigned char *buf = NULL;
-	int i = 0, ret = 0;
+	/* failed is special. We use bitwise ops, but it is essentially bool. */
+	int i = 0, ret = 0, failed = 0;
 
 	if (writecnt > 65536 || readcnt > 65536)
 		return SPI_INVALID_LENGTH;
@@ -237,6 +238,11 @@
 		buf[i++] = (readcnt - 1) & 0xff;
 		buf[i++] = ((readcnt - 1) >> 8) & 0xff;
 		ret = send_buf(ftdic, buf, i);
+		failed = ret;
+		/* We can't abort here, we still have to deassert CS#. */
+		if (ret)
+			fprintf(stderr, "send_buf failed before read: %i\n",
+				ret);
 		i = 0;
 		if (ret == 0) {
 			/*
@@ -245,6 +251,10 @@
 			 * command. We may be scheduled out etc.
 			 */
 			ret = get_buf(ftdic, readarr, readcnt);
+			failed |= ret;
+			/* We can't abort here either. */
+			if (ret)
+				fprintf(stderr, "get_buf failed: %i\n", ret);
 		}
 	}
 
@@ -252,10 +262,12 @@
 	buf[i++] = SET_BITS_LOW;
 	buf[i++] = CS_BIT;
 	buf[i++] = 0x0b;
-	if (send_buf(ftdic, buf, i))
-		return -1;
+	ret = send_buf(ftdic, buf, i);
+	failed |= ret;
+	if (ret)
+		fprintf(stderr, "send_buf failed at end: %i\n", ret);
 
-	return ret;
+	return failed ? -1 : 0;
 }
 
 int ft2232_spi_read(struct flashchip *flash, uint8_t *buf, int start, int len)





More information about the flashrom mailing list