Zach Welch wrote:
On Tue, 2009-05-19 at 16:53 +0200, Magnus Lundin wrote:
Hi

Info : J-Link compiled Feb 20 2006 18:20:20 -- Update --
Info : JLink caps 0x3
Error: J-Link command EMU_CMD_GET_MAX_MEM_BLOCK failed (-110)
Open OCD seems to get reasonable ansvers from first two JLink commands.

The /* query hardware maximum memory block */ should not be run for this
version, I had removed it in my patch. Next patch will use results from
JLink caps to select what info to query.

I am waiting for more info from Segger about version diffrences and
endpoints.

How are we doing with this patch?  It looks like we have made some good
progress this week, so I don't want the effort to stall.

What are the thoughts about committing your latest version?  Even if
more changes may be pending, it seems that your work has improved things
for folks with some devices, so I think we have made constructive
progress from where we were before now.  If nothing else, we should get
some more testing feedback. ;)

Cheers,

Zach
There is a set of new patches that has been tested by Michael Fischer, as far as i know there were no problems.

There are still things that should be fixed in the resethandling in jtag_add_reset and minimizing the differences between ft2232 and jlink behaviour. But still would suggest that the following patcches are commited. They are not untested.

Have a nice weekend
Magnus

Index: src/jtag/jtag.c
===================================================================
--- src/jtag/jtag.c	(revision 1881)
+++ src/jtag/jtag.c	(working copy)
@@ -1253,6 +1253,7 @@
 		jtag_error=retval;
 		return;
 	}
+	jtag_execute_queue();
 
 	if (jtag_srst)
 	{
@@ -1280,7 +1281,7 @@
 		 * and inform possible listeners about this
 		 */
 		LOG_DEBUG("TRST line asserted");
-		cmd_queue_cur_state = TAP_RESET;
+		tap_set_state(TAP_RESET);
 		jtag_call_event_callbacks(JTAG_TRST_ASSERTED);
 	}
 	else
Index: src/jtag/ft2232.c
===================================================================
--- src/jtag/ft2232.c	(revision 1875)
+++ src/jtag/ft2232.c	(working copy)
@@ -1629,10 +1629,13 @@
 		first_unsent = cmd;
 	}
 
+#if 0
+	/* This is (or should) be handled in jtag_add_reset */ 
 	if ( (cmd->cmd.reset->trst == 1) || ( cmd->cmd.reset->srst && (jtag_reset_config & RESET_SRST_PULLS_TRST) ) )
 	{
 		tap_set_state(TAP_RESET);
 	}
+#endif
 	layout->reset(cmd->cmd.reset->trst, cmd->cmd.reset->srst);
 	require_send = 1;
 
Index: src/jtag/jlink.c
===================================================================
--- src/jtag/jlink.c	(revision 1875)
+++ src/jtag/jlink.c	(working copy)
@@ -36,9 +36,13 @@
 #define JLINK_WRITE_ENDPOINT	0x02
 #define JLINK_READ_ENDPOINT		0x81
 
+unsigned int jlink_write_ep = JLINK_WRITE_ENDPOINT;
+unsigned int jlink_read_ep = JLINK_READ_ENDPOINT;
+unsigned int jlink_hw_jtag_version = 2;
+
 #define JLINK_USB_TIMEOUT		1000
 
-// See Section 1.3.2 of the Segger JLink USB protocol manual
+/* See Section 1.3.2 of the Segger JLink USB protocol manual */
 /* 2048 is the max value we can use here */
 //#define JLINK_TAP_BUFFER_SIZE 2048
 #define JLINK_TAP_BUFFER_SIZE 256
@@ -60,6 +64,7 @@
 #define EMU_CMD_HW_CLOCK			0xc8
 #define EMU_CMD_HW_TMS0 			0xc9
 #define EMU_CMD_HW_TMS1 			0xca
+#define EMU_CMD_HW_JTAG2    		0xce
 #define EMU_CMD_HW_JTAG3    		0xcf
 #define EMU_CMD_GET_MAX_MEM_BLOCK	0xd4
 #define EMU_CMD_HW_RESET0   		0xdc
