aboutsummaryrefslogtreecommitdiffstats
path: root/Projects/AVRISP-MKII/Lib/XPROG/XPROGTarget.c
diff options
context:
space:
mode:
authorDean Camera <dean@fourwalledcubicle.com>2009-12-29 14:43:03 +0000
committerDean Camera <dean@fourwalledcubicle.com>2009-12-29 14:43:03 +0000
commitb1dbd92c32022c2ec1601f6a6e51c5714a69c56c (patch)
tree6b32bb39caf32b9106f0fc303b7364bbe3a495f5 /Projects/AVRISP-MKII/Lib/XPROG/XPROGTarget.c
parente1c1c256192c099f5bfa23946c050aa5954aca4a (diff)
downloadlufa-b1dbd92c32022c2ec1601f6a6e51c5714a69c56c.tar.gz
lufa-b1dbd92c32022c2ec1601f6a6e51c5714a69c56c.tar.bz2
lufa-b1dbd92c32022c2ec1601f6a6e51c5714a69c56c.zip
Fixed AVRISP PDI race condition where the guard time between direction changes could be interpreted as a start bit. Fixed TPI interface lines not being changed correctly when in bit-banged TPI mode.
Diffstat (limited to 'Projects/AVRISP-MKII/Lib/XPROG/XPROGTarget.c')
-rw-r--r--Projects/AVRISP-MKII/Lib/XPROG/XPROGTarget.c137
1 files changed, 75 insertions, 62 deletions
diff --git a/Projects/AVRISP-MKII/Lib/XPROG/XPROGTarget.c b/Projects/AVRISP-MKII/Lib/XPROG/XPROGTarget.c
index 856b48903..c1f1a6316 100644
--- a/Projects/AVRISP-MKII/Lib/XPROG/XPROGTarget.c
+++ b/Projects/AVRISP-MKII/Lib/XPROG/XPROGTarget.c
@@ -279,33 +279,16 @@ void XPROGTarget_DisableTargetTPI(void)
*/
void XPROGTarget_SendByte(const uint8_t Byte)
{
-#if defined(XPROG_VIA_HARDWARE_USART)
/* Switch to Tx mode if currently in Rx mode */
if (!(IsSending))
- {
- PORTD |= (1 << 3);
- DDRD |= (1 << 3);
-
- UCSR1B |= (1 << TXEN1);
- UCSR1B &= ~(1 << RXEN1);
-
- IsSending = true;
- }
-
+ XPROGTarget_SetTxMode();
+
+#if defined(XPROG_VIA_HARDWARE_USART)
/* Wait until there is space in the hardware Tx buffer before writing */
while (!(UCSR1A & (1 << UDRE1)));
UCSR1A |= (1 << TXC1);
UDR1 = Byte;
#else
- /* Switch to Tx mode if currently in Rx mode */
- if (!(IsSending))
- {
- BITBANG_PDIDATA_PORT |= BITBANG_PDIDATA_MASK;
- BITBANG_PDIDATA_DDR |= BITBANG_PDIDATA_MASK;
-
- IsSending = true;
- }
-
/* Calculate the new USART frame data here while while we wait for a previous byte (if any) to finish sending */
uint16_t NewUSARTData = ((1 << 11) | (1 << 10) | (0 << 9) | ((uint16_t)Byte << 1) | (0 << 0));
@@ -332,37 +315,15 @@ void XPROGTarget_SendByte(const uint8_t Byte)
*/
uint8_t XPROGTarget_ReceiveByte(void)
{
-#if defined(XPROG_VIA_HARDWARE_USART)
/* Switch to Rx mode if currently in Tx mode */
if (IsSending)
- {
- while (!(UCSR1A & (1 << TXC1)));
- UCSR1A |= (1 << TXC1);
-
- UCSR1B &= ~(1 << TXEN1);
- UCSR1B |= (1 << RXEN1);
-
- DDRD &= ~(1 << 3);
- PORTD &= ~(1 << 3);
-
- IsSending = false;
- }
+ XPROGTarget_SetRxMode();
+#if defined(XPROG_VIA_HARDWARE_USART)
/* Wait until a byte has been received before reading */
while (!(UCSR1A & (1 << RXC1)) && TimeoutMSRemaining);
return UDR1;
#else
- /* Switch to Rx mode if currently in Tx mode */
- if (IsSending)
- {
- while (SoftUSART_BitCount);
-
- BITBANG_PDIDATA_DDR &= ~BITBANG_PDIDATA_MASK;
- BITBANG_PDIDATA_PORT &= ~BITBANG_PDIDATA_MASK;
-
- IsSending = false;
- }
-
/* Wait until a byte has been received before reading */
SoftUSART_BitCount = BITS_IN_USART_FRAME;
while (SoftUSART_BitCount && TimeoutMSRemaining);
@@ -375,19 +336,11 @@ uint8_t XPROGTarget_ReceiveByte(void)
/** Sends a BREAK via the USART to the attached target, consisting of a full frame of idle bits. */
void XPROGTarget_SendBreak(void)
{
-#if defined(XPROG_VIA_HARDWARE_USART)
/* Switch to Tx mode if currently in Rx mode */
if (!(IsSending))
- {
- PORTD |= (1 << 3);
- DDRD |= (1 << 3);
-
- UCSR1B &= ~(1 << RXEN1);
- UCSR1B |= (1 << TXEN1);
-
- IsSending = true;
- }
+ XPROGTarget_SetTxMode();
+#if defined(XPROG_VIA_HARDWARE_USART)
/* Need to do nothing for a full frame to send a BREAK */
for (uint8_t i = 0; i < BITS_IN_USART_FRAME; i++)
{
@@ -396,21 +349,81 @@ void XPROGTarget_SendBreak(void)
while (!(PIND & (1 << 5)));
}
#else
- /* Switch to Tx mode if currently in Rx mode */
- if (!(IsSending))
+ while (SoftUSART_BitCount);
+
+ /* Need to do nothing for a full frame to send a BREAK */
+ SoftUSART_Data = 0x0FFF;
+ SoftUSART_BitCount = BITS_IN_USART_FRAME;
+#endif
+}
+
+static void XPROGTarget_SetTxMode(void)
+{
+#if defined(XPROG_VIA_HARDWARE_USART)
+ /* Wait for a full cycle of the clock */
+ while (PIND & (1 << 5));
+ while (!(PIND & (1 << 5)));
+
+ PORTD |= (1 << 3);
+ DDRD |= (1 << 3);
+
+ UCSR1B &= ~(1 << RXEN1);
+ UCSR1B |= (1 << TXEN1);
+
+ IsSending = true;
+#else
+ while (SoftUSART_BitCount);
+
+ /* Wait for a full cycle of the clock */
+ SoftUSART_Data = 0x0001;
+ SoftUSART_BitCount = 1;
+ while (SoftUSART_BitCount);
+
+ if (XPROG_SelectedProtocol == XPRG_PROTOCOL_PDI)
{
BITBANG_PDIDATA_PORT |= BITBANG_PDIDATA_MASK;
BITBANG_PDIDATA_DDR |= BITBANG_PDIDATA_MASK;
-
- IsSending = true;
}
-
+ else
+ {
+ BITBANG_TPIDATA_PORT |= BITBANG_TPIDATA_MASK;
+ BITBANG_TPIDATA_DDR |= BITBANG_TPIDATA_MASK;
+ }
+#endif
+
+ IsSending = true;
+}
+
+static void XPROGTarget_SetRxMode(void)
+{
+#if defined(XPROG_VIA_HARDWARE_USART)
+ while (!(UCSR1A & (1 << TXC1)));
+ UCSR1A |= (1 << TXC1);
+
+ UCSR1B &= ~(1 << TXEN1);
+ UCSR1B |= (1 << RXEN1);
+
+ DDRD &= ~(1 << 3);
+ PORTD &= ~(1 << 3);
+#else
while (SoftUSART_BitCount);
- /* Need to do nothing for a full frame to send a BREAK */
- SoftUSART_Data = 0x0FFF;
- SoftUSART_BitCount = BITS_IN_USART_FRAME;
+ if (XPROG_SelectedProtocol == XPRG_PROTOCOL_PDI)
+ {
+ BITBANG_PDIDATA_DDR &= ~BITBANG_PDIDATA_MASK;
+ BITBANG_PDIDATA_PORT &= ~BITBANG_PDIDATA_MASK;
+ }
+ else
+ {
+ BITBANG_TPIDATA_DDR &= ~BITBANG_TPIDATA_MASK;
+ BITBANG_TPIDATA_PORT &= ~BITBANG_TPIDATA_MASK;
+ }
+
+ /* Wait until DATA line has been pulled up to idle by the target */
+ while (!(BITBANG_PDIDATA_PIN & BITBANG_PDIDATA_MASK));
#endif
+
+ IsSending = false;
}
#endif