Hi

The following patch is a first step towards support for sevaral AP in one dap.

- Adds a apsel variable, corresponding to the corresponding field in the DP SELECT register, to the swjdap structure. - adds a function swjdp_apselect(swjdp_common_t *swjdp,u8 apsel) to set this variable.
- adds two cortex_m3 interactive commands
cortex_m3 dap #n Shows the contents of ROM/Debug base register and AP ID Register cortex_m3 apsel #n Configures to use AP #n in subsequent memory accesses.

This should be a possible starting point to explore other debug configurations that the Cortex_M3

Tested on STM32 with no problems found. I dont have any A8 hardware.

Regards,
Magnus

Index: src/target/cortex_m3.c
===================================================================
--- src/target/cortex_m3.c	(revision 1454)
+++ src/target/cortex_m3.c	(working copy)
@@ -45,6 +45,8 @@
 /* cli handling */
 int cortex_m3_register_commands(struct command_context_s *cmd_ctx);
 int handle_cortex_m3_mask_interrupts_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
+int handle_cortex_m3_dap_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
+int handle_cortex_m3_apsel_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
 
 /* forward declarations */
 void cortex_m3_enable_breakpoints(struct target_s *target);
@@ -1581,6 +1583,8 @@
 	
 	cortex_m3_cmd = register_command(cmd_ctx, NULL, "cortex_m3", NULL, COMMAND_ANY, "cortex_m3 specific commands");		
 	register_command(cmd_ctx, cortex_m3_cmd, "maskisr", handle_cortex_m3_mask_interrupts_command, COMMAND_EXEC, "mask cortex_m3 interrupts ['on'|'off']");
+	register_command(cmd_ctx, cortex_m3_cmd, "dap", handle_cortex_m3_dap_command, COMMAND_EXEC, "dap info for ap [num] (default 0)");
+	register_command(cmd_ctx, cortex_m3_cmd, "apsel", handle_cortex_m3_apsel_command, COMMAND_EXEC, "select a different AP [num] (default 0)");
 	
 	return retval;
 }
@@ -1618,3 +1622,62 @@
 	
 	return ERROR_OK;
 }
+
+int handle_cortex_m3_dap_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
+{
+	target_t *target = get_current_target(cmd_ctx);
+	armv7m_common_t *armv7m = target->arch_info;
+	cortex_m3_common_t *cortex_m3 = armv7m->arch_info;
+	swjdp_common_t *swjdp = &cortex_m3->swjdp_info;
+
+	u32 dbgbase,apid;
+	u32 apsel,apselold;
+	u8 rev, mem_ap; 
+
+	apsel = 0;
+	apselold = swjdp->apsel;
+	if (argc > 0)
+	{	
+		apsel = strtoul(args[0], NULL, 0);
+	}
+
+	
+	swjdp_apselect(swjdp, apsel);
+	ahbap_read_reg_u32(swjdp, 0xF8, &dbgbase);
+	ahbap_read_reg_u32(swjdp, 0xFC, &apid);
+	swjdp_transaction_endcheck(swjdp);
+	swjdp_apselect(swjdp, apselold);
+	command_print(cmd_ctx, "ap debugbase 0x%8.8x", dbgbase);
+	command_print(cmd_ctx, "ap identification register 0x%8.8x", apid);
+	if (apid)
+	{
+		mem_ap = (apid>>16)&0x1;
+	}
+
+	return ERROR_OK;
+
+}
+
+int handle_cortex_m3_apsel_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
+{
+	target_t *target = get_current_target(cmd_ctx);
+	armv7m_common_t *armv7m = target->arch_info;
+	cortex_m3_common_t *cortex_m3 = armv7m->arch_info;
+	swjdp_common_t *swjdp = &cortex_m3->swjdp_info;
+
+	u32 apsel,apid;
+
+	apsel = 0;
+	if (argc > 0)
+	{	
+		apsel = strtoul(args[0], NULL, 0);
+	}
+
+	swjdp_apselect(swjdp, apsel);
+	ahbap_read_reg_u32(swjdp, (apsel<<24)|0xFC, &apid);
+	swjdp_transaction_endcheck(swjdp);
+	command_print(cmd_ctx, "ap %i selected, identification register 0x%8.8x", apsel, apid);
+
+	return ERROR_OK;
+
+}
 
Index: src/target/cortex_swjdp.c
===================================================================
--- src/target/cortex_swjdp.c	(revision 1454)
+++ src/target/cortex_swjdp.c	(working copy)
@@ -246,9 +246,10 @@
 		else
 		{
 			u32 dcb_dhcsr,nvic_shcsr, nvic_bfar, nvic_cfsr;
+			u32 ahbap_csv;
 
 			/* Print information about last AHBAP access */
-			LOG_ERROR("AHBAP: dp_select 0x%x, ap_csw 0x%x, ap_tar 0x%x", swjdp->dp_select_value, swjdp->ap_csw_value, swjdp->ap_tar_value);
+			LOG_ERROR("AHBAP Cached values: dp_select 0x%x, ap_csw 0x%x, ap_tar 0x%x", swjdp->dp_select_value, swjdp->ap_csw_value, swjdp->ap_tar_value);
 			if (ctrlstat & SSTICKYORUN)
 				LOG_ERROR("SWJ-DP OVERRUN - check clock or reduce jtag speed");
 
@@ -263,12 +264,20 @@
 
 			LOG_DEBUG("swjdp: status 0x%x", ctrlstat);
 
+			ahbap_read_reg_u32(swjdp, AHBAP_CSW, &ahbap_csv);
+			if ((retval=jtag_execute_queue())!=ERROR_OK)
+				return retval;
+			LOG_ERROR("Read AHBAP_CSW 0x%x", ahbap_csv);
+
+#if 0
 			/* Can we find out the reason for the error ?? */
+			/* WARNING This creates an infinite loop when memorymapped core registers cannot be accessed, and no info about SWJDP communicaton problems, REMOVE!!? */
 			ahbap_read_system_atomic_u32(swjdp, DCB_DHCSR, &dcb_dhcsr);
 			ahbap_read_system_atomic_u32(swjdp, NVIC_SHCSR, &nvic_shcsr);
 			ahbap_read_system_atomic_u32(swjdp, NVIC_CFSR, &nvic_cfsr);
 			ahbap_read_system_atomic_u32(swjdp, NVIC_BFAR, &nvic_bfar);
 			LOG_ERROR("dcb_dhcsr 0x%x, nvic_shcsr 0x%x, nvic_cfsr 0x%x, nvic_bfar 0x%x", dcb_dhcsr, nvic_shcsr, nvic_cfsr, nvic_bfar);
+#endif
 		}
 		if ((retval=jtag_execute_queue())!=ERROR_OK)
 			return retval;