@@ -67,6 +72,7 @@
 #define EMU_CMD_HW_TRST0    		0xde
 #define EMU_CMD_HW_TRST1    		0xdf
 #define EMU_CMD_GET_CAPS    		0xe8
+#define EMU_CMD_GET_HW_VERSION  	0xf0
 
 /* max speed 12MHz v5.0 jlink */
 #define JLINK_MAX_SPEED 12000
@@ -82,6 +88,7 @@
 
 /* CLI command handler functions */
 static int jlink_handle_jlink_info_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
+static int jlink_handle_jlink_hw_jtag_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
 
 /* Queue command functions */
 static void jlink_end_state(tap_state_t state);
@@ -209,10 +216,13 @@
 
 	jlink_tap_execute();
 
+#if 0
+/* This is handled in jtag_add_reset */ 
 	if ( (cmd->cmd.reset->trst == 1) || ( cmd->cmd.reset->srst && (jtag_reset_config & RESET_SRST_PULLS_TRST) ) )
 	{
 		tap_set_state(TAP_RESET);
 	}
+#endif
 
 	jlink_reset(cmd->cmd.reset->trst, cmd->cmd.reset->srst);
 	jlink_tap_execute();
@@ -301,8 +311,11 @@
 
 static int jlink_register_commands(struct command_context_s *cmd_ctx)
 {
+
 	register_command(cmd_ctx, NULL, "jlink_info", jlink_handle_jlink_info_command, COMMAND_EXEC,
 		"query jlink info");
+	register_command(cmd_ctx, NULL, "jlink_hw_jtag", jlink_handle_jlink_hw_jtag_command, COMMAND_EXEC,
+		"set/get jlink hw jtag command version [2|3]");
 	return ERROR_OK;
 }
 
@@ -318,6 +331,7 @@
 		return ERROR_JTAG_INIT_FAILED;
 	}
 
