[svn-commits] tzafrir: branch tools/2.2 r7621 - in /tools/branches/2.2: ./ xpp/ xpp/perl_mo...

SVN commits to the Digium repositories svn-commits at lists.digium.com
Sun Nov 22 05:48:42 CST 2009


Author: tzafrir
Date: Sun Nov 22 05:48:40 2009
New Revision: 7621

URL: http://svnview.digium.com/svn/dahdi?view=rev&rev=7621
Log:
xpp: MPP protocol v.1.4

* New firmware loading protocol
  - Older one (1.3) is still supported for now
* Support loading firmwares from Astribanks with a minimal firmware
  (1163)
* astribank_tool -Q: always query, regardless of verbosity level

xpp rev: up to 7559

Merged revisions 7609 via svnmerge from 
https://origsvn.digium.com/svn/dahdi/tools/trunk

Modified:
    tools/branches/2.2/   (props changed)
    tools/branches/2.2/xpp/astribank_hexload.c
    tools/branches/2.2/xpp/astribank_tool.8
    tools/branches/2.2/xpp/astribank_tool.c
    tools/branches/2.2/xpp/astribank_usb.h
    tools/branches/2.2/xpp/mpp.h
    tools/branches/2.2/xpp/mpp_funcs.c
    tools/branches/2.2/xpp/mpp_funcs.h
    tools/branches/2.2/xpp/perl_modules/Dahdi/Hardware/USB.pm
    tools/branches/2.2/xpp/perl_modules/Dahdi/Xpp/Mpp.pm

Propchange: tools/branches/2.2/
------------------------------------------------------------------------------
--- svnmerge-integrated (original)
+++ svnmerge-integrated Sun Nov 22 05:48:40 2009
@@ -1,1 +1,1 @@
-/tools/trunk:1-6678,6823,6829-6830,6832-6833,6835,6837-6886,6889-6982,6985-6998,7000-7011,7013-7042,7044,7046-7131,7133,7135-7136,7139-7217,7220-7255,7257-7262,7264-7332,7334-7460,7462,7464-7476,7596
+/tools/trunk:1-6678,6823,6829-6830,6832-6833,6835,6837-6886,6889-6982,6985-6998,7000-7011,7013-7042,7044,7046-7131,7133,7135-7136,7139-7217,7220-7255,7257-7262,7264-7332,7334-7460,7462,7464-7476,7596,7609

Modified: tools/branches/2.2/xpp/astribank_hexload.c
URL: http://svnview.digium.com/svn/dahdi/tools/branches/2.2/xpp/astribank_hexload.c?view=diff&rev=7621&r1=7620&r2=7621
==============================================================================
--- tools/branches/2.2/xpp/astribank_hexload.c (original)
+++ tools/branches/2.2/xpp/astribank_hexload.c Sun Nov 22 05:48:40 2009
@@ -41,6 +41,7 @@
 {
 	fprintf(stderr, "Usage: %s [options...] -D {/proc/bus/usb|/dev/bus/usb}/<bus>/<dev> hexfile...\n", progname);
 	fprintf(stderr, "\tOptions: {-F|-p}\n");
+	fprintf(stderr, "\t\t[-E]               # Burn to EEPROM\n");
 	fprintf(stderr, "\t\t[-F]               # Load FPGA firmware\n");
 	fprintf(stderr, "\t\t[-p]               # Load PIC firmware\n");
 	fprintf(stderr, "\t\t[-v]               # Increase verbosity\n");
@@ -65,24 +66,27 @@
 	offset_dummy = hexline->d.content.header.offset;
 	data = hexline->d.content.tt_data.data;
 	if((ret = mpp_send_seg(astribank, data, offset_dummy, len)) < 0) {
-		ERR("Failed FPGA send line: %d\n", ret);
+		ERR("Failed hexfile send line: %d\n", ret);
 		return -EINVAL;
 	}
 	return 0;
 }
 
