Skip to content

Commit ad7c663

Browse files
committed
Fix #1249
Fix #1249
1 parent 2caece5 commit ad7c663

3 files changed

Lines changed: 23 additions & 27 deletions

File tree

megaavr/cores/megatinycore/UART.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -310,7 +310,7 @@
310310
"push r25" "\n\t"
311311
"push r26" "\n\t"
312312
"push r27" "\n\t"
313-
"set" "\n\t" // SEt the T flag - we use this to determine how we got here and hence whether to rjmp to end of poll or reti
313+
"set" "\n\t" // Set the T flag - we use this to determine how we got here and hence whether to rjmp to end of poll or reti
314314
"_poll_dre:" "\n\t"
315315
"push r28" "\n\t"
316316
"push r29" "\n\t"

megaavr/cores/megatinycore/UART_constants.h

Lines changed: 12 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -112,28 +112,21 @@
112112
#define PIN_SERIAL_XDIR (3)
113113

114114
/* Modifier Definitions - these can be OR'ed with the other definition to turn on features like one-wire half duplex and more */
115-
#if !defined(USART_RS485_0_bm)
116-
#define USART_RS485_0_bm USART_RS4850_bm
117-
#if defined(USART_RS4851_bm)
118-
#define USART_RS485_1_bm USART_RS4851_bm
119-
#endif
120-
#elif !defined(USART_RS4850_bm)
121-
#define USART_RS4850_bm USART_RS485_0_bm
122-
#if defined(USART_RS485_1_bm)
123-
#define USART_RS4851_bm USART_RS485_1_bm
124-
#endif
115+
#if (!defined(USART_RS485_1_bm))
116+
#define USART_RS485_1_bm (0x02)
125117
#endif
126-
#define SERIAL_RS485 (((uint16_t) USART_RS485_0_bm) << 8)// 0x0100
127-
#if defined(USART_RS485_1_bm)
128-
#define SERIAL_RS485_OTHER (((uint16_t) USART_RS485_1_bm) << 9)// 0x0200 tinyAVR 0/1
118+
#if (!defined(USART_RS485_0_bm))
119+
#define USART_RS485_0_bm (0x01)
129120
#endif
121+
#define SERIAL_RS485 ((uint16_t) (USART_RS485_0_bm << 8)) // 0x0100
122+
#define SERIAL_RS485_OTHER ((uint16_t) (USART_RS485_1_bm << 8)) // 0x0200 tinyAVR 0/1
130123

131-
#define SERIAL_OPENDRAIN ((uint16_t) 0x0400)// 0x0400
132-
#define SERIAL_LOOPBACK (((uint16_t) USART_LBME_bm) << 8)// 0x0800
133-
#define SERIAL_TX_ONLY (((uint16_t) USART_RXEN_bm) << 8)// 0x8000 The TXEN/RXEN bits are swapped - we invert the meaning of this bit.
134-
#define SERIAL_RX_ONLY (((uint16_t) USART_TXEN_bm) << 8)// 0x4000 so if not specified, you get a serial port with both pins. Do not specify both. That will not enable anything.
135-
#define SERIAL_EVENT_RX ((uint16_t) 0x2000)// 0x2000
136-
//#define SERIAL_MODE_SYNC Defined Above // 0x0040 - works much like a modifier to enable synchronous mode.
124+
#define SERIAL_OPENDRAIN ((uint16_t) 0x0400) // 0x0400
125+
#define SERIAL_LOOPBACK (((uint16_t) USART_LBME_bm) << 8) // 0x0800
126+
#define SERIAL_EVENT_RX ((uint16_t) 0x2000) // 0x2000
127+
#define SERIAL_RX_ONLY (((uint16_t) USART_TXEN_bm) << 8) // 0x4000 so if not specified, you get a serial port with both pins. Do not specify both. That will not enable anything.
128+
#define SERIAL_TX_ONLY (((uint16_t) USART_RXEN_bm) << 8) // 0x8000 The TXEN/RXEN bits are swapped - we invert the meaning of this bit.
129+
//#define SERIAL_MODE_SYNC Defined Above // 0x0040 - works much like a modifier to enable synchronous mode.
137130
// See the Serial reference for more information as additional steps are required
138131
#define SERIAL_HALF_DUPLEX (SERIAL_LOOPBACK | SERIAL_OPENDRAIN)
139132
//

megaavr/extras/Ref_Serial.md

Lines changed: 10 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -133,7 +133,9 @@ The "other" RS485 mode, according to the ATtiny3216/3217 datasheet:
133133
"Writing RS485[1] to `1` enables the RS-485 mode which automatically sets the TXD pin to output one clock cycle
134134
before starting transmission and sets it back to input when the transmission is complete."
135135

