From ba8a80b30c4da36ef10854b53b06d9ff9acaca44 Mon Sep 17 00:00:00 2001
From: "henryk@ploetzli.ch"
 <henryk@ploetzli.ch@ef4ab9da-24cd-11de-8aaa-f3a34680c41f>
Date: Fri, 28 Aug 2009 00:37:28 +0000
Subject: [PATCH 1/1] Add version command

---
 armsrc/appmain.c    | 11 +++++++++++
 armsrc/apps.h       |  2 ++
 armsrc/fpgaloader.c | 31 +++++++++++++++++++++++++++++++
 armsrc/util.c       | 13 +++++++++++++
 include/usb_cmd.h   |  1 +
 winsrc/command.cpp  |  8 ++++++++
 6 files changed, 66 insertions(+)

diff --git a/armsrc/appmain.c b/armsrc/appmain.c
index a3871eb6..551ee694 100644
--- a/armsrc/appmain.c
+++ b/armsrc/appmain.c
@@ -236,6 +236,14 @@ void ReadMem(int addr)
 		DbpIntegers(0, data[i], data[i+1]);
 }
 
+void SendVersion(void)
+{
+	char temp[48]; /* Limited data payload in USB packets */
+	DbpString("Prox/RFID mark3 RFID instrument");
+	FpgaGatherVersion(temp, sizeof(temp));
+	DbpString(temp);
+}
+
 // samy's sniff and repeat routine
 void SamyRun()
 {
@@ -616,6 +624,9 @@ void UsbPacketReceived(BYTE *packet, int len)
 		case CMD_SET_LF_DIVISOR:
 			FpgaSendCommand(FPGA_CMD_SET_DIVISOR, c->ext1);
 			break;
+		case CMD_VERSION:
+			SendVersion();
+			break;
 #ifdef WITH_LCD
 		case CMD_LCD_RESET:
 			LCDReset();
diff --git a/armsrc/apps.h b/armsrc/apps.h
index 878ec526..7605baa3 100644
--- a/armsrc/apps.h
+++ b/armsrc/apps.h
@@ -30,6 +30,7 @@ extern DWORD BigBuf[];
 void FpgaSendCommand(WORD cmd, WORD v);
 void FpgaWriteConfWord(BYTE v);
 void FpgaDownloadAndGo(void);
+void FpgaGatherVersion(char *dst, int len);
 void FpgaSetupSsc(void);
 void SetupSpi(int mode);
 void FpgaSetupSscDma(BYTE *buf, int len);
@@ -104,6 +105,7 @@ int strlen(char *str);
 void *memcpy(void *dest, const void *src, int len);
 void *memset(void *dest, int c, int len);
 int memcmp(const void *av, const void *bv, int len);
+char *strncat(char *dest, const char *src, unsigned int n);
 void SpinDelay(int ms);
 void SpinDelayUs(int us);
 void LED(int led, int ms);
diff --git a/armsrc/fpgaloader.c b/armsrc/fpgaloader.c
index e07c2542..88fdc4cf 100644
--- a/armsrc/fpgaloader.c
+++ b/armsrc/fpgaloader.c
@@ -285,6 +285,37 @@ void FpgaDownloadAndGo(void)
 		DownloadFPGA((DWORD *)0x2000, 10524, 1);
 }
 
+void FpgaGatherVersion(char *dst, int len)
+{
+	char *fpga_info; 
+	unsigned int fpga_info_len;
+	dst[0] = 0;
+	if(!bitparse_find_section('e', (void**)&fpga_info, &fpga_info_len)) {
+		strncat(dst, "FPGA image: legacy image without version information", len-1);
+	} else {
+		strncat(dst, "FPGA image built", len-1);
+		/* USB packets only have 48 bytes data payload, so be terse */
+#if 0
+		if(bitparse_find_section('a', (void**)&fpga_info, &fpga_info_len) && fpga_info[fpga_info_len-1] == 0 ) {
+			strncat(dst, " from ", len-1);
+			strncat(dst, fpga_info, len-1);
+		}
+		if(bitparse_find_section('b', (void**)&fpga_info, &fpga_info_len) && fpga_info[fpga_info_len-1] == 0 ) {
+			strncat(dst, " for ", len-1);
+			strncat(dst, fpga_info, len-1);
+		}
+#endif
+		if(bitparse_find_section('c', (void**)&fpga_info, &fpga_info_len) && fpga_info[fpga_info_len-1] == 0 ) {
+			strncat(dst, " on ", len-1);
+			strncat(dst, fpga_info, len-1);
+		}
+		if(bitparse_find_section('d', (void**)&fpga_info, &fpga_info_len) && fpga_info[fpga_info_len-1] == 0 ) {
+			strncat(dst, " at ", len-1);
+			strncat(dst, fpga_info, len-1);
+		}
+	}
+}
+
 //-----------------------------------------------------------------------------
 // Send a 16 bit command/data pair to the FPGA.
 // The bit format is:  C3 C2 C1 C0 D11 D10 D9 D8 D7 D6 D5 D4 D3 D2 D1 D0
diff --git a/armsrc/util.c b/armsrc/util.c
index 8a3da63a..a102bbb5 100644
--- a/armsrc/util.c
+++ b/armsrc/util.c
@@ -52,6 +52,19 @@ int strlen(char *str)
 	return l;
 }
 
+char* strncat(char *dest, const char *src, unsigned int n)
+{
+	unsigned int dest_len = strlen(dest);
+	unsigned int i;
+	
+	for (i = 0 ; i < n && src[i] != '\0' ; i++)
+		dest[dest_len + i] = src[i];
+	dest[dest_len + i] = '\0';
+	
+	return dest;
+}
+
+
 void LEDsoff()
 {
 	LED_A_OFF();
diff --git a/include/usb_cmd.h b/include/usb_cmd.h
index 6818bb5e..b5c438c6 100644
--- a/include/usb_cmd.h
+++ b/include/usb_cmd.h
@@ -35,6 +35,7 @@ typedef struct {
 #define CMD_LCD																				0x0104
 #define CMD_BUFF_CLEAR																0x0105
 #define CMD_READ_MEM																	0x0106
+#define CMD_VERSION																	0x0107
 
 // For low-frequency tags
 #define CMD_READ_TI_TYPE															0x0202
diff --git a/winsrc/command.cpp b/winsrc/command.cpp
index 08feb3dd..3a858ddc 100644
--- a/winsrc/command.cpp
+++ b/winsrc/command.cpp
@@ -2732,6 +2732,13 @@ static void CmdReadmem(char *str)
 	SendCommand(&c, FALSE);
 }
 
+static void CmdVersion(char *str)
+{
+	UsbCommand c;
+	c.cmd = CMD_VERSION;
+	SendCommand(&c, FALSE);
+}
+
 static void CmdLcdReset(char *str)
 {
 	UsbCommand c;
@@ -2844,6 +2851,7 @@ static struct {
 	{"tiwrite",				CmdTIWrite,					0, "Write new data to a r/w TI 134 kHz tag"},
 	{"threshold",			CmdThreshold,				1, "Maximize/minimize every value in the graph window depending on threshold"},
 	{"tune",					CmdTune,						0, "Measure antenna tuning"},
+	{"version",			CmdVersion,				0, "Show version inforation about the connected Proxmark"},
 	{"vchdemod",			CmdVchdemod,				0, "['clone'] -- Demodulate samples for VeriChip"},
 	{"zerocrossings",	CmdZerocrossings,		1, "Count time between zero-crossings"},
 };
-- 
2.39.5