-static int load_fpga(struct astribank_device *astribank, const char *hexfile)
+static int load_hexfile(struct astribank_device *astribank, const char *hexfile, enum dev_dest dest)
 {
 	struct hexdata		*hexdata = NULL;
 	int			finished = 0;
 	int			ret;
 	int			i;
+	char			star[] = "+\\+|+/+-";
 
 	if((hexdata  = parse_hexfile(hexfile, MAX_HEX_LINES)) == NULL) {
 		perror(hexfile);
 		return -errno;
 	}
-	INFO("Loading FPGA: %s (version %s)\n", hexdata->fname, hexdata->version_info);
+	INFO("Loading hexfile to %s: %s (version %s)\n",
+		dev_dest2str(dest),
+		hexdata->fname, hexdata->version_info);
 #if 0
 	FILE		*fp;
 	if((fp = fopen("fpga_dump_new.txt", "w")) == NULL) {
@@ -90,8 +94,8 @@
 		exit(1);
 	}
 #endif
-	if((ret = mpp_send_start(astribank, DEST_FPGA)) < 0) {
-		ERR("Failed FPGA send start: %d\n", ret);
+	if((ret = mpp_send_start(astribank, dest, hexdata->version_info)) < 0) {
+		ERR("Failed hexfile send start: %d\n", ret);
 		return ret;
 	}
 	for(i = 0; i < hexdata->maxlines; i++) {
@@ -99,6 +103,10 @@
 
 		if(!hexline)
 			break;
+		if(verbose > LOG_INFO) {
+			printf("Sending: %4d%%    %c\r", (100 * i) / hexdata->last_line, star[i % sizeof(star)]);
+			fflush(stdout);
+		}
 		if(finished) {
 			ERR("Extra data after End Of Data Record (line %d)\n", i);
 			return 0;
@@ -109,19 +117,23 @@
 			continue;
 		}
 		if((ret = handle_hexline(astribank, hexline)) < 0) {
-			ERR("Failed FPGA sending in lineno %d (ret=%d)\n", i, ret);;
+			ERR("Failed hexfile sending in lineno %d (ret=%d)\n", i, ret);;
 			return ret;
 		}
 	}
+	if(verbose > LOG_INFO) {
+		putchar('\n');
+		fflush(stdout);
+	}
 	if((ret = mpp_send_end(astribank)) < 0) {
-		ERR("Failed FPGA send end: %d\n", ret);
+		ERR("Failed hexfile send end: %d\n", ret);
 		return ret;
 	}
 #if 0
 	fclose(fp);
 #endif
 	free_hexdata(hexdata);
-	DBG("FPGA firmware loaded successfully\n");
+	DBG("hexfile loaded successfully\n");
 	return 0;
 }
 
@@ -129,9 +141,10 @@
 {
 	char			*devpath = NULL;
 	struct astribank_device *astribank;
-	int			opt_fpga = 0;
 	int			opt_pic = 0;
-	const char		options[] = "vd:D:Fp";
+	int			opt_dest = 0;
+	enum dev_dest		dest = DEST_NONE;
+	const char		options[] = "vd:D:EFp";
 	int			iface_num;
 	int			ret;
 
@@ -147,8 +160,21 @@
 			case 'D':
 				devpath = optarg;
 				break;
+			case 'E':
+				if(dest != DEST_NONE) {
+					ERR("The -F and -E options are mutually exclusive.\n");
+					usage();
+				}
+				opt_dest = 1;
+				dest = DEST_EEPROM;
+				break;
 			case 'F':
-				opt_fpga = 1;
+				if(dest != DEST_NONE) {
+					ERR("The -F and -E options are mutually exclusive.\n");
+					usage();
+				}
+				opt_dest = 1;
+				dest = DEST_FPGA;
 				break;
 			case 'p':
 				opt_pic = 1;
@@ -162,17 +188,18 @@
 			case 'h':
 			default:
 				ERR("Unknown option '%c'\n", c);
-				return 1;
-		}
-	}
-	if((opt_fpga ^ opt_pic) == 0) {
-		ERR("The -F and -p options are mutually exclusive.\n");
+				usage();
+		}
+	}
+	if((opt_dest ^ opt_pic) == 0) {
+		ERR("The -F, -E and -p options are mutually exclusive.\n");
 		usage();
 	}
-	iface_num = (opt_fpga) ? 1 : 0;
-	if(opt_fpga) {
+	iface_num = (opt_dest) ? 1 : 0;
+	if(!opt_pic) {
 		if(optind != argc - 1) {
-			ERR("The -F option requires exacly one hexfile argument\n");
+			ERR("Got %d hexfile names (Need exactly one hexfile)\n",
+				argc - 1 - optind);
 			usage();
 		}
 	}
@@ -185,9 +212,9 @@
 		return 1;
 	}
 	show_astribank_info(astribank);