136-
Obviously this begs the question of how any of the devices involved are supposed to prevent collisions - I don't think there *is* a way. That would explain why this feature was removed from the Dx-series documentation (it was present in the initial DA-series IO headers, and is likely still in the hardware...).
136+
Obviously this begs the question of how any of the devices involved are supposed to prevent collisions - I don't think there *is* a way. That would explain why this feature was removed from the Dx-series documentation. I was suspecting this was going to get quietly killed, but it seems to in fact be coming back with the V2 USART debuting on the LA and likely EC-series parts, under the name of hardware flow control.
137+
138+
Yes, serial will need total reimplementation.
137139

138140

139141

@@ -159,10 +161,10 @@ Below is an unabridged list of the versions:
159161
void printHexln(const double f, bool s = 0) {_prtHxdw((uint8_t *) &f, s); println();} // compiler knows the difference.
160162
void printHexln(const int32_t d, bool s = 0) {_prtHxdw((uint8_t *) &d, s); println();} // with just float, it can't tell if an
161163
void printHexln(const uint32_t l, bool s = 0) {_prtHxdw((uint8_t *) &l, s); println();} // a "long" "unsigned long" or "float"
162-
uint8_t * printHex( uint8_t* p, uint8_t len, char sep = 0 ); // is intended when passing a floating point literal.
163-
uint16_t * printHex( uint16_t* p, uint8_t len, char sep = 0, bool s = 0); // But it works if we provide a copy of printHex for double
164-
volatile uint8_t * printHex(volatile uint8_t* p, uint8_t len, char sep = 0 ); // Anomalies were observed with the above when used on the
165-
volatile uint16_t * printHex(volatile uint16_t* p, uint8_t len, char sep = 0, bool s = 0); // extended I/O space. Nothing definitive was found.
164+
uint8_t * printHex( uint8_t* p, uint8_t len, char sep = 0 );
165+
uint16_t * printHex( uint16_t* p, uint8_t len, char sep = 0, bool s = 0);
166+
volatile uint8_t * printHex(volatile uint8_t* p, uint8_t len, char sep = 0 );
167+
volatile uint16_t * printHex(volatile uint16_t* p, uint8_t len, char sep = 0, bool s = 0);
166168
```
167169
168170
There are two particular features worth noting in addition to the correct number of leading zeros, and the fact that it is not horrendously bloated like full serial print.
@@ -213,7 +215,6 @@ Many peripherals have a couple of 16-bit registers, amongst a sea of 8-bit ones.
213215
This starts the serial port. Options should be made by combining the constant referring to the desired character size, parity and stop bit length, zero or more of the modifiers below
214216
215217
#### Basic USART options
216-
217218
| Data Size | Parity | 1 stop bit | 2 stop bit |
218219
|-----------|--------|------------|------------|
219220
| 5 bit | NONE | SERIAL_5N1 | SERIAL_5N2 |
@@ -229,9 +230,11 @@ This starts the serial port. Options should be made by combining the constant re
229230
| 7 bit | ODD | SERIAL_7O1 | SERIAL_7O2 |
230231
| 8 bit | ODD | SERIAL_8O1 | SERIAL_8O2 |
231232
233+
**Tip**: SERIAL_8N2 is much more robust to clock variation than SERIAL_8N1. I advocate defaulting to using two stop bits unless there's a compelling reason not to (there almost never is, because any signal that could be output with 2 stop bits selected could also have been output idf only 1 stop bit was selected, if you assume that
232234
233235
#### Modifiers
234236
* SERIAL_RS485 - Enables RS485 mode.
237+
* SERIAL_RS485_OTHER - sets the othger RS485 bit (if present) or attempts to (if not). It is unclear whether this bit is setable and if settable, whether it has any function. This feature returns as hardware flow control in the refreshged USART coming on the LA.
235238
* SERIAL_OPENDRAIN - Sets port to open-drain mode
236239
* SERIAL_LOOPBACK - Enables single wire operation and internally connects tx to rx.
237240
* SERIAL_TX_ONLY - Enables only Tx.
@@ -468,7 +471,7 @@ While there's always some dead time between bits, that is usually *very* small,
468471
469472
470473
### How bad baud rate calculation used to be
471-
This chart shows what baud rates will work at what system clocks, on classic AVRs and modern AVRs. the difference is shocking.
474+
This chart shows what baud rates will work at what system clocks, on classic AVRs and modern AVRs. the difference is shocking.
472475
[AVR Baud Rate Accuracy Chart](https://docs.google.com/spreadsheets/d/1rzxFOs6a89jr69ouCdZp8Za1PuUdj1u1IoepTaHVFPk/edit?usp=sharing)
473476
474477
It was mentioned previously that one of most common places to encounter grossly inaccurate baud rates is classic AVRs. This example illustrates just *how bad* one of the most popular baud rate was on classic AVRs, namely 115200 baud. "Well it says the baud rate can be up to 1/8th the system clock, and I'm running at 8 MHz, no problem" you think "And see, it talks just fine to my other classic AVR". Nope. When you do this, you've dug a big hole, covered it with a tablecloth and waited until the sun went down. Adding a modern AVR or anything with a decent baud rate generator is then taking a late night stroll in the area of that covered hole. You're begging for trouble

0 commit comments

Comments
 (0)