@@ -294,14 +303,31 @@
 	return scan_inout_check_u32(swjdp, SWJDP_IR_DPACC, reg_addr, DPAP_READ, 0, value);
 }
 
+int swjdp_apselect(swjdp_common_t *swjdp,u8 apsel)
+{
+	u32 select;
+	select = (apsel<<24) & 0xFF000000;
+
+	if (select != swjdp->apsel)
+	{
+		swjdp->apsel = select;
+		/* Switchin AP invalidates cached values */
+		swjdp->dp_select_value = -1;
+		swjdp->ap_csw_value = -1;
+		swjdp->ap_tar_value = -1;
+	}
+
+	return ERROR_OK;
+}
+
 int swjdp_bankselect_apacc(swjdp_common_t *swjdp,u32 reg_addr)
 {
 	u32 select;
-	select = (reg_addr & 0xFF0000F0);
+	select = (reg_addr & 0x000000F0);
 
 	if (select != swjdp->dp_select_value)
 	{
-		swjdp_write_dpacc(swjdp, select, DP_SELECT);
+		swjdp_write_dpacc(swjdp, select | swjdp->apsel, DP_SELECT);
 		swjdp->dp_select_value = select;
 	}
 
@@ -686,7 +712,7 @@
 *                                                                                *
 * ahbap_read_buf_u32(swjdp_common_t *swjdp, u8 *buffer, int count, u32 address)  *
 *                                                                                *
-* Read block fast in target order (little endian) into a buffer                  *
+* Read block of memory fast in target order (little endian) into a buffer        *
 *                                                                                *
 **********************************************************************************/
 int ahbap_read_buf_u32(swjdp_common_t *swjdp, u8 *buffer, int count, u32 address)
@@ -922,6 +948,15 @@
 	return retval;
 }
 
+/*****************************************************************************
+*                                                                            *
+* ahbap_read_coreregister_u32(swjdp_common_t *swjdp, u32 *value, int regnum) *
+*                                                                            *
+* Read a u32 value from a processor core register using the NVIC/DCB         *
+* core debug component                                                       *
+*                                                                            *
+*****************************************************************************/
+
 int ahbap_read_coreregister_u32(swjdp_common_t *swjdp, u32 *value, int regnum)
 {
 	int retval;
@@ -981,6 +1016,7 @@
 
 	LOG_DEBUG(" ");
 
+	swjdp->apsel = 0;
 	swjdp->ap_csw_value = -1;
 	swjdp->ap_tar_value = -1;
 	swjdp->trans_mode = TRANS_MODE_ATOMIC;
Index: src/target/cortex_swjdp.h
===================================================================
--- src/target/cortex_swjdp.h	(revision 1454)
+++ src/target/cortex_swjdp.h	(working copy)
@@ -67,7 +67,7 @@
 #define CSW_ADDRINC_PACKED	(2<<4)
 #define CSW_HPROT			(1<<25)
 #define CSW_MASTER_DEBUG	(1<<29)
-#define CSW_DBGSWENABLE		(1<<31)
+#define CSW_DBGSWENABLE		(1<<31) /* Remove this, reserved bit, Cortex-M3 TRM 11.39, different from CoreSight DAP-Lite */
 
 /* transaction mode */
 #define TRANS_MODE_NONE			0
@@ -87,6 +87,8 @@
 	arm_jtag_t *jtag_info;
 	/* Control config */
 	u32 dp_ctrl_stat;
+	/* Support for several AP's in one DAP */
+	u32 apsel;
 	/* Register select cache */
 	u32 dp_select_value;
 	u32 ap_csw_value;
@@ -102,6 +104,8 @@
 /* extern int swjdp_write_apacc(swjdp_common_t *swjdp, u32 value, u8 reg_addr); */
 extern int swjdp_read_dpacc(swjdp_common_t *swjdp, u32 *value, u8 reg_addr);
 /* extern int swjdp_read_apacc(swjdp_common_t *swjdp, u32 *value, u8 reg_addr); */
+int swjdp_apselect(swjdp_common_t *swjdp,u8 apsel);
+
 extern int ahbap_write_reg(swjdp_common_t *swjdp, u32 reg_addr, u8* out_value_buf);
 extern int ahbap_read_reg(swjdp_common_t *swjdp, u32 reg_addr, u8 *in_value_buf);
 
_______________________________________________
Openocd-development mailing list
Openocd-development@lists.berlios.de
https://lists.berlios.de/mailman/listinfo/openocd-development

Reply via email to