-	if(opt_fpga) {
-		if(load_fpga(astribank, argv[optind]) < 0) {
-			ERR("Loading FPGA firmware failed\n");
+	if(opt_dest) {
+		if(load_hexfile(astribank, argv[optind], dest) < 0) {
+			ERR("Loading firmware to %s failed\n", dev_dest2str(dest));
 			return 1;
 		}
 	} else if(opt_pic) {

Modified: tools/branches/2.2/xpp/astribank_tool.8
URL: http://svnview.digium.com/svn/dahdi/tools/branches/2.2/xpp/astribank_tool.8?view=diff&rev=7621&r1=7620&r2=7621
==============================================================================
--- tools/branches/2.2/xpp/astribank_tool.8 (original)
+++ tools/branches/2.2/xpp/astribank_tool.8 Sun Nov 22 05:48:40 2009
@@ -3,13 +3,15 @@
 .SH NAME
 astribank_tool \- Xorcom Astribank (xpp) control tool
 .SH SYNOPSIS
-.B astribank_tool -D \fIdevice-path\fR [ options ]
+.B astribank_tool [ options ] [ operation... ] -D \fIdevice-path\fR
 
 .B astribank_tool [-h]
 
 .SH DESCRIPTION
 .B astribank_tool
 is a tool to control the USB-level functionality of an Astribank.
+The tool operates on a single Astribank at a time (given as parameter
+to the -D command line option).
 
 .SH OPTIONS
 .B -D 
@@ -46,6 +48,11 @@
 and the system on the second port is available.
 .RE
 
+.B -Q
+.RS
+Query astribank properties via MPP protocol.
+.RE
+
 .B -n
 .RS
 Renumerate the Astribank product number (e.g: from 1161 to 1162).

Modified: tools/branches/2.2/xpp/astribank_tool.c
URL: http://svnview.digium.com/svn/dahdi/tools/branches/2.2/xpp/astribank_tool.c?view=diff&rev=7621&r1=7620&r2=7621
==============================================================================
--- tools/branches/2.2/xpp/astribank_tool.c (original)
+++ tools/branches/2.2/xpp/astribank_tool.c Sun Nov 22 05:48:40 2009
@@ -41,14 +41,16 @@
 
 static void usage()
 {
-	fprintf(stderr, "Usage: %s [options...] -D {/proc/bus/usb|/dev/bus/usb}/<bus>/<dev>\n", progname);
-	fprintf(stderr, "\tOptions: {-n|-r kind}\n");
+	fprintf(stderr, "Usage: %s [options] -D {/proc/bus/usb|/dev/bus/usb}/<bus>/<dev> [operation...]\n", progname);
+	fprintf(stderr, "\tOptions:\n");
+	fprintf(stderr, "\t\t[-v]               # Increase verbosity\n");
+	fprintf(stderr, "\t\t[-d mask]          # Debug mask (0xFF for everything)\n");
+	fprintf(stderr, "\tOperations:\n");
 	fprintf(stderr, "\t\t[-n]               # Renumerate device\n");
 	fprintf(stderr, "\t\t[-r kind]          # Reset: kind = {half|full}\n");
 	fprintf(stderr, "\t\t[-p port]          # TwinStar: USB port number [0, 1]\n");
 	fprintf(stderr, "\t\t[-w (0|1)]         # TwinStar: Watchdog off or on guard\n");
-	fprintf(stderr, "\t\t[-v]               # Increase verbosity\n");
-	fprintf(stderr, "\t\t[-d mask]          # Debug mask (0xFF for everything)\n");
+	fprintf(stderr, "\t\t[-Q]               # Query device properties\n");
 	exit(1);
 }
 
@@ -82,9 +84,6 @@
 	struct capabilities	capabilities;
 	struct extrainfo	extrainfo;
 
-	show_astribank_info(astribank);
-	if(verbose <= LOG_INFO)
-		return 0;
 	ret = mpp_caps_get(astribank, &eeprom_table, &capabilities, NULL);
 	if(ret < 0)
 		return ret;
@@ -147,11 +146,12 @@
 {
 	char			*devpath = NULL;
 	struct astribank_device *astribank;
-	const char		options[] = "vd:D:nr:p:w:";
+	const char		options[] = "vd:D:nr:p:w:Q";
 	int			opt_renumerate = 0;
 	char			*opt_port = NULL;
 	char			*opt_watchdog = NULL;
 	char			*opt_reset = NULL;
+	int			opt_query = 0;
 	int			ret;
 
 	progname = argv[0];
@@ -183,6 +183,9 @@
 				 */
 				if(reset_kind(opt_reset) < 0)
 					usage();
+				break;
+			case 'Q':
+				opt_query = 1;
 				break;
 			case 'v':
 				verbose++;
@@ -215,7 +218,11 @@
 
 		return 1;
 	}
-	show_hardware(astribank);
+	/*
+	 * First process reset options. We want to be able
+	 * to reset minimal USB firmwares even if they don't
+	 * implement the full MPP protocol (e.g: EEPROM_BURN)
+	 */
 	if(opt_reset) {
 		int	full_reset;
 
@@ -228,6 +235,11 @@
 			ERR("%s Reseting astribank failed: %d\n",
 				(full_reset) ? "Full" : "Half", ret);
 		}
+		goto out;
+	}
+	show_astribank_info(astribank);
+	if(opt_query) {
+		show_hardware(astribank);
 	} else if(opt_renumerate) {
 		DBG("Renumerate\n");
 		if((ret = mpp_renumerate(astribank)) < 0) {
@@ -255,6 +267,7 @@
 			return 1;
 		}
 	}
+out:
 	mpp_exit(astribank);
 	return 0;
 }

Modified: tools/branches/2.2/xpp/astribank_usb.h
URL: http://svnview.digium.com/svn/dahdi/tools/branches/2.2/xpp/astribank_usb.h?view=diff&rev=7621&r1=7620&r2=7621
==============================================================================
--- tools/branches/2.2/xpp/astribank_usb.h (original)
+++ tools/branches/2.2/xpp/astribank_usb.h Sun Nov 22 05:48:40 2009
@@ -78,6 +78,7 @@
 	uint8_t			status;
 	uint8_t			mpp_proto_version;
 	struct eeprom_table	*eeprom;
+	struct firmware_versions	fw_versions;
 	const struct interface_type	*fwtype;
 	uint16_t		tx_sequenceno;
 };

Modified: tools/branches/2.2/xpp/mpp.h
URL: http://svnview.digium.com/svn/dahdi/tools/branches/2.2/xpp/mpp.h?view=diff&rev=7621&r1=7620&r2=7621
==============================================================================
--- tools/branches/2.2/xpp/mpp.h (original)
+++ tools/branches/2.2/xpp/mpp.h Sun Nov 22 05:48:40 2009
@@ -34,7 +34,8 @@
 
 #define	MK_PROTO_VERSION(major, minor)	(((major) << 4) | (0x0F & (minor)))
 
