changeset 65:225dc1d9f2f1

ftee-decode program written, compiles
author Mychaela Falconia <falcon@freecalypso.org>
date Tue, 12 Sep 2023 22:23:30 +0000
parents ca2250b4833d
children 85256d5aa559
files .hgignore fteeprom/Makefile fteeprom/ftee-decode.c
diffstat 3 files changed, 139 insertions(+), 2 deletions(-) [+]
line wrap: on
line diff
--- a/.hgignore	Tue Sep 12 20:17:07 2023 +0000
+++ b/.hgignore	Tue Sep 12 22:23:30 2023 +0000
@@ -10,6 +10,7 @@
 
 ^duart28/fc-duart28-conf$
 
+^fteeprom/ftee-decode$
 ^fteeprom/ftee-gen2232c$
 ^fteeprom/ftee-gen2232h$
 ^fteeprom/ftee-gen232r$
--- a/fteeprom/Makefile	Tue Sep 12 20:17:07 2023 +0000
+++ b/fteeprom/Makefile	Tue Sep 12 22:23:30 2023 +0000
@@ -1,7 +1,7 @@
 CC=	gcc
 CFLAGS=	-O2
-PROGS=	ftee-gen2232c ftee-gen2232h ftee-gen232r ftee-mkblank fteeprom-erase \
-	fteeprom-prog fteeprom-read
+PROGS=	ftee-decode ftee-gen2232c ftee-gen2232h ftee-gen232r ftee-mkblank \
+	fteeprom-erase fteeprom-prog fteeprom-read
 LIBS=	../libftmini/libftmini.a ../libuwrap/libuwrap.a
 
 INSTALL_PREFIX=	/opt/freecalypso
@@ -10,6 +10,9 @@
 
 all:	${PROGS}
 
+ftee-decode:	ftee-decode.o read_eeprom_image.o
+	${CC} ${CFLAGS} -o $@ $@.o read_eeprom_image.o
+
 ftee-gen2232c:	ftee-gen2232c.o filesearch.o
 	${CC} ${CFLAGS} -o $@ $@.o filesearch.o
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/fteeprom/ftee-decode.c	Tue Sep 12 22:23:30 2023 +0000
@@ -0,0 +1,133 @@
+/*
+ * This program reads an FTDI EEPROM image from a file (or from stdin)
+ * and performs some basic decoding on it.  Only the part of the EEPROM
+ * structure that is common for all chips is looked at, and only very
+ * shallow decoding is performed, without differentiating by FTDI chip
+ * type.  Compared to simply studying EEPROM images in raw hex, the main
+ * utility of this program is decoding and displaying the three textual
+ * ID strings.
+ */
+
+#include <sys/types.h>
+#include <string.h>
+#include <strings.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+extern unsigned eeprom_size;
+extern u_short eeprom[256];
+
+static unsigned useful_size;
+
+static int
+verify_eeprom_chksum()
+{
+	u_short chksum = 0xAAAA;
+	unsigned n;
+
+	for (n = 0; n < useful_size; n++) {
+		chksum ^= eeprom[n];
+		chksum = (chksum << 1) | (chksum >> 15);
+	}
+	return (chksum == 0);
+}
+
+static void
+show_string_desc(headline, ptr_word)
+	char *headline;
+	unsigned ptr_word;
+{
+	unsigned start_byte, desc_len;
+	unsigned start_word, total_words;
+	unsigned head_word, nchars;
+	u_short *sp;
+	unsigned n, uni;
+
+	if (!ptr_word) {
+		printf("%s NULL\n", headline);
+		return;
+	}
+	if (ptr_word & 0x0101) {
+inv:		printf("%s INVALID\n", headline);
+		return;
+	}
+	start_byte = ptr_word & 0xFF;
+	desc_len = ptr_word >> 8;
+	if (useful_size == 64)
+		start_byte &= 0x7F;
+	start_word = start_byte >> 1;
+	total_words = desc_len >> 1;
+	if (start_word < 10)
+		goto inv;
+	if (total_words < 1)
+		goto inv;
+	if (start_word + total_words >= useful_size)
+		goto inv;
+	head_word = eeprom[start_word];
+	if ((head_word & 0xFF) != desc_len)
+		goto inv;
+	if ((head_word >> 8) != 0x03)
+		goto inv;
+	nchars = total_words - 1;
+	printf("%s \"", headline);
+	sp = eeprom + start_word + 1;
+	for (n = 0; n < nchars; n++) {
+		uni = *sp++;
+		if (uni < 0x20 || uni > 0x7E) {
+			printf("\\u%04X", uni);
+			continue;
+		}
+		if (uni == '"' || uni == '\\')
+			putchar('\\');
+		putchar(uni);
+	}
+	putchar('"');
+	putchar('\n');
+}
+
+main(argc, argv)
+	char **argv;
+{
+	if (argc != 2) {
+		fprintf(stderr, "usage: %s eeprom-image-file\n", argv[0]);
+		exit(1);
+	}
+	if (strcmp(argv[1], "-"))
+		read_eeprom_from_file(argv[1]);
+	else
+		read_eeprom_from_stdin();
+	switch (eeprom_size) {
+	case 64:
+		printf("EEPROM size: 128 bytes (93C46 or FT232R)\n");
+		useful_size = 64;
+		break;
+	case 128:
+		printf("EEPROM size: 256 bytes (93C56)\n");
+		useful_size = 128;
+		break;
+	case 256:
+		printf("EEPROM size: 512 bytes (93C66)\n");
+		useful_size = 128;
+		break;
+	default:
+		fprintf(stderr,
+			"BUG: invalid EEPROM size not caught earlier\n");
+		exit(1);
+	}
+	printf("EEPROM checksum is %s\n",
+		verify_eeprom_chksum() ? "good" : "BAD!");
+	printf("FTDI byte 00: 0x%02X\n", eeprom[0] & 0xFF);
+	printf("FTDI byte 01: 0x%02X\n", eeprom[0] >> 8);
+	printf("idVendor:     0x%04X\n", eeprom[1]);
+	printf("idProduct:    0x%04X\n", eeprom[2]);
+	printf("bcdDevice:    0x%04X\n", eeprom[3]);
+	printf("bmAttributes: 0x%02X\n", eeprom[4] & 0xFF);
+	printf("bMaxPower:    %u mA\n", (eeprom[4] >> 8) * 2);
+	printf("FTDI byte 0A: 0x%02X\n", eeprom[5] & 0xFF);
+	printf("FTDI byte 0B: 0x%02X\n", eeprom[5] >> 8);
+	printf("bcdUSB word:  0x%04X\n", eeprom[6]);
+	show_string_desc("Manuf string:  ", eeprom[7]);
+	show_string_desc("Product string:", eeprom[8]);
+	show_string_desc("Serial# string:", eeprom[9]);
+	exit(0);
+}