From cd0bd7bf90e7e64a42b1efcee5a60cfdfc91d7a2 Mon Sep 17 00:00:00 2001
From: Dean Camera <dean@fourwalledcubicle.com>
Date: Sat, 9 Jun 2012 13:00:56 +0000
Subject: [PATCH] Added new JTAG_ENABLE() macro for the AVR8 architecture.
 Fixed the JTAG_DISABLE() macro clearing all other bits in MCUSR when called.

Moved the XPLAIN board specific bootloader entry condition code to the Application_Jump_Check() function of the DFU bootloader, added support for the original XPLAIN board to the CDC class bootloader.
---
 Bootloaders/CDC/BootloaderCDC.c    | 21 +++++++++++++++++
 Bootloaders/DFU/BootloaderDFU.c    | 38 +++++++++++++++++-------------
 LUFA/Common/ArchitectureSpecific.h | 20 +++++++++++++++-
 LUFA/DoxygenPages/ChangeLog.txt    |  4 +++-
 4 files changed, 64 insertions(+), 19 deletions(-)

diff --git a/Bootloaders/CDC/BootloaderCDC.c b/Bootloaders/CDC/BootloaderCDC.c
index ef68e148c..dcfa978e3 100644
--- a/Bootloaders/CDC/BootloaderCDC.c
+++ b/Bootloaders/CDC/BootloaderCDC.c
@@ -70,8 +70,29 @@ uint32_t MagicBootKey ATTR_NO_INIT;
  */
 void Application_Jump_Check(void)
 {
+	bool JumpToApplication = false;
+
+	#if ((BOARD == BOARD_XPLAIN) || (BOARD == BOARD_XPLAIN_REV1))
+		/* Disable JTAG debugging */
+		JTAG_DISABLE();
+
+		/* Enable pull-up on the JTAG TCK pin so we can use it to select the mode */
+		PORTF |= (1 << 4);
+		Delay_MS(10);
+
+		/* If the TCK pin is not jumpered to ground, start the user application instead */
+		JumpToApplication |= ((PINF & (1 << 4)) != 0);
+
+		/* Re-enable JTAG debugging */
+		JTAG_ENABLE();
+	#endif
+
 	/* If the reset source was the bootloader and the key is correct, clear it and jump to the application */
 	if ((MCUSR & (1 << WDRF)) && (MagicBootKey == MAGIC_BOOT_KEY))
+	  JumpToApplication |= true;
+
+	/* If a request has been made to jump to the user application, honor it */
+	if (JumpToApplication)
 	{
 		/* Turn off the watchdog */
 		MCUSR &= ~(1<<WDRF);
diff --git a/Bootloaders/DFU/BootloaderDFU.c b/Bootloaders/DFU/BootloaderDFU.c
index f5c8d170e..64850e3bb 100644
--- a/Bootloaders/DFU/BootloaderDFU.c
+++ b/Bootloaders/DFU/BootloaderDFU.c
@@ -106,8 +106,29 @@ uint32_t MagicBootKey ATTR_NO_INIT;
  */
 void Application_Jump_Check(void)
 {
+	bool JumpToApplication = false;
+
+	#if ((BOARD == BOARD_XPLAIN) || (BOARD == BOARD_XPLAIN_REV1))
+		/* Disable JTAG debugging */
+		JTAG_DISABLE();
+
+		/* Enable pull-up on the JTAG TCK pin so we can use it to select the mode */
+		PORTF |= (1 << 4);
+		Delay_MS(10);
+
+		/* If the TCK pin is not jumpered to ground, start the user application instead */
+		JumpToApplication |= ((PINF & (1 << 4)) != 0);
+
+		/* Re-enable JTAG debugging */
+		JTAG_ENABLE();
+	#endif
+
 	/* If the reset source was the bootloader and the key is correct, clear it and jump to the application */
 	if ((MCUSR & (1 << WDRF)) && (MagicBootKey == MAGIC_BOOT_KEY))
+	  JumpToApplication |= true;
+
+	/* If a request has been made to jump to the user application, honor it */
+	if (JumpToApplication)
 	{
 		/* Turn off the watchdog */
 		MCUSR &= ~(1<<WDRF);
@@ -130,23 +151,6 @@ int main(void)
 	/* Configure hardware required by the bootloader */
 	SetupHardware();
 
-	#if ((BOARD == BOARD_XPLAIN) || (BOARD == BOARD_XPLAIN_REV1))
-	/* Disable JTAG debugging */
-	MCUCR |= (1 << JTD);
-	MCUCR |= (1 << JTD);
-
-	/* Enable pull-up on the JTAG TCK pin so we can use it to select the mode */
-	PORTF |= (1 << 4);
-	Delay_MS(10);
-
-	/* If the TCK pin is not jumpered to ground, start the user application instead */
-	RunBootloader = (!(PINF & (1 << 4)));
-
-	/* Re-enable JTAG debugging */
-	MCUCR &= ~(1 << JTD);
-	MCUCR &= ~(1 << JTD);
-	#endif
-
 	/* Turn on first LED on the board to indicate that the bootloader has started */
 	LEDs_SetAllLEDs(LEDS_LED1);
 
diff --git a/LUFA/Common/ArchitectureSpecific.h b/LUFA/Common/ArchitectureSpecific.h
index f7dca6631..1a05be812 100644
--- a/LUFA/Common/ArchitectureSpecific.h
+++ b/LUFA/Common/ArchitectureSpecific.h
@@ -65,6 +65,24 @@
 		/* Macros: */
 			#if (ARCH == ARCH_AVR8) || (ARCH == ARCH_XMEGA) || defined(__DOXYGEN__)
 				#if (ARCH == ARCH_AVR8) || defined(__DOXYGEN__)
+					/** Re-enables the AVR's JTAG bus in software, until a system reset. This will re-enable JTAG debugging
+					 *  interface after is has been disbled in software via \ref JTAG_DISABLE().
+					 *
+					 *  \note This macro is not available for all architectures.
+					 */
+					#define JTAG_ENABLE()                  MACROS{                                      \
+																	__asm__ __volatile__ (               \
+																	"in __tmp_reg__,__SREG__" "\n\t"     \
+																	"cli" "\n\t"                         \
+																	"out %1, %0" "\n\t"                  \
+																	"out __SREG__, __tmp_reg__" "\n\t"   \
+																	"out %1, %0" "\n\t"                  \
+																	:                                    \
+																	: "r" (MCUCR & ~(1 << JTD)),         \
+																	  "M" (_SFR_IO_ADDR(MCUCR))          \
+																	: "r0");                             \
+															}MACROE
+
 					/** Disables the AVR's JTAG bus in software, until a system reset. This will override the current JTAG
 					 *  status as set by the JTAGEN fuse, disabling JTAG debugging and reverting the JTAG pins back to GPIO
 					 *  mode.
@@ -79,7 +97,7 @@
 																	"out __SREG__, __tmp_reg__" "\n\t"   \
 																	"out %1, %0" "\n\t"                  \
 																	:                                    \
-																	: "r" (1 << JTD),                    \
+																	: "r" (MCUCR | (1 << JTD)),          \
 																	  "M" (_SFR_IO_ADDR(MCUCR))          \
 																	: "r0");                             \
 															}MACROE
diff --git a/LUFA/DoxygenPages/ChangeLog.txt b/LUFA/DoxygenPages/ChangeLog.txt
index 14c9ef0b3..13c7b55ae 100644
--- a/LUFA/DoxygenPages/ChangeLog.txt
+++ b/LUFA/DoxygenPages/ChangeLog.txt
@@ -18,7 +18,8 @@
   *   - Added new Pipe_ConfigurePipeTable() function
   *   - Added build test to verify correct compilation of all board drivers using all driver APIs
   *   - Added build test to verify correct compilation of all bootloaders using all supported devices  
-  *   - Added build test to verify that there are no detectable errors in the codebase via static analysis 
+  *   - Added build test to verify that there are no detectable errors in the codebase via static analysis
+  *   - Added new JTAG_ENABLE() macro for the AVR8 architecture
   *  - Library Applications:
   *   - Modified the CDC Host demos to set a default CDC Line Encoding on enumerated devices
   *   - Added Dataflash operational checks and aborts to all projects using the Dataflash to ensure it is working correctly before use
@@ -66,6 +67,7 @@
   *     the stack (thanks to Jonathan Hudgins)
   *   - Fixed broken MIDI host driver MIDI_Host_ReceiveEventPacket() function due to not unfreezing the MIDI data IN pipe before use (thanks to Michael Brown)
   *   - Fixed swapped Little Endian/Big Endian endpoint and pipe write code for the UC3 devices (thanks to Andrew Chu)
+  *   - Fixed the JTAG_DISABLE() macro clearing all other bits in MCUSR when called
   *  - Library Applications:
   *   - Fixed error in the AVRISP-MKII programmer when ISP mode is used at 64KHz (thanks to Ben R. Porter)
   *   - Fixed AVRISP-MKII programmer project failing to compile for the U4 chips when VTARGET_ADC_CHANNEL is defined to an invalid channel and NO_VTARGET_DETECT is
-- 
GitLab