+	jlink_hw_jtag_version = 2;
 	check_cnt = 0;
 	while (check_cnt < 3)
 	{
@@ -543,7 +557,7 @@
 {
 	int result;
 	int len;
-	u32 jlink_caps, jlink_max_size;
+	u32 jlink_caps, jlink_max_size, jlink_hw_version;
 
 	/* query hardware version */
 	jlink_simple_command(EMU_CMD_VERSION);
@@ -556,6 +570,12 @@
 	}
 
 	len = buf_get_u32(usb_in_buffer, 0, 16);
+	if (len > JLINK_IN_BUFFER_SIZE)
+	{
+		LOG_ERROR("J-Link command EMU_CMD_VERSION impossible return length 0x%0x", len);
+		len = JLINK_IN_BUFFER_SIZE;
+	}
+	
 	result = jlink_usb_read(jlink_jtag_handle, len);
 	if (result != len)
 	{
@@ -579,21 +599,42 @@
 	jlink_caps = buf_get_u32(usb_in_buffer, 0, 32);
 	LOG_INFO("JLink caps 0x%x", jlink_caps);
 
+	if (jlink_caps & (1<<1)) /* EMU_CAP_GET_HW_VERSION */
+	{
+		/* query hardware version */
+		jlink_simple_command(EMU_CMD_GET_HW_VERSION);
 
-	/* query hardware maximum memory block */
-	jlink_simple_command(EMU_CMD_GET_MAX_MEM_BLOCK);
+		result = jlink_usb_read(jlink_jtag_handle, 4);
+		if (4 != result)
+		{
+			LOG_ERROR("J-Link command EMU_CMD_GET_HW_VERSION failed (%d)\n", result);
+			return ERROR_JTAG_DEVICE_ERROR;
+		}
 
-	result = jlink_usb_read(jlink_jtag_handle, 4);
-	if (4 != result)
-	{
-		LOG_ERROR("J-Link command EMU_CMD_GET_MAX_MEM_BLOCK failed (%d)\n", result);
-		return ERROR_JTAG_DEVICE_ERROR;
+		jlink_hw_version = buf_get_u32(usb_in_buffer, 0, 32);
+		if ( ((jlink_hw_version/10000)%100) >= 5 ) /* Major revision >= 5 */
+		{
+			jlink_hw_jtag_version = 3;
+		}
+		LOG_INFO("JLink hw version %i", jlink_hw_version);
 	}
 
-	jlink_max_size = buf_get_u32(usb_in_buffer, 0, 32);
-	LOG_INFO("JLink max mem block %i", jlink_max_size);
+	if (jlink_caps & (1<<11)) /* EMU_CAP_GET_MAX_BLOCK_SIZE */
+	{
+		/* query hardware maximum memory block */
+		jlink_simple_command(EMU_CMD_GET_MAX_MEM_BLOCK);
 
+		result = jlink_usb_read(jlink_jtag_handle, 4);
+		if (4 != result)
+		{
+			LOG_ERROR("J-Link command EMU_CMD_GET_MAX_MEM_BLOCK failed (%d)\n", result);
+			return ERROR_JTAG_DEVICE_ERROR;
+		}
 
+		jlink_max_size = buf_get_u32(usb_in_buffer, 0, 32);
+		LOG_INFO("JLink max mem block %i", jlink_max_size);
+	}
+
 	return ERROR_OK;
 }
 
@@ -608,6 +649,31 @@
 	return ERROR_OK;
 }
 
+static int jlink_handle_jlink_hw_jtag_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
+{
+	if (argc == 1)
+	{
+		if (strcmp(args[0], "2") == 0)
+		{
+			jlink_hw_jtag_version = 2;
+		}
+		else if (strcmp(args[0], "3") == 0)
+		{
+			jlink_hw_jtag_version = 3;
+		} else
+		{
+			return ERROR_COMMAND_SYNTAX_ERROR;
+		}
+	} else if (argc != 0)
+	{
+		return ERROR_COMMAND_SYNTAX_ERROR;
+	}
+
+	command_print(cmd_ctx, "jlink hw jtag  %i", jlink_hw_jtag_version);
+
+	return ERROR_OK;
+}
+
 /***************************************************************************/
 /* J-Link tap functions */
 
@@ -661,7 +727,7 @@
 	int bit_index = tap_length % 8;
 	u8 bit = 1 << bit_index;
 
-	// we do not pad TMS, so be sure to initialize all bits
+	/* we do not pad TMS, so be sure to initialize all bits */
 	if (0 == bit_index)
 	{
 		tms_buffer[index] = tdi_buffer[index] = 0;
@@ -721,7 +787,14 @@
 	// number of full bytes (plus one if some would be left over)
 	byte_length = TAP_SCAN_BYTES(tap_length);
 
-	usb_out_buffer[0] = EMU_CMD_HW_JTAG3;
+	if (jlink_hw_jtag_version >= 3)
+	{
+		usb_out_buffer[0] = EMU_CMD_HW_JTAG3;
+	}
+	else
+	{
+		usb_out_buffer[0] = EMU_CMD_HW_JTAG2;
+	}
 	usb_out_buffer[1] = 0;
 	usb_out_buffer[2] = (tap_length >> 0) & 0xff;
 	usb_out_buffer[3] = (tap_length >> 8) & 0xff;
@@ -814,6 +887,24 @@
 				 */
 				usb_set_altinterface(result->usb_handle, 0);
 #endif
+				int i;
+				for (i =0 ; i<dev->config[0].interface[0].altsetting[0].bNumEndpoints; i++)
+				{
+					u8 epnum = dev->config[0].interface[0].altsetting[0].endpoint[i].bEndpointAddress;
+					{						
+						if (epnum&0x80)
+						{ 
+							LOG_DEBUG("usb ep in %02x",epnum);
+							jlink_read_ep = epnum;
+						}
+						else
+						{
+							LOG_DEBUG("usb ep out %02x",epnum);
+							jlink_write_ep = epnum;
+						}
+					}
+				}
+
 				return result;
 			}
 		}
@@ -833,7 +924,7 @@
 static int jlink_usb_message(jlink_jtag_t *jlink_jtag, int out_length, int in_length)
 {
 	int result;
-	int result2;
+	int result2 = ERROR_OK;
 
 	result = jlink_usb_write(jlink_jtag, out_length);
 	if (result != out_length)
@@ -851,38 +942,41 @@
 		return ERROR_JTAG_DEVICE_ERROR;
 	}
 