-#define	MPP_PROTOCOL_VERSION	MK_PROTO_VERSION(1,3)
+#define	MPP_PROTOCOL_VERSION	MK_PROTO_VERSION(1,4)
+#define	MPP_SUPPORTED_VERSION(x)	((x) == MK_PROTO_VERSION(1,3) || (x) == MK_PROTO_VERSION(1,4))
 
 /*
  * The eeprom_table is common to all eeprom types.
@@ -49,6 +50,13 @@
 	uint8_t		label[LABEL_SIZE];
 } PACKED;
 
+#define	VERSION_LEN	6
+struct firmware_versions {
+	char	usb[VERSION_LEN];
+	char	fpga[VERSION_LEN];
+	char	eeprom[VERSION_LEN];
+} PACKED;
+
 struct capabilities {
 	uint8_t		ports_fxs;
 	uint8_t		ports_fxo;
@@ -94,6 +102,7 @@
 
 	MPP_STATUS_GET		= 0x11,	/* Get Astribank Status	*/
 	MPP_STATUS_GET_REPLY	= 0x91,
+	MPP_STATUS_GET_REPLY_V13	= 0x91,	/* backward compat */
 
 	MPP_EXTRAINFO_GET	= 0x13,	/* Get extra vendor information	*/
 	MPP_EXTRAINFO_GET_REPLY	= 0x93,
@@ -150,11 +159,20 @@
 
 CMD_DEF(STATUS_GET);
 
+CMD_DEF(STATUS_GET_REPLY_V13,
+	uint8_t	i2cs_data;
+
+#define	STATUS_FPGA_LOADED(x)	((x) & 0x01)
+	uint8_t	status;		/* BIT(0) - FPGA is loaded */
+	);
+
+
 CMD_DEF(STATUS_GET_REPLY,
 	uint8_t	i2cs_data;
 
 #define	STATUS_FPGA_LOADED(x)	((x) & 0x01)
 	uint8_t	status;		/* BIT(0) - FPGA is loaded */
+	struct firmware_versions fw_versions;
 	);
 
 CMD_DEF(EEPROM_SET,
@@ -199,6 +217,7 @@
 
 CMD_DEF(DEV_SEND_START,
 	uint8_t		dest;
+	char		ihex_version[VERSION_LEN];
 	);
 
 CMD_DEF(DEV_SEND_END);
@@ -253,6 +272,7 @@
 		MEMBER(PROTO_QUERY);
 		MEMBER(PROTO_REPLY);
 		MEMBER(STATUS_GET);
+		MEMBER(STATUS_GET_REPLY_V13);
 		MEMBER(STATUS_GET_REPLY);
 		MEMBER(EEPROM_SET);
 		MEMBER(CAPS_GET);

Modified: tools/branches/2.2/xpp/mpp_funcs.c
URL: http://svnview.digium.com/svn/dahdi/tools/branches/2.2/xpp/mpp_funcs.c?view=diff&rev=7621&r1=7620&r2=7621
==============================================================================
--- tools/branches/2.2/xpp/mpp_funcs.c (original)
+++ tools/branches/2.2/xpp/mpp_funcs.c Sun Nov 22 05:48:40 2009
@@ -76,6 +76,18 @@
 	return msgs[et];
 };
 
+const char *dev_dest2str(enum dev_dest dest)
+{
+	const static char	*msgs[] = {
+		[DEST_NONE]	= "NONE",
+		[DEST_FPGA]	= "FPGA",
+		[DEST_EEPROM]	= "EEPROM",
+	};
+	if(dest > sizeof(msgs)/sizeof(msgs[0]))
+		return NULL;
+	return msgs[dest];
+};
+
 struct command_desc {
 	uint8_t		op;
 	const char	*name;
@@ -98,13 +110,13 @@
 	CMD_RECV(ACK),
 	CMD_SEND(PROTO_QUERY),
 	CMD_SEND(STATUS_GET),
-	CMD_SEND(STATUS_GET_REPLY),
+	CMD_RECV(STATUS_GET_REPLY),
 	CMD_SEND(EEPROM_SET),
 	CMD_SEND(CAPS_GET),
 	CMD_RECV(CAPS_GET_REPLY),
 	CMD_SEND(CAPS_SET),
 	CMD_SEND(EXTRAINFO_GET),
-	CMD_SEND(EXTRAINFO_GET_REPLY),
+	CMD_RECV(EXTRAINFO_GET_REPLY),
 	CMD_SEND(EXTRAINFO_SET),
 	CMD_RECV(PROTO_REPLY),
 	CMD_SEND(RENUM),
@@ -127,6 +139,41 @@
 	CMD_SEND(TWS_PWR_GET),
 	CMD_RECV(TWS_PWR_GET_REPLY),
 };
+
+static const struct command_desc	command_table_V13[] = {
+	CMD_RECV(ACK),
+	CMD_SEND(PROTO_QUERY),
+	CMD_SEND(STATUS_GET),
+	CMD_RECV(STATUS_GET_REPLY_V13),
+	CMD_SEND(EEPROM_SET),
+	CMD_SEND(CAPS_GET),
+	CMD_RECV(CAPS_GET_REPLY),
+	CMD_SEND(CAPS_SET),
+	CMD_SEND(EXTRAINFO_GET),
+	CMD_RECV(EXTRAINFO_GET_REPLY),
+	CMD_SEND(EXTRAINFO_SET),
+	CMD_RECV(PROTO_REPLY),
+	CMD_SEND(RENUM),
+	CMD_SEND(EEPROM_BLK_RD),
+	CMD_RECV(EEPROM_BLK_RD_REPLY),
+	CMD_SEND(DEV_SEND_SEG),
+	CMD_SEND(DEV_SEND_START),
+	CMD_SEND(DEV_SEND_END),
+	CMD_SEND(RESET),
+	CMD_SEND(HALF_RESET),
+	CMD_SEND(SER_SEND),
+	CMD_SEND(SER_RECV),
+	/* Twinstar */
+	CMD_SEND(TWS_WD_MODE_SET),
+	CMD_SEND(TWS_WD_MODE_GET),
+	CMD_RECV(TWS_WD_MODE_GET_REPLY),
+	CMD_SEND(TWS_PORT_SET),
+	CMD_SEND(TWS_PORT_GET),
+	CMD_RECV(TWS_PORT_GET_REPLY),
+	CMD_SEND(TWS_PWR_GET),
+	CMD_RECV(TWS_PWR_GET_REPLY),
+};
+
 #undef	CMD_SEND
 #undef	CMD_RECV
 
