UART Transmission with atmega328p
-
- Posts: 103
- http://meble-kuchenne.info.pl
- Joined: Mon Dec 07, 2020 12:47 pm
- Been thanked: 1 time
Re: UART Transmission with atmega328p
Your suggestion to use the checksum is perhaps a good idea. I have read that all transmitted bytes are subtracted from 0xFFFF. With a 6-channel receiver, for example, the remaining channels (i.e. 8) are filled with 0x05DC. But only the sender knows the exact data of the 6 channels it is sending and can check the checksum, or am I making a mistake?
-
- Valued Contributor
- Posts: 1628
- Joined: Wed Dec 09, 2020 9:37 pm
- Has thanked: 142 times
- Been thanked: 761 times
Re: UART Transmission with atmega328p
It would 'normally' be transmitted as the last 2 bytes of the message - and should be correct for the packet to be valid.
Should be possible to check using a downloaded packet - if it's just a subtraction then all should be well - some checksum use a CRC and life would be harder unless the docs give a clue.
Should be possible to check using a downloaded packet - if it's just a subtraction then all should be well - some checksum use a CRC and life would be harder unless the docs give a clue.
Re: UART Transmission with atmega328p
That means I have to subtract the 6 words of the 6 received channels from 0xFFFF, then subtract 8 times 0x05DC for the unused channels and then compare that with the last word (the checksum), right?
-
- Valued Contributor
- Posts: 1628
- Joined: Wed Dec 09, 2020 9:37 pm
- Has thanked: 142 times
- Been thanked: 761 times
Re: UART Transmission with atmega328p
Well worth a try - it might also include the header as well.
What values do you receive on the unused channels (ie do you get 0x05DC or 'random' values)
If it works - easy to do in a loop in the code.
What values do you receive on the unused channels (ie do you get 0x05DC or 'random' values)
If it works - easy to do in a loop in the code.
Re: UART Transmission with atmega328p
Yes exactly, the unused channels always deliver 0x05DC.
You just have to think about what kind of receiver you have, 6 or 8 channel etc.
Another stupid question: when do you use parameters and when do you use variables? You have also defined parameters in your chart. I haven't used them yet.
You just have to think about what kind of receiver you have, 6 or 8 channel etc.
Another stupid question: when do you use parameters and when do you use variables? You have also defined parameters in your chart. I haven't used them yet.
-
- Valued Contributor
- Posts: 1628
- Joined: Wed Dec 09, 2020 9:37 pm
- Has thanked: 142 times
- Been thanked: 761 times
Re: UART Transmission with atmega328p
I would always favour local variables (and function parameters) over global variables. Global variables are sometimes a necessary evil (for example for the interrupt handler). If you create a large program then it makes life much simpler and avoids many possible errors.
It's worth splitting your program into small (hopefully) easily understood functions - the overhead is very small to use them
Where possible functions should avoid having side effects - they can (and will) come back to bite you at some stage with a weird crash.
It's worth splitting your program into small (hopefully) easily understood functions - the overhead is very small to use them
Where possible functions should avoid having side effects - they can (and will) come back to bite you at some stage with a weird crash.
-
- Valued Contributor
- Posts: 1628
- Joined: Wed Dec 09, 2020 9:37 pm
- Has thanked: 142 times
- Been thanked: 761 times
Re: UART Transmission with atmega328p
A quick thought on checksums after some googling.
As far as I can tell - the value (the last two bytes of the packet) should match 0xFFFF - each byte of the packet (including 0x2040 but excluding the checksum) (Note the first byte is actually a packet length (0x20) then a command (only 0x40 supported)
Then I think we could refactor slightly.
The Rx interrupt could calculate the checksum as well as calculating the channel values:
We know the current position (so 0 is LSB of channel 0)
So something like (thinking aloud):
(in the interrupt handler)
I've attempted to implement this (please post a few 'full' data rows - for testing.)
Maybe also need to add a timeout - connection lost?
Martin
As far as I can tell - the value (the last two bytes of the packet) should match 0xFFFF - each byte of the packet (including 0x2040 but excluding the checksum) (Note the first byte is actually a packet length (0x20) then a command (only 0x40 supported)
Then I think we could refactor slightly.
The Rx interrupt could calculate the checksum as well as calculating the channel values:
We know the current position (so 0 is LSB of channel 0)
So something like (thinking aloud):
(in the interrupt handler)
Code: Select all
(case 1)
csum = 0xFFFF - 0x20 - 0x40
(case 2)
if pos < 28 // Data in bytes 0..27
csum = csum - .c
channel = pos / 2 // 0 and 1 = channel 0, 2 and 3 = channel 1...
if channel < 6 // We have channels 0..5
if (pos & 1) == 0 // Even byte is LSB
data[channel] = .c
else
data[channel] = data[channel] + (.c << 8)
if pos = 28 // LSB of checksum
checksum = .c
if pos = 29 // MSB of checksum
checksum = checksum + (.c << 8)
Maybe also need to add a timeout - connection lost?
Martin
- Attachments
-
- IBUS4.fcfx
- (26.24 KiB) Downloaded 131 times
Re: UART Transmission with atmega328p
Wow, thanks for your new idea.
Nothing is currently displayed, i.e. the programme is stuck somewhere. I'll have to see if I can find something.
Nothing is currently displayed, i.e. the programme is stuck somewhere. I'll have to see if I can find something.