/I2C_Telemetry/trunk/uart.c |
---|
54,6 → 54,7 |
#include <string.h> |
#include <avr/pgmspace.h> |
#include <inttypes.h> |
#include <util/delay_basic.h> |
#include "main.h" |
#include "uart.h" |
#include "libtel.h" |
164,7 → 165,7 |
tmp_tx = UART0_tx_buffer.pData[UART0_tx_buffer.Position++]; // read next byte from txd buffer |
UDR0 = tmp_tx; |
// if terminating character or end of txd buffer reached |
if((tmp_tx == '\0') || (UART0_tx_buffer.Position >= UART0_tx_buffer.DataBytes)) |
if(UART0_tx_buffer.Position >= UART0_tx_buffer.DataBytes) |
{ |
Buffer_Clear(&UART0_tx_buffer); // clear txd buffer, that unlocks it. |
} |
282,7 → 283,7 |
} |
} |
// if a new frame has been created, initiate transmission |
if(UART0_tx_buffer.Locked) UDR0 = UART0_tx_buffer.pData[UART0_tx_buffer.Position++]; // initiates the transmittion (continued in the TX ISR) |
if(UART0_tx_buffer.Locked && (UART0_tx_buffer.Position == 0)) UDR0 = UART0_tx_buffer.pData[UART0_tx_buffer.Position++]; // initiates the transmittion (continued in the TX ISR) |
} |
438,12 → 439,11 |
void USART0_SetBaudrate(uint32_t baudrate) |
{ |
uint16_t ubrr; |
uint8_t sreg = SREG; |
// wait for last bytes to send |
loop_until_bit_is_set(UCSR0A, UDRE0); |
// disable all interrupts before configuration |
cli(); |
_delay_loop_2(1000); |
// disable RX-Interrupt |
UCSR0B &= ~(1 << RXCIE0); |
472,45 → 472,53 |
// enable TX-Interrupt |
UCSR0B |= (1 << TXCIE0); |
// restore global interrupt flags |
SREG = sreg; |
} |
void UART0_ConnectTo(uint8_t direction) |
{ |
// wait for last bytes to send |
// wait for last bytes to send if pending |
loop_until_bit_is_set(UCSR0A, UDRE0); |
_delay_loop_2(1000); |
// disable RX-Interrupt |
UCSR0B &= ~(1 << RXCIE0); |
// disable TX-Interrupt |
UCSR0B &= ~(1 << TXCIE0); |
switch(direction) |
{ |
case PC: |
TXD_GPS_OFF; |
RXD_GPS_OFF; |
TXD_PC_ON; |
RXD_PC_ON; |
TXD_GPS_OFF; |
RXD_GPS_OFF; |
break; |
case GPS: |
RXD_PC_OFF; |
TXD_PC_OFF; |
RXD_GPS_ON; |
TXD_GPS_ON; |
RXD_PC_OFF; |
TXD_PC_OFF; |
break; |
case PC_GPS: |
default: |
RXD_GPS_OFF; |
TXD_PC_ON; |
RXD_PC_ON; |
TXD_GPS_ON; |
RXD_GPS_OFF; |
break; |
} |
asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); |
asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); |
asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); asm volatile ("nop"); |
// flush receive buffer |
while ( UCSR0A & (1<<RXC0) ) UDR0; |
// enable interrupts at the end |
// enable RX-Interrupt |
UCSR0B |= (1 << RXCIE0); |
// enable TX-Interrupt |
UCSR0B |= (1 << TXCIE0); |
} |
/****************************************************************/ |
/I2C_Telemetry/trunk/uart.h |
---|
4,13 → 4,13 |
//Baud rate of the USART |
#define USART0_BAUD 57600L |
#define RXD_PC_ON {PORTD = ~(1<<PORTD4); DDRD &= ~(1<<DDD4);} // input tristate |
#define RXD_PC_ON {PORTD |= (1<<PORTD4); DDRD &= ~(1<<DDD4);} // input pullup |
#define RXD_PC_OFF {DDRD |= (1<<DDD4); PORTD |= (1<<PORTD4);} // output high |
#define RXD_GPS_ON {PORTD = ~(1<<PORTD5); DDRD &= ~(1<<DDD5);} // input tristate |
#define RXD_GPS_ON {PORTD |= (1<<PORTD5); DDRD &= ~(1<<DDD5);} // input pullup |
#define RXD_GPS_OFF {DDRD |= (1<<DDD5); PORTD |= (1<<PORTD5);} // output high |
#define TXD_GPS_ON {PORTB = ~(1<<PORTB2); DDRB &= ~(1<<DDB2);} // input tristate |
#define TXD_GPS_ON {PORTD |= (1<<PORTB2); DDRB &= ~(1<<DDB2);} // input pullup |
#define TXD_GPS_OFF {DDRB |= (1<<DDB2); PORTB |= (1<<PORTB2);} // output high |
#define TXD_PC_ON {PORTC = ~(1<<PORTC5); DDRC &= ~(1<<DDC5);} // input tristate |
#define TXD_PC_ON {PORTD |= (1<<PORTC5); DDRC &= ~(1<<DDC5);} // input pullup |
#define TXD_PC_OFF {DDRC |= (1<<DDC5); PORTC |= (1<<PORTC5);} // output high |
// bitmask for UART_VersionInfo_t.HardwareError[0] |
/I2C_Telemetry/trunk/ubx.c |
---|
324,28 → 324,29 |
RxHdr.Length += ((uint16_t)c)<<8; // high byte last |
if (RxHdr.Length >= UBX_MSG_DATA_SIZE) |
{ |
ubxState = UBXSTATE_IDLE; |
ubxState = UBXSTATE_IDLE; |
} |
else |
{ |
cka += c; |
ckb += cka; |
RxBytes = 0; // reset data byte counter |
ubxState = UBXSTATE_DATA; |
cka += c; |
ckb += cka; |
RxBytes = 0; // reset data byte counter |
ubxState = UBXSTATE_DATA; |
} |
break; |
case UBXSTATE_DATA: // collecting data |
if (RxBytes < UBX_MSG_DATA_SIZE) |
{ |
RxData[RxBytes++] = c; // copy curent data byte if any space is left |
cka += c; |
ckb += cka; |
if (RxBytes >= RxHdr.Length) ubxState = UBXSTATE_CKA; // switch to next state if all data have been received |
RxData[RxBytes++] = c; // copy curent data byte if any space is left |
cka += c; |
ckb += cka; |
if (RxBytes >= RxHdr.Length) ubxState = UBXSTATE_CKA; // switch to next state if all data have been received |
} |
else // rx buffer overrun |
{ |
ubxState = UBXSTATE_IDLE; |
ubxState = UBXSTATE_IDLE; |
} |
break; |
354,67 → 355,66 |
if (c == cka) ubxState = UBXSTATE_CKB; |
else |
{ |
ubxState = UBXSTATE_IDLE; |
ubxState = UBXSTATE_IDLE; |
} |
break; |
case UBXSTATE_CKB: |
if (c == ckb) |
{ // checksum is ok |
if (c == ckb) |
{ // checksum is ok |
switch(RxHdr.Class) |
{ |
case UBX_CLASS_NAV: |
switch(RxHdr.Id) |
{ |
case UBX_ID_POSLLH: // geodetic position |
memcpy((uint8_t*)&UbxPosLlh, RxData, RxHdr.Length); |
UbxPosLlh.Status = NEWDATA; |
break; |
switch(RxHdr.Class) |
{ |
case UBX_CLASS_NAV: |
switch(RxHdr.Id) |
{ |
case UBX_ID_POSLLH: // geodetic position |
memcpy((uint8_t*)&UbxPosLlh, RxData, RxHdr.Length); |
UbxPosLlh.Status = NEWDATA; |
break; |
case UBX_ID_VELNED: // velocity vector in tangent plane |
memcpy((uint8_t*)&UbxVelNed, RxData, RxHdr.Length); |
UbxVelNed.Status = NEWDATA; |
break; |
case UBX_ID_VELNED: // velocity vector in tangent plane |
memcpy((uint8_t*)&UbxVelNed, RxData, RxHdr.Length); |
UbxVelNed.Status = NEWDATA; |
break; |
case UBX_ID_SOL: // navigation solution |
memcpy((uint8_t*)&UbxSol, RxData, RxHdr.Length); |
UbxSol.Status = NEWDATA; |
break; |
case UBX_ID_SOL: // navigation solution |
memcpy((uint8_t*)&UbxSol, RxData, RxHdr.Length); |
UbxSol.Status = NEWDATA; |
break; |
default: |
break; |
} // EOF switch(Id) |
Update_GPSData(); |
break; |
default: |
break; |
} // EOF switch(Id) |
Update_GPSData(); |
break; |
default: // any other class |
break; |
} // EOF switch(class) |
default: // any other class |
break; |
} // EOF switch(class) |
// check generic msg filter |
if(UbxMsg.Status != NEWDATA) |
{ // msg buffer is free |
if(((UbxMsg.Hdr.Class & UbxMsg.ClassMask) == (RxHdr.Class & UbxMsg.ClassMask)) && ((UbxMsg.Hdr.Id & UbxMsg.IdMask) == (RxHdr.Id & UbxMsg.IdMask))) |
{ // msg matches to the filter criteria |
UbxMsg.Status = INVALID; |
UbxMsg.Hdr.Class = RxHdr.Class; |
UbxMsg.Hdr.Id = RxHdr.Id; |
UbxMsg.Hdr.Length = RxHdr.Length; |
if(UbxMsg.Hdr.Length <= UBX_MSG_DATA_SIZE) |
{ // copy data block |
memcpy(UbxMsg.Data, RxData, RxHdr.Length); |
UbxMsg.Status = NEWDATA; |
} |
} // EOF filter matches |
} // EOF != INVALID |
}// EOF crc ok |
ubxState = UBXSTATE_IDLE; // ready to parse new data |
break; |
// check generic msg filter |
if(UbxMsg.Status != NEWDATA) |
{ // msg buffer is free |
if(((UbxMsg.Hdr.Class & UbxMsg.ClassMask) == (RxHdr.Class & UbxMsg.ClassMask)) && ((UbxMsg.Hdr.Id & UbxMsg.IdMask) == (RxHdr.Id & UbxMsg.IdMask))) |
{ // msg matches to the filter criteria |
UbxMsg.Status = INVALID; |
UbxMsg.Hdr.Class = RxHdr.Class; |
UbxMsg.Hdr.Id = RxHdr.Id; |
UbxMsg.Hdr.Length = RxHdr.Length; |
if(UbxMsg.Hdr.Length <= UBX_MSG_DATA_SIZE) |
{ // copy data block |
memcpy(UbxMsg.Data, RxData, RxHdr.Length); |
UbxMsg.Status = NEWDATA; |
} |
} // EOF filter matches |
} // EOF != INVALID |
}// EOF crc ok |
ubxState = UBXSTATE_IDLE; // ready to parse new data |
break; |
default: // unknown ubx state |
ubxState = UBXSTATE_IDLE; |
break; |
ubxState = UBXSTATE_IDLE; |
break; |
} |
} |