-	if (result == in_length)
+	if (jlink_hw_jtag_version >= 3)
 	{
-		/* Must read the result from the EMU too */
-		result2 = jlink_usb_read_emu_result(jlink_jtag);
-		if (1 != result2)
+		if (result == in_length)
 		{
-			LOG_ERROR("jlink_usb_read_emu_result retried requested=1, result=%d, in_length=%i", result2,in_length);
-			/* Try again once, should only happen if (in_length%64==0) */
+			/* Must read the result from the EMU too */
 			result2 = jlink_usb_read_emu_result(jlink_jtag);
 			if (1 != result2)
 			{
-				LOG_ERROR("jlink_usb_read_emu_result failed "
-					"(requested=1, result=%d)", result2);
-				return ERROR_JTAG_DEVICE_ERROR;
+				LOG_ERROR("jlink_usb_read_emu_result retried requested=1, result=%d, in_length=%i", result2,in_length);
+				/* Try again once, should only happen if (in_length%64==0) */
+				result2 = jlink_usb_read_emu_result(jlink_jtag);
+				if (1 != result2)
+				{
+					LOG_ERROR("jlink_usb_read_emu_result failed "
+						"(requested=1, result=%d)", result2);
+					return ERROR_JTAG_DEVICE_ERROR;
+				}
 			}
+
+			/* Check the result itself */
+			result2 = usb_emu_result_buffer[0];
 		}
+		else
+		{
+			/* Save the result, then remove it from return value */
+			result2 = usb_in_buffer[result--];
+		}
 
-		/* Check the result itself */
-		result2 = usb_emu_result_buffer[0];
+		if (result2)
+		{
+			LOG_ERROR("jlink_usb_message failed with result=%d)", result2);
+			return ERROR_JTAG_DEVICE_ERROR;
+		}
 	}
-	else
-	{
-		/* Save the result, then remove it from return value */
-		result2 = usb_in_buffer[result--];
-	}
 
-	if (result2)
-	{
-		LOG_ERROR("jlink_usb_message failed with result=%d)", result2);
-		return ERROR_JTAG_DEVICE_ERROR;
-	}
-
 	return result;
 }
 
@@ -937,7 +1031,7 @@
 		return -1;
 	}
 
-	result = usb_bulk_write_ex(jlink_jtag->usb_handle, JLINK_WRITE_ENDPOINT,
+	result = usb_bulk_write_ex(jlink_jtag->usb_handle, jlink_write_ep,
 		(char *)usb_out_buffer, out_length, JLINK_USB_TIMEOUT);
 
 	DEBUG_JTAG_IO("jlink_usb_write, out_length = %d, result = %d", out_length, result);
@@ -951,7 +1045,7 @@
 /* Read data from USB into in_buffer. */
 static int jlink_usb_read(jlink_jtag_t *jlink_jtag, int expected_size)
 {
-	int result = usb_bulk_read_ex(jlink_jtag->usb_handle, JLINK_READ_ENDPOINT,
+	int result = usb_bulk_read_ex(jlink_jtag->usb_handle, jlink_read_ep,
 		(char *)usb_in_buffer, expected_size, JLINK_USB_TIMEOUT);
 
 	DEBUG_JTAG_IO("jlink_usb_read, result = %d", result);
@@ -965,7 +1059,7 @@
 /* Read the result from the previous EMU cmd into result_buffer. */
 static int jlink_usb_read_emu_result(jlink_jtag_t *jlink_jtag)
 {
-	int result = usb_bulk_read_ex(jlink_jtag->usb_handle, JLINK_READ_ENDPOINT,
+	int result = usb_bulk_read_ex(jlink_jtag->usb_handle, jlink_read_ep,
 		(char *)usb_emu_result_buffer, 1 /* JLINK_EMU_RESULT_BUFFER_SIZE */,
 		JLINK_USB_TIMEOUT);
 
_______________________________________________
Openocd-development mailing list
Openocd-development@lists.berlios.de
https://lists.berlios.de/mailman/listinfo/openocd-development

Reply via email to