@@ -148,22 +195,45 @@
 	free(cmd);
 }
 
-struct mpp_command *new_command(uint8_t op, uint16_t extra_data)
+const struct command_desc *get_command_desc(uint8_t protocol_version, uint8_t op)
+{
+	const struct command_desc	*desc;
+
+	switch(protocol_version) {
+		case MK_PROTO_VERSION(1,3):
+			if(op > sizeof(command_table_V13)/sizeof(command_table_V13[0])) {
+				//ERR("Invalid op=0x%X. Bigger than max valid op\n", op);
+				return NULL;
+			}
+			desc = &command_table_V13[op];
+			if(!desc->name)
+				return NULL;
+			break;
+		default:
+			if(op > sizeof(command_table)/sizeof(command_table[0])) {
+				//ERR("Invalid op=0x%X. Bigger than max valid op\n", op);
+				return NULL;
+			}
+			desc = &command_table[op];
+			if(!desc->name)
+				return NULL;
+			break;
+	}
+	return desc;
+}
+
+struct mpp_command *new_command(uint8_t protocol_version, uint8_t op, uint16_t extra_data)
 {
 	struct mpp_command		*cmd;
 	const struct command_desc	*desc;
 	uint16_t			len;
 
-	DBG("OP=0x%X (extra_data %d)\n", op, extra_data);
-	if(op > sizeof(command_table)/sizeof(command_table[0])) {
-		ERR("Invalid op=0x%X. Bigger than max valid op\n", op);
-		return NULL;
-	}
-	desc = &command_table[op];
-	if(!desc->name) {
+	desc = get_command_desc(protocol_version, op);
+	if(!desc) {
 		ERR("Unknown op=0x%X.\n", op);
 		return NULL;
 	}
+	DBG("OP=0x%X [%s] (extra_data %d)\n", op, desc->name, extra_data);
 	len = desc->len + extra_data;
 	if((cmd = malloc(len)) == NULL) {
 		ERR("Out of memory\n");
@@ -173,29 +243,6 @@
 	cmd->header.len = len;
 	cmd->header.seq = 0;	/* Overwritten in send_usb() */
 	return cmd;
-}
-
-const struct command_desc *get_command_desc(uint8_t op)
-{
-	const struct command_desc	*desc;
-
-	if(op > sizeof(command_table)/sizeof(command_table[0])) {
-		//ERR("Invalid op=0x%X. Bigger than max valid op\n", op);
-		return NULL;
-	}
-	desc = &command_table[op];
-	if(!desc->name)
-		return NULL;
-	return desc;
-}
-
-const char *get_command_name(uint8_t op)
-{
-	const struct command_desc	*desc;
-
-	if((desc = get_command_desc(op)) == NULL)
-		return NULL;
-	return desc->name;
 }
 
 void dump_command(struct mpp_command *cmd)
@@ -259,6 +306,8 @@
 	if(ret < 0) {
 		ERR("Receive from usb failed.\n");
 		goto err;
+	} else if(ret == 0) {
+		goto err;	/* No reply */
 	}
 	if(ret != reply->header.len) {
 		ERR("Wrong length received: got %d bytes, but length field says %d bytes%s\n",
@@ -283,13 +332,17 @@
 	struct mpp_command		*reply = NULL;
 	const struct command_desc	*reply_desc;
 	const struct command_desc	*expected;
+	const struct command_desc	*cmd_desc;
 	uint8_t				reply_op;
 	int				ret;
 
 	if(reply_ref)
 		*reply_ref = NULL;	/* So the caller knows if a reply was received */
 	reply_op = cmd->header.op | 0x80;
-	expected = get_command_desc(reply_op);
+	if(cmd->header.op == MPP_PROTO_QUERY)
+		astribank->mpp_proto_version = MPP_PROTOCOL_VERSION;	/* bootstrap */
+	cmd_desc = get_command_desc(astribank->mpp_proto_version, cmd->header.op);
+	expected = get_command_desc(astribank->mpp_proto_version, reply_op);
 	//printf("%s: len=%d\n", __FUNCTION__, cmd->header.len);
 	ret = send_command(astribank, cmd, TIMEOUT);
 	if(!reply_ref) {
@@ -313,7 +366,7 @@
 		goto out;
 	}
 	DBG("REPLY OP: 0x%X\n", reply->header.op);
-	reply_desc = get_command_desc(reply->header.op);
+	reply_desc = get_command_desc(astribank->mpp_proto_version, reply->header.op);
 	if(!reply_desc) {
 		ERR("Unknown reply op=0x%02X\n", reply->header.op);
 		ret = -EPROTO;
@@ -330,8 +383,9 @@
 			goto out;
 		} else if(status != STAT_OK) {
 
-			ERR("Got ACK (for OP=0x%X): %d - %s\n",
+			ERR("Got ACK (for OP=0x%X [%s]): %d - %s\n",
 				cmd->header.op,
+				cmd_desc->name,
 				status,
 				ack_status_msg(status));
 #if 0
@@ -371,6 +425,12 @@
 	return ret;
 }
 
+static int set_ihex_version(char *dst, const char *src)
+{
+	memcpy(dst, src, VERSION_LEN);
+	return 0;
+}
+
 /*
  * Protocol Commands
  */
@@ -383,7 +443,7 @@
 
 	DBG("\n");
 	assert(astribank != NULL);
-	if((cmd = new_command(MPP_PROTO_QUERY, 0)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_PROTO_QUERY, 0)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
@@ -394,13 +454,17 @@
 		return ret;
 	}
 	astribank->mpp_proto_version = CMD_FIELD(reply, PROTO_REPLY, proto_version);
-	if(astribank->mpp_proto_version != MPP_PROTOCOL_VERSION) {
+	if(! MPP_SUPPORTED_VERSION(astribank->mpp_proto_version)) {
 		ERR("Got mpp protocol version: %02x (expected %02x)\n",
 			astribank->mpp_proto_version,
 			MPP_PROTOCOL_VERSION);
 		ret = -EPROTO;
 		goto out;
 	}
+	if(astribank->mpp_proto_version != MPP_PROTOCOL_VERSION) {
+		ERR("Deprecated (but working) MPP protocol version [%X]. Please upgrade to [%X] ASAP\n",
+			astribank->mpp_proto_version, MPP_PROTOCOL_VERSION);
+	}
 	DBG("Protocol version: %02x\n", astribank->mpp_proto_version);
 	ret = astribank->mpp_proto_version;
 	free_command(reply);
@@ -416,7 +480,7 @@
 
 	DBG("\n");
 	assert(astribank != NULL);
-	if((cmd = new_command(MPP_STATUS_GET, 0)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_STATUS_GET, 0)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
@@ -427,8 +491,13 @@
 	}
 	astribank->eeprom_type = 0x3 & (CMD_FIELD(reply, STATUS_GET_REPLY, i2cs_data) >> 3);
 	astribank->status = CMD_FIELD(reply, STATUS_GET_REPLY, status);
+	astribank->fw_versions = CMD_FIELD(reply, STATUS_GET_REPLY, fw_versions);
 	DBG("EEPROM TYPE: %02x\n", astribank->eeprom_type);
 	DBG("FPGA Firmware: %s\n", (astribank->status & 0x1) ? "Loaded" : "Empty");
+	DBG("Firmware Versions: USB='%s' FPGA='%s' EEPROM='%s'\n",
+		astribank->fw_versions.usb,
+		astribank->fw_versions.fpga,
+		astribank->fw_versions.eeprom);
 	free_command(reply);
 	return ret;
 }
@@ -441,7 +510,7 @@
 
 	DBG("\n");
 	assert(astribank != NULL);
-	if((cmd = new_command(MPP_EEPROM_SET, 0)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_EEPROM_SET, 0)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
@@ -462,7 +531,7 @@
 
 	DBG("\n");
 	assert(astribank != NULL);
-	if((cmd = new_command(MPP_RENUM, 0)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_RENUM, 0)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
@@ -485,7 +554,7 @@
 
 	DBG("\n");
 	assert(astribank != NULL);
-	if((cmd = new_command(MPP_CAPS_GET, 0)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_CAPS_GET, 0)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
@@ -523,7 +592,7 @@
 
 	DBG("\n");
 	assert(astribank != NULL);
-	if((cmd = new_command(MPP_CAPS_SET, 0)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_CAPS_SET, 0)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
@@ -547,7 +616,7 @@
 
 	DBG("\n");
 	assert(astribank != NULL);
-	if((cmd = new_command(MPP_EXTRAINFO_GET, 0)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_EXTRAINFO_GET, 0)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
@@ -572,7 +641,7 @@
 
 	DBG("\n");
 	assert(astribank != NULL);
-	if((cmd = new_command(MPP_EXTRAINFO_SET, 0)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_EXTRAINFO_SET, 0)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
@@ -595,7 +664,7 @@
 
 	DBG("len = %d, offset = %d\n", len, offset);
 	assert(astribank != NULL);
-	if((cmd = new_command(MPP_EEPROM_BLK_RD, 0)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_EEPROM_BLK_RD, 0)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
@@ -620,20 +689,21 @@
 	return size;
 }
 
-int mpp_send_start(struct astribank_device *astribank, enum dev_dest dest)
+int mpp_send_start(struct astribank_device *astribank, enum dev_dest dest, const char *ihex_version)
 {
 	struct mpp_command	*cmd;
 	struct mpp_command	*reply = NULL;
 	int			ret = 0;
 
-	DBG("dest = %d\n", dest);
-	assert(astribank != NULL);
-	if((cmd = new_command(MPP_DEV_SEND_START, 0)) == NULL) {
+	DBG("dest = %s ihex_version = '%s'\n", dev_dest2str(dest), ihex_version);
+	assert(astribank != NULL);
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_DEV_SEND_START, 0)) == NULL) {
 		ERR("new_command failed\n");
 		ret = -ENOMEM;
 		goto out;
 	}
 	CMD_FIELD(cmd, DEV_SEND_START, dest) = dest;
+	set_ihex_version(CMD_FIELD(cmd, DEV_SEND_START, ihex_version), ihex_version);
 	ret = process_command(astribank, cmd, &reply);
 	if(ret < 0) {
 		ERR("process_command failed: %d\n", ret);
@@ -656,7 +726,7 @@
 
 	DBG("\n");
 	assert(astribank != NULL);
-	if((cmd = new_command(MPP_DEV_SEND_END, 0)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_DEV_SEND_END, 0)) == NULL) {
 		ERR("new_command failed\n");
 		ret = -ENOMEM;
 		goto out;
@@ -688,7 +758,7 @@
 	}
 	DBG("len = %d, offset = %d (0x%02X, 0x%02X)\n", len, offset, *data, *(data + 1));
 	assert(astribank != NULL);
-	if((cmd = new_command(MPP_DEV_SEND_SEG, len)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_DEV_SEND_SEG, len)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
@@ -725,7 +795,7 @@
 
 	DBG("full = %s\n", (full_reset) ? "YES" : "NO");
 	assert(astribank != NULL);
-	if((cmd = new_command(op, 0)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, op, 0)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
@@ -746,7 +816,7 @@
 
 	DBG("len=%d\n", len);
 	assert(astribank != NULL);
-	if((cmd = new_command(MPP_SER_SEND, len)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_SER_SEND, len)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
@@ -804,7 +874,7 @@
 
 	DBG("\n");
 	assert(astribank != NULL);
-	if((cmd = new_command(MPP_TWS_WD_MODE_GET, 0)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_TWS_WD_MODE_GET, 0)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
@@ -827,7 +897,7 @@
 
 	DBG("%s\n", (yes) ? "YES" : "NO");
 	assert(astribank != NULL);
-	if((cmd = new_command(MPP_TWS_WD_MODE_SET, 0)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_TWS_WD_MODE_SET, 0)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
@@ -849,7 +919,7 @@
 
 	DBG("\n");
 	assert(astribank != NULL);
-	if((cmd = new_command(MPP_TWS_PWR_GET, 0)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_TWS_PWR_GET, 0)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
@@ -872,7 +942,7 @@
 
 	DBG("\n");
 	assert(astribank != NULL);
-	if((cmd = new_command(MPP_TWS_PORT_GET, 0)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_TWS_PORT_GET, 0)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
@@ -891,7 +961,6 @@
 {
 	struct mpp_command	*cmd;
 	int			ret;
-	struct mpp_command	*reply;
 
 	DBG("\n");
 	assert(astribank != NULL);
@@ -899,17 +968,16 @@
 		ERR("Invalid portnum (%d)\n", portnum);
 		return -EINVAL;
 	}
-	if((cmd = new_command(MPP_TWS_PORT_SET, 0)) == NULL) {
+	if((cmd = new_command(astribank->mpp_proto_version, MPP_TWS_PORT_SET, 0)) == NULL) {
 		ERR("new_command failed\n");
 		return -ENOMEM;
 	}
 	CMD_FIELD(cmd, TWS_PORT_SET, portnum) = portnum;
-	ret = process_command(astribank, cmd, &reply);
-	if(ret < 0) {
-		ERR("process_command failed: %d\n", ret);
-		return ret;
-	}
-	free_command(reply);
+	ret = process_command(astribank, cmd, NULL);
+	if(ret < 0) {
+		ERR("process_command failed: %d\n", ret);
+		return ret;
+	}
 	return 0;
 }
 
@@ -983,9 +1051,19 @@
 
 void show_astribank_status(struct astribank_device *astribank, FILE *fp)
 {
-	fprintf(fp, "Astribank: EEPROM      : %s\n", eeprom_type2str(astribank->eeprom_type));
+	char	version_buf[BUFSIZ];
+	int	is_loaded = STATUS_FPGA_LOADED(astribank->status);
+
+	fprintf(fp, "Astribank: EEPROM      : %s\n",
+		eeprom_type2str(astribank->eeprom_type));
 	fprintf(fp, "Astribank: FPGA status : %s\n",
-		STATUS_FPGA_LOADED(astribank->status) ? "Loaded" : "Empty");
+		is_loaded ? "Loaded" : "Empty");
+	if(is_loaded) {
+		memset(version_buf, 0, sizeof(version_buf));
+		memcpy(version_buf, astribank->fw_versions.fpga, VERSION_LEN);
+		fprintf(fp, "Astribank: FPGA version: %s\n",
+			version_buf);
+	}
 }
 
 void show_extrainfo(const struct extrainfo *extrainfo, FILE *fp)

Modified: tools/branches/2.2/xpp/mpp_funcs.h
URL: http://svnview.digium.com/svn/dahdi/tools/branches/2.2/xpp/mpp_funcs.h?view=diff&rev=7621&r1=7620&r2=7621
==============================================================================
--- tools/branches/2.2/xpp/mpp_funcs.h (original)
+++ tools/branches/2.2/xpp/mpp_funcs.h Sun Nov 22 05:48:40 2009
@@ -45,7 +45,7 @@
 int mpp_extrainfo_get(struct astribank_device *astribank, struct extrainfo *info);
 int mpp_extrainfo_set(struct astribank_device *astribank, const struct extrainfo *info);
 int mpp_eeprom_blk_rd(struct astribank_device *astribank, uint8_t *buf, uint16_t offset, uint16_t len);
-int mpp_send_start(struct astribank_device *astribank, enum dev_dest dest);
+int mpp_send_start(struct astribank_device *astribank, enum dev_dest dest, const char *ihex_version);
 int mpp_send_end(struct astribank_device *astribank);
 int mpp_send_seg(struct astribank_device *astribank, const uint8_t *data, uint16_t offset, uint16_t len);
 int mpp_reset(struct astribank_device *astribank, int full_reset);
@@ -72,7 +72,9 @@
 
 /* low-level */
 int process_command(struct astribank_device *astribank, struct mpp_command *cmd, struct mpp_command **reply_ref);
-struct mpp_command *new_command(uint8_t op, uint16_t extra_data);
+struct mpp_command *new_command(uint8_t protocol_version, uint8_t op, uint16_t extra_data);
 void free_command(struct mpp_command *cmd);
 
+const char *dev_dest2str(enum dev_dest dest);
+
 #endif	/* MPP_FUNCS_H */

Modified: tools/branches/2.2/xpp/perl_modules/Dahdi/Hardware/USB.pm
URL: http://svnview.digium.com/svn/dahdi/tools/branches/2.2/xpp/perl_modules/Dahdi/Hardware/USB.pm?view=diff&rev=7621&r1=7620&r2=7621
==============================================================================
--- tools/branches/2.2/xpp/perl_modules/Dahdi/Hardware/USB.pm (original)
+++ tools/branches/2.2/xpp/perl_modules/Dahdi/Hardware/USB.pm Sun Nov 22 05:48:40 2009
@@ -33,6 +33,7 @@
 	'e4e4:1160'	=> { DRIVER => 'xpp_usb', DESCRIPTION => 'Astribank-modular no-firmware' },
 	'e4e4:1161'	=> { DRIVER => 'xpp_usb', DESCRIPTION => 'Astribank-modular USB-firmware' },
 	'e4e4:1162'	=> { DRIVER => 'xpp_usb', DESCRIPTION => 'Astribank-modular FPGA-firmware' },
+	'e4e4:1163'	=> { DRIVER => 'xpp_usb', DESCRIPTION => 'Astribank-TwinStar monitor' },
 	
 	# Sangoma USB FXO:
 	'10c4:8461'	=> { DRIVER => 'wanpipe', DESCRIPTION => 'Sangoma WANPIPE USB-FXO Device' },

Modified: tools/branches/2.2/xpp/perl_modules/Dahdi/Xpp/Mpp.pm
URL: http://svnview.digium.com/svn/dahdi/tools/branches/2.2/xpp/perl_modules/Dahdi/Xpp/Mpp.pm?view=diff&rev=7621&r1=7620&r2=7621
==============================================================================
--- tools/branches/2.2/xpp/perl_modules/Dahdi/Xpp/Mpp.pm (original)
+++ tools/branches/2.2/xpp/perl_modules/Dahdi/Xpp/Mpp.pm Sun Nov 22 05:48:40 2009
@@ -102,8 +102,9 @@
 	}
 }
 
-sub astribank_tool_cmd($) {
+sub astribank_tool_cmd($@) {
 	my $dev = shift || die;
+	my @args = @_;
 	my $usb_top;
 
 	# Find USB bus toplevel
@@ -113,7 +114,7 @@
 	my $name = $dev->priv_device_name();
 	die "$0: Unkown private device name" unless defined $name;
 	my $path = "$usb_top/$name";
-	return ($astribank_tool, '-D', "$path");
+	return ($astribank_tool, '-D', "$path", @args);
 }
 
 sub new($$$) {
@@ -136,7 +137,7 @@
 	}
 	return $mppinfo unless $product =~ /116[12]/;
 	$mppinfo->{'MPP_TALK'} = 1;
-	my @cmd = astribank_tool_cmd($dev);
+	my @cmd = astribank_tool_cmd($dev, '-Q');
 	my $name = $dev->priv_device_name();
 	my $dbg_file = "$name";
 	$dbg_file =~ s/\W/_/g;
@@ -191,9 +192,9 @@
 	my $dev = $mppinfo->dev || die;
 	return undef unless defined $mppinfo->mpp_talk;
 	my $old = $mppinfo->tws_watchdog;
-	my @cmd = astribank_tool_cmd($dev);
+	my @cmd = astribank_tool_cmd($dev, '-w', $on);
 	print STDERR "DEBUG($on): '@cmd'\n";
-	system(@cmd, '-w', $on);
+	system(@cmd);
 	die "Running $astribank_tool failed: $?" if $?;
 }
 
@@ -204,8 +205,8 @@
 	my $port = $mppinfo->twinstar_port;
 	$port = ($port == 1) ? 0 : 1;
 	die "Unknown TwinStar port" unless defined $port;
-	my @cmd = astribank_tool_cmd($dev);
-	system(@cmd, '-p', $port);
+	my @cmd = astribank_tool_cmd($dev, '-p', $port);
+	system(@cmd);
 	die "Running $astribank_tool failed: $?" if $?;
 }
 




More information about the svn-commits mailing list