Subversion Repositories MK3Mag

Rev

Rev 22 | Rev 26 | Go to most recent revision | Only display areas with differences | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 22 Rev 23
1
/*#######################################################################################
1
/*#######################################################################################
2
MK3Mag 3D-Magnet sensor
2
MK3Mag 3D-Magnet sensor
3
!!! THIS IS NOT FREE SOFTWARE !!!
3
!!! THIS IS NOT FREE SOFTWARE !!!
4
#######################################################################################*/
4
#######################################################################################*/
5
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
5
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
6
// + Copyright (c) 05.2008 Holger Buss
6
// + Copyright (c) 05.2008 Holger Buss
7
// + Thanks to Ilja Fähnrich (P_Latzhalter)
7
// + Thanks to Ilja Fähnrich (P_Latzhalter)
8
// + Nur für den privaten Gebrauch
8
// + Nur für den privaten Gebrauch
9
// + www.MikroKopter.com
9
// + www.MikroKopter.com
10
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
10
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
11
// + Die Portierung der Software (oder Teile davon) auf andere Systeme (ausser der Hardware von www.mikrokopter.de) ist nur
11
// + Die Portierung der Software (oder Teile davon) auf andere Systeme (ausser der Hardware von www.mikrokopter.de) ist nur
12
// + mit unserer Zustimmung zulässig
12
// + mit unserer Zustimmung zulässig
13
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
13
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
14
// + Es gilt für das gesamte Projekt (Hardware, Software, Binärfiles, Sourcecode und Dokumentation),
14
// + Es gilt für das gesamte Projekt (Hardware, Software, Binärfiles, Sourcecode und Dokumentation),
15
// + dass eine Nutzung (auch auszugsweise) nur für den privaten (nicht-kommerziellen) Gebrauch zulässig ist.
15
// + dass eine Nutzung (auch auszugsweise) nur für den privaten (nicht-kommerziellen) Gebrauch zulässig ist.
16
// + AUSNAHME: Ein bei www.mikrokopter.de erworbener vorbestückter MK3Mag darf als Baugruppe auch in kommerziellen Systemen verbaut werden
16
// + AUSNAHME: Ein bei www.mikrokopter.de erworbener vorbestückter MK3Mag darf als Baugruppe auch in kommerziellen Systemen verbaut werden
17
// + Im Zweifelsfall bitte anfragen bei: info@mikrokopter.de
17
// + Im Zweifelsfall bitte anfragen bei: info@mikrokopter.de
18
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
18
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
19
// + Werden Teile des Quellcodes (mit oder ohne Modifikation) weiterverwendet oder veröffentlicht,
19
// + Werden Teile des Quellcodes (mit oder ohne Modifikation) weiterverwendet oder veröffentlicht,
20
// + unterliegen sie auch diesen Nutzungsbedingungen und diese Nutzungsbedingungen incl. Copyright müssen dann beiliegen
20
// + unterliegen sie auch diesen Nutzungsbedingungen und diese Nutzungsbedingungen incl. Copyright müssen dann beiliegen
21
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
21
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
22
// + Sollte die Software (auch auszugesweise) oder sonstige Informationen des MikroKopter-Projekts
22
// + Sollte die Software (auch auszugesweise) oder sonstige Informationen des MikroKopter-Projekts
23
// + auf anderen Webseiten oder sonstigen Medien veröffentlicht werden, muss unsere Webseite "http://www.mikrokopter.de"
23
// + auf anderen Webseiten oder sonstigen Medien veröffentlicht werden, muss unsere Webseite "http://www.mikrokopter.de"
24
// + eindeutig als Ursprung verlinkt werden
24
// + eindeutig als Ursprung verlinkt werden
25
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
25
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
26
// + Keine Gewähr auf Fehlerfreiheit, Vollständigkeit oder Funktion
26
// + Keine Gewähr auf Fehlerfreiheit, Vollständigkeit oder Funktion
27
// + Benutzung auf eigene Gefahr
27
// + Benutzung auf eigene Gefahr
28
// + Wir übernehmen keinerlei Haftung für direkte oder indirekte Personen- oder Sachschäden
28
// + Wir übernehmen keinerlei Haftung für direkte oder indirekte Personen- oder Sachschäden
29
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
29
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
30
// + Die Funktion printf_P() unterliegt ihrer eigenen Lizenz und ist hiervon nicht betroffen
30
// + Die Funktion printf_P() unterliegt ihrer eigenen Lizenz und ist hiervon nicht betroffen
31
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
31
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
32
// + Redistributions of source code (with or without modifications) must retain the above copyright notice,
32
// + Redistributions of source code (with or without modifications) must retain the above copyright notice,
33
// + this list of conditions and the following disclaimer.
33
// + this list of conditions and the following disclaimer.
34
// +   * PORTING this software (or parts of it) to systems (other than hardware from www.mikrokopter.de) is NOT allowed
34
// +   * PORTING this software (or parts of it) to systems (other than hardware from www.mikrokopter.de) is NOT allowed
35
// +   * Neither the name of the copyright holders nor the names of contributors may be used to endorse or promote products derived
35
// +   * Neither the name of the copyright holders nor the names of contributors may be used to endorse or promote products derived
36
// +     from this software without specific prior written permission.
36
// +     from this software without specific prior written permission.
37
// +   * The use of this project (hardware, software, binary files, sources and documentation) is only permittet
37
// +   * The use of this project (hardware, software, binary files, sources and documentation) is only permittet
38
// +     for non-commercial use (directly or indirectly)
38
// +     for non-commercial use (directly or indirectly)
39
// +     Commercial use (for excample: selling of MikroKopters, selling of PCBs, assembly, ...) is only permitted
39
// +     Commercial use (for excample: selling of MikroKopters, selling of PCBs, assembly, ...) is only permitted
40
// +     with our written permission
40
// +     with our written permission
41
// +     Exception: A preassembled MK3Mag, purchased from www.mikrokopter.de may be used as a part of commercial systems
41
// +     Exception: A preassembled MK3Mag, purchased from www.mikrokopter.de may be used as a part of commercial systems
42
// +     In case of doubt please contact: info@MikroKopter.de
42
// +     In case of doubt please contact: info@MikroKopter.de
43
// +   * If sources or documentations are redistributet on other webpages, our webpage (http://www.MikroKopter.de) must be
43
// +   * If sources or documentations are redistributet on other webpages, our webpage (http://www.MikroKopter.de) must be
44
// +     clearly linked as origin
44
// +     clearly linked as origin
45
// +  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
45
// +  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
46
// +  AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
46
// +  AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
47
// +  IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
47
// +  IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
48
// +  ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
48
// +  ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
49
// +  LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
49
// +  LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
50
// +  CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
50
// +  CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
51
// +  SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
51
// +  SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
52
// +  INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
52
// +  INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
53
// +  CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
53
// +  CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
54
// +  ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
54
// +  ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
55
// +  POSSIBILITY OF SUCH DAMAGE.
55
// +  POSSIBILITY OF SUCH DAMAGE.
56
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
56
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
57
#include <avr/io.h>
57
#include <avr/io.h>
58
#include <avr/interrupt.h>
58
#include <avr/interrupt.h>
59
#include <avr/wdt.h>
59
#include <avr/wdt.h>
60
#include "main.h"
60
#include "main.h"
61
#include "uart.h"
61
#include "uart.h"
62
#include "timer0.h"
62
#include "timer0.h"
63
#include "twislave.h"
63
#include "twislave.h"
64
 
64
 
65
 
65
 
66
#define FALSE   0
66
#define FALSE   0
67
#define TRUE    1
67
#define TRUE    1
68
 
68
 
69
#define TXD_BUFFER_LEN  150
69
#define TXD_BUFFER_LEN  100
70
#define RXD_BUFFER_LEN  150
70
#define RXD_BUFFER_LEN  100
71
 
71
 
72
volatile uint8_t txd_buffer[TXD_BUFFER_LEN];
72
volatile uint8_t txd_buffer[TXD_BUFFER_LEN];
73
volatile uint8_t rxd_buffer_locked = FALSE;
73
volatile uint8_t rxd_buffer_locked = FALSE;
74
volatile uint8_t rxd_buffer[RXD_BUFFER_LEN];
74
volatile uint8_t rxd_buffer[RXD_BUFFER_LEN];
75
volatile uint8_t txd_complete = TRUE;
75
volatile uint8_t txd_complete = TRUE;
76
volatile uint8_t ReceivedBytes = 0;
76
volatile uint8_t ReceivedBytes = 0;
-
 
77
 
-
 
78
#define VERSION_INFO    0x01
-
 
79
#define DEBUG_DATA              0x02
-
 
80
#define DEBUG_LABEL             0x04
-
 
81
#define COMPASS_HEADING 0x08
-
 
82
 
77
 
-
 
78
 
-
 
79
 
-
 
80
uint8_t RequestVerInfo                  = FALSE;
-
 
81
uint8_t RequestDebugData                = FALSE;
83
uint8_t RequestFlags = 0x00;
82
uint8_t RequestDebugLabel               = FALSE;
84
uint8_t RequestDebugLabel = 0;
83
uint8_t RequestCompassHeading   = FALSE;
85
 
84
 
86
 
85
uint8_t MySlaveAddr = 0;
87
uint8_t MySlaveAddr = 0;
86
 
-
 
87
//unsigned char,DebugGetAnforderung = 0,
88
 
88
 
89
 
89
DebugOut_t              DebugOut;
90
struct DebugOut_t               DebugOut;
90
ExternData_t    ExternData;
91
struct ExternData_t             ExternData;
91
ExternControl_t ExternControl;
92
struct ExternControl_t  ExternControl;
92
VersionInfo_t   VersionInfo;
93
struct VersionInfo_t    VersionInfo;
93
 
94
 
94
uint16_t  Debug_Timer;
95
uint16_t  Debug_Timer;
95
 
96
 
96
const uint8_t ANALOG_LABEL[32][16] =
97
const uint8_t ANALOG_LABEL[32][16] =
97
{
98
{
98
   //1234567890123456
99
   //1234567890123456
99
    "Magnet X        ", //0
100
    "Magnet X        ", //0
100
    "Magnet Y        ",
101
    "Magnet Y        ",
101
    "Magnet Z        ",
102
    "Magnet Z        ",
102
    "Raw X           ",
103
    "Raw X           ",
103
    "Raw Y           ",
104
    "Raw Y           ",
104
    "Raw Z           ", //5
105
    "Raw Z           ", //5
105
    "Attitude Nick   ",
106
    "Attitude Nick   ",
106
    "Attitude Roll   ",
107
    "Attitude Roll   ",
107
    "XOffset         ",
108
    "XOffset         ",
108
    "XRange          ",
109
    "XRange          ",
109
    "YOffset         ", //10
110
    "YOffset         ", //10
110
    "YRange          ",
111
    "YRange          ",
111
    "ZOffset         ",
112
    "ZOffset         ",
112
    "ZRange          ",
113
    "ZRange          ",
113
    "Calstate        ",
114
    "Calstate        ",
114
    "Heading         ", //15
115
    "Heading         ", //15
115
    "User0           ",
116
    "User0           ",
116
    "User1           ",
117
    "User1           ",
117
    "Analog18        ",
118
    "Analog18        ",
118
    "Analog19        ",
119
    "Analog19        ",
119
    "Analog20        ", //20
120
    "Analog20        ", //20
120
    "Analog21        ",
121
    "Analog21        ",
121
    "Analog22        ",
122
    "Analog22        ",
122
    "Analog23        ",
123
    "Analog23        ",
123
    "Analog24        ",
124
    "Analog24        ",
124
    "Analog25        ", //25
125
    "Analog25        ", //25
125
    "Analog26        ",
126
    "Analog26        ",
126
    "Analog27        ",
127
    "Analog27        ",
127
    "Analog28        ",
128
    "Analog28        ",
128
    "Analog29        ",
129
    "Analog29        ",
129
    "Analog30        ", //30
130
    "Analog30        ", //30
130
    "Analog31        "
131
    "Analog31        "
131
};
132
};
132
 
133
 
133
 
134
 
134
/****************************************************************/
135
/****************************************************************/
135
/*              Initialization of the USART0                    */
136
/*              Initialization of the USART0                    */
136
/****************************************************************/
137
/****************************************************************/
137
void USART0_Init (void)
138
void USART0_Init (void)
138
{
139
{
139
        uint16_t ubrr = (uint16_t) ((uint32_t) SYSCLK/(8 * BAUD_RATE) - 1);
140
        uint16_t ubrr = (uint16_t) ((uint32_t) SYSCLK/(8 * BAUD_RATE) - 1);
140
 
141
 
141
        // disable all interrupts before configuration
142
        // disable all interrupts before configuration
142
        cli();
143
        cli();
143
 
144
 
144
        // disable RX-Interrupt
145
        // disable RX-Interrupt
145
        UCSR0B &= ~(1 << RXCIE0);
146
        UCSR0B &= ~(1 << RXCIE0);
146
        // disable TX-Interrupt
147
        // disable TX-Interrupt
147
        UCSR0B &= ~(1 << TXCIE0);
148
        UCSR0B &= ~(1 << TXCIE0);
148
 
149
 
149
        // set direction of RXD0 and TXD0 pins
150
        // set direction of RXD0 and TXD0 pins
150
 
151
 
151
        // set RXD0 (PD0) as an input pin tristate
152
        // set RXD0 (PD0) as an input pin tristate
152
        DDRD  &= ~(1 << DDD0);
153
        DDRD  &= ~(1 << DDD0);
153
        PORTD &= ~(1 << PORTD0);
154
        PORTD &= ~(1 << PORTD0);
154
        // set TXD0 (PD1) as an output pin
155
        // set TXD0 (PD1) as an output pin
155
        DDRD  |= (1 << DDD1);
156
        DDRD  |= (1 << DDD1);
156
        PORTD &= ~(1 << PORTD1);
157
        PORTD &= ~(1 << PORTD1);
157
 
158
 
158
 
159
 
159
        // USART0 Baud Rate Register
160
        // USART0 Baud Rate Register
160
        // set clock divider
161
        // set clock divider
161
        UBRR0H = (uint8_t)(ubrr >> 8);
162
        UBRR0H = (uint8_t)(ubrr >> 8);
162
        UBRR0L = (uint8_t)ubrr;
163
        UBRR0L = (uint8_t)ubrr;
163
 
164
 
164
        // USART0 Control and Status Register A, B, C
165
        // USART0 Control and Status Register A, B, C
165
 
166
 
166
        // enable double speed operation
167
        // enable double speed operation
167
        UCSR0A |= (1 << U2X0);
168
        UCSR0A |= (1 << U2X0);
168
 
169
 
169
        // set asynchronous mode
170
        // set asynchronous mode
170
        UCSR0C &= ~(1 << UMSEL01);
171
        UCSR0C &= ~(1 << UMSEL01);
171
        UCSR0C &= ~(1 << UMSEL00);
172
        UCSR0C &= ~(1 << UMSEL00);
172
        // no parity
173
        // no parity
173
        UCSR0C &= ~(1 << UPM01);
174
        UCSR0C &= ~(1 << UPM01);
174
        UCSR0C &= ~(1 << UPM00);
175
        UCSR0C &= ~(1 << UPM00);
175
        // 1 stop bit
176
        // 1 stop bit
176
        UCSR0C &= ~(1 << USBS0);
177
        UCSR0C &= ~(1 << USBS0);
177
        // 8-bit
178
        // 8-bit
178
        UCSR0B &= ~(1 << UCSZ02);
179
        UCSR0B &= ~(1 << UCSZ02);
179
        UCSR0C |=  (1 << UCSZ01);
180
        UCSR0C |=  (1 << UCSZ01);
180
        UCSR0C |=  (1 << UCSZ00);
181
        UCSR0C |=  (1 << UCSZ00);
181
 
182
 
182
        // enable receiver and transmitter
183
        // enable receiver and transmitter
183
        UCSR0B |= (1 << RXEN0);
184
        UCSR0B |= (1 << RXEN0);
184
        UCSR0B |= (1 << TXEN0);
185
        UCSR0B |= (1 << TXEN0);
185
 
186
 
186
        // flush receive buffer
187
        // flush receive buffer
187
        while ( UCSR0A & (1<<RXC0) ) UDR0;
188
        while ( UCSR0A & (1<<RXC0) ) UDR0;
188
 
189
 
189
        // enable RX-Interrupt
190
        // enable RX-Interrupt
190
        UCSR0B |= (1 << RXCIE0);
191
        UCSR0B |= (1 << RXCIE0);
191
        // enable TX-Interrupt
192
        // enable TX-Interrupt
192
        UCSR0B |= (1 << TXCIE0);
193
        UCSR0B |= (1 << TXCIE0);
193
 
194
 
194
        rxd_buffer_locked = FALSE;
195
        rxd_buffer_locked = FALSE;
195
        txd_complete = TRUE;
196
        txd_complete = TRUE;
196
 
197
 
197
 
198
 
198
        VersionInfo.Major = VERSION_MAJOR;
199
        VersionInfo.Major = VERSION_MAJOR;
199
        VersionInfo.Minor = VERSION_MINOR;
200
        VersionInfo.Minor = VERSION_MINOR;
200
    VersionInfo.PCCompatible = VERSION_COMPATIBLE;
201
    VersionInfo.PCCompatible = VERSION_COMPATIBLE;
201
 
202
 
202
 
203
 
203
    // Version beim Start ausgeben (nicht schön, aber geht... )
204
    // Version beim Start ausgeben (nicht schön, aber geht... )
204
        uart_putchar ('\n');
205
        uart_putchar ('\n');
205
        uart_putchar ('C');
206
        uart_putchar ('C');
206
        uart_putchar ('P');
207
        uart_putchar ('P');
207
        uart_putchar (':');
208
        uart_putchar (':');
208
        uart_putchar ('V');
209
        uart_putchar ('V');
209
        uart_putchar (0x30 + VERSION_MAJOR);
210
        uart_putchar (0x30 + VERSION_MAJOR);
210
        uart_putchar ('.');uart_putchar (0x30 + VERSION_MINOR/10);
211
        uart_putchar ('.');uart_putchar (0x30 + VERSION_MINOR/10);
211
        uart_putchar (0x30 + VERSION_MINOR%10);
212
        uart_putchar (0x30 + VERSION_MINOR%10);
212
    uart_putchar ('\n');
213
    uart_putchar ('\n');
213
}
214
}
214
 
215
 
215
// ---------------------------------------------------------------------------------
216
// ---------------------------------------------------------------------------------
216
void USART0_EnableTXD(void)
217
void USART0_EnableTXD(void)
217
{
218
{
218
        DDRD |= (1<<DDD1);                      // set TXD pin as output
219
        DDRD |= (1<<DDD1);                      // set TXD pin as output
219
        PORTD &= ~(1 << PORTD1);
220
        PORTD &= ~(1 << PORTD1);
220
        UCSR0B |= (1 << TXEN0);         // enable TX in USART
221
        UCSR0B |= (1 << TXEN0);         // enable TX in USART
221
        UCSR0B |= (1 << TXCIE0);        // disable TX-Interrupt
222
        UCSR0B |= (1 << TXCIE0);        // disable TX-Interrupt
222
}
223
}
223
 
224
 
224
// ---------------------------------------------------------------------------------
225
// ---------------------------------------------------------------------------------
225
void USART0_DisableTXD(void)
226
void USART0_DisableTXD(void)
226
{
227
{
227
        while(!txd_complete){ };
228
        while(!txd_complete){ };
228
 
229
 
229
        UCSR0B &= ~(1 << TXCIE0);   // disable TX-Interrupt
230
        UCSR0B &= ~(1 << TXCIE0);   // disable TX-Interrupt
230
        UCSR0B &= ~(1 << TXEN0);        // disable TXD in USART
231
        UCSR0B &= ~(1 << TXEN0);        // disable TXD in USART
231
        DDRD &= ~(1<<DDD1);             // set TXD pin as input
232
        DDRD &= ~(1<<DDD1);             // set TXD pin as input
232
        PORTD &= ~(1 << PORTD1);
233
        PORTD &= ~(1 << PORTD1);
233
}
234
}
234
 
235
 
235
/****************************************************************/
236
/****************************************************************/
236
/*               USART0 transmitter ISR                         */
237
/*               USART0 transmitter ISR                         */
237
/****************************************************************/
238
/****************************************************************/
238
ISR(USART_TX_vect)
239
ISR(USART_TX_vect)
239
{
240
{
240
        static uint16_t ptr_txd_buffer = 0;
241
        static uint16_t ptr_txd_buffer = 0;
241
        uint8_t tmp_tx;
242
        uint8_t tmp_tx;
242
        if(!txd_complete) // transmission not completed
243
        if(!txd_complete) // transmission not completed
243
        {
244
        {
244
                ptr_txd_buffer++;                    // die [0] wurde schon gesendet
245
                ptr_txd_buffer++;                    // die [0] wurde schon gesendet
245
                tmp_tx = txd_buffer[ptr_txd_buffer];
246
                tmp_tx = txd_buffer[ptr_txd_buffer];
246
                // if terminating character or end of txd buffer was reached
247
                // if terminating character or end of txd buffer was reached
247
                if((tmp_tx == '\r') || (ptr_txd_buffer == TXD_BUFFER_LEN))
248
                if((tmp_tx == '\r') || (ptr_txd_buffer == TXD_BUFFER_LEN))
248
                {
249
                {
249
                        ptr_txd_buffer = 0; // reset txd pointer
250
                        ptr_txd_buffer = 0; // reset txd pointer
250
                        txd_complete = TRUE; // stop transmission
251
                        txd_complete = TRUE; // stop transmission
251
                }
252
                }
252
                UDR0 = tmp_tx; // send current byte will trigger this ISR again
253
                UDR0 = tmp_tx; // send current byte will trigger this ISR again
253
        }
254
        }
254
        // transmission completed
255
        // transmission completed
255
        else ptr_txd_buffer = 0;
256
        else ptr_txd_buffer = 0;
256
}
257
}
257
 
258
 
258
/****************************************************************/
259
/****************************************************************/
259
/*               USART0 receiver ISR                            */
260
/*               USART0 receiver ISR                            */
260
/****************************************************************/
261
/****************************************************************/
261
ISR(USART_RX_vect)
262
ISR(USART_RX_vect)
262
{
263
{
263
        static uint16_t crc;
264
        static uint16_t crc;
264
        uint8_t crc1, crc2;
265
        uint8_t crc1, crc2;
265
        uint8_t c;
266
        uint8_t c;
266
        static uint8_t ptr_rxd_buffer = 0;
267
        static uint8_t ptr_rxd_buffer = 0;
267
 
268
 
268
        c = UDR0;  // catch the received byte
269
        c = UDR0;  // catch the received byte
269
 
270
 
270
        if(rxd_buffer_locked) return; // if rxd buffer is locked immediately return
271
        if(rxd_buffer_locked) return; // if rxd buffer is locked immediately return
271
 
272
 
272
        // the rxd buffer is unlocked
273
        // the rxd buffer is unlocked
273
        if((ptr_rxd_buffer == 0) && (c == '#')) // if rxd buffer is empty and syncronisation character is received
274
        if((ptr_rxd_buffer == 0) && (c == '#')) // if rxd buffer is empty and syncronisation character is received
274
        {
275
        {
275
                rxd_buffer[ptr_rxd_buffer++] = c; // copy 1st byte to buffer
276
                rxd_buffer[ptr_rxd_buffer++] = c; // copy 1st byte to buffer
276
                crc = c; // init crc
277
                crc = c; // init crc
277
        }
278
        }
278
        #if 0
279
        #if 0
279
        else if (ptr_rxd_buffer == 1) // handle address
280
        else if (ptr_rxd_buffer == 1) // handle address
280
        {
281
        {
281
                rxd_buffer[ptr_rxd_buffer++] = c; // copy byte to rxd buffer
282
                rxd_buffer[ptr_rxd_buffer++] = c; // copy byte to rxd buffer
282
                crc += c; // update crc
283
                crc += c; // update crc
283
        }
284
        }
284
        #endif
285
        #endif
285
        else if (ptr_rxd_buffer < RXD_BUFFER_LEN) // collect incomming bytes
286
        else if (ptr_rxd_buffer < RXD_BUFFER_LEN) // collect incomming bytes
286
        {
287
        {
287
                if(c != '\r') // no termination character
288
                if(c != '\r') // no termination character
288
                {
289
                {
289
                        rxd_buffer[ptr_rxd_buffer++] = c; // copy byte to rxd buffer
290
                        rxd_buffer[ptr_rxd_buffer++] = c; // copy byte to rxd buffer
290
                        crc += c; // update crc
291
                        crc += c; // update crc
291
                }
292
                }
292
                else // termination character was received
293
                else // termination character was received
293
                {
294
                {
294
                        // the last 2 bytes are no subject for checksum calculation
295
                        // the last 2 bytes are no subject for checksum calculation
295
                        // they are the checksum itself
296
                        // they are the checksum itself
296
                        crc -= rxd_buffer[ptr_rxd_buffer-2];
297
                        crc -= rxd_buffer[ptr_rxd_buffer-2];
297
                        crc -= rxd_buffer[ptr_rxd_buffer-1];
298
                        crc -= rxd_buffer[ptr_rxd_buffer-1];
298
                        // calculate checksum from transmitted data
299
                        // calculate checksum from transmitted data
299
                        crc %= 4096;
300
                        crc %= 4096;
300
                        crc1 = '=' + crc / 64;
301
                        crc1 = '=' + crc / 64;
301
                        crc2 = '=' + crc % 64;
302
                        crc2 = '=' + crc % 64;
302
                        // compare checksum to transmitted checksum bytes
303
                        // compare checksum to transmitted checksum bytes
303
                        if((crc1 == rxd_buffer[ptr_rxd_buffer-2]) && (crc2 == rxd_buffer[ptr_rxd_buffer-1]))
304
                        if((crc1 == rxd_buffer[ptr_rxd_buffer-2]) && (crc2 == rxd_buffer[ptr_rxd_buffer-1]))
304
                        {   // checksum valid
305
                        {   // checksum valid
305
                                rxd_buffer_locked = TRUE;          // lock the rxd buffer
306
                                rxd_buffer_locked = TRUE;          // lock the rxd buffer
306
                                ReceivedBytes = ptr_rxd_buffer;    // store number of received bytes
307
                                ReceivedBytes = ptr_rxd_buffer;    // store number of received bytes
307
                                rxd_buffer[ptr_rxd_buffer] = '\r'; // set termination character
308
                                rxd_buffer[ptr_rxd_buffer] = '\r'; // set termination character
308
                                // if 2nd byte is an 'R' enable watchdog that will result in an reset
309
                                // if 2nd byte is an 'R' enable watchdog that will result in an reset
309
                                if(rxd_buffer[2] == 'R') {wdt_enable(WDTO_250MS);} // Reset-Commando
310
                                if(rxd_buffer[2] == 'R') {wdt_enable(WDTO_250MS);} // Reset-Commando
310
                        }
311
                        }
311
                        else
312
                        else
312
                        {       // checksum invalid
313
                        {       // checksum invalid
313
                                rxd_buffer_locked = FALSE; // unlock rxd buffer
314
                                rxd_buffer_locked = FALSE; // unlock rxd buffer
314
                        }
315
                        }
315
                        ptr_rxd_buffer = 0; // reset rxd buffer pointer
316
                        ptr_rxd_buffer = 0; // reset rxd buffer pointer
316
                }
317
                }
317
        }
318
        }
318
        else // rxd buffer overrun
319
        else // rxd buffer overrun
319
        {
320
        {
320
                ptr_rxd_buffer = 0; // reset rxd buffer
321
                ptr_rxd_buffer = 0; // reset rxd buffer
321
                rxd_buffer_locked = FALSE; // unlock rxd buffer
322
                rxd_buffer_locked = FALSE; // unlock rxd buffer
322
        }
323
        }
323
}
324
}
324
 
325
 
325
 
326
 
326
// --------------------------------------------------------------------------
327
// --------------------------------------------------------------------------
327
void AddCRC(uint16_t datalen)
328
void AddCRC(uint16_t datalen)
328
{
329
{
329
        uint16_t tmpCRC = 0, i;
330
        uint16_t tmpCRC = 0, i;
330
        for(i = 0; i < datalen; i++)
331
        for(i = 0; i < datalen; i++)
331
        {
332
        {
332
                tmpCRC += txd_buffer[i];
333
                tmpCRC += txd_buffer[i];
333
        }
334
        }
334
        tmpCRC %= 4096;
335
        tmpCRC %= 4096;
335
        txd_buffer[i++] = '=' + tmpCRC / 64;
336
        txd_buffer[i++] = '=' + tmpCRC / 64;
336
        txd_buffer[i++] = '=' + tmpCRC % 64;
337
        txd_buffer[i++] = '=' + tmpCRC % 64;
337
        txd_buffer[i++] = '\r';
338
        txd_buffer[i++] = '\r';
338
        txd_complete = FALSE;
339
        txd_complete = FALSE;
339
        UDR0 = txd_buffer[0]; // initiates the transmission (continued in the TXD ISR)
340
        UDR0 = txd_buffer[0]; // initiates the transmission (continued in the TXD ISR)
340
}
341
}
341
 
342
 
342
 
343
 
343
 
344
 
344
// --------------------------------------------------------------------------
345
// --------------------------------------------------------------------------
345
void SendOutData(uint8_t cmd,uint8_t module, uint8_t *snd, uint8_t len)
346
void SendOutData(uint8_t cmd,uint8_t module, uint8_t *snd, uint8_t len)
346
{
347
{
347
        uint16_t pt = 0;
348
        uint16_t pt = 0;
348
        uint8_t a,b,c;
349
        uint8_t a,b,c;
349
        uint8_t ptr = 0;
350
        uint8_t ptr = 0;
350
 
351
 
351
        txd_buffer[pt++] = '#';         // Start character
352
        txd_buffer[pt++] = '#';         // Start character
352
        txd_buffer[pt++] = module;      // Address (a=0; b=1,...)
353
        txd_buffer[pt++] = module;      // Address (a=0; b=1,...)
353
        txd_buffer[pt++] = cmd;         // Command
354
        txd_buffer[pt++] = cmd;         // Command
354
 
355
 
355
        while(len)
356
        while(len)
356
        {
357
        {
357
                if(len) { a = snd[ptr++]; len--;} else a = 0;
358
                if(len) { a = snd[ptr++]; len--;} else a = 0;
358
                if(len) { b = snd[ptr++]; len--;} else b = 0;
359
                if(len) { b = snd[ptr++]; len--;} else b = 0;
359
                if(len) { c = snd[ptr++]; len--;} else c = 0;
360
                if(len) { c = snd[ptr++]; len--;} else c = 0;
360
                txd_buffer[pt++] = '=' + (a >> 2);
361
                txd_buffer[pt++] = '=' + (a >> 2);
361
                txd_buffer[pt++] = '=' + (((a & 0x03) << 4) | ((b & 0xf0) >> 4));
362
                txd_buffer[pt++] = '=' + (((a & 0x03) << 4) | ((b & 0xf0) >> 4));
362
                txd_buffer[pt++] = '=' + (((b & 0x0f) << 2) | ((c & 0xc0) >> 6));
363
                txd_buffer[pt++] = '=' + (((b & 0x0f) << 2) | ((c & 0xc0) >> 6));
363
                txd_buffer[pt++] = '=' + ( c & 0x3f);
364
                txd_buffer[pt++] = '=' + ( c & 0x3f);
364
        }
365
        }
365
        AddCRC(pt); // add checksum after data block and initates the transmission
366
        AddCRC(pt); // add checksum after data block and initates the transmission
366
}
367
}
367
 
368
 
368
 
369
 
369
// --------------------------------------------------------------------------
370
// --------------------------------------------------------------------------
370
void Decode64(uint8_t *ptrOut, uint8_t len, uint8_t ptrIn, uint8_t max)
371
void Decode64(uint8_t *ptrOut, uint8_t len, uint8_t ptrIn, uint8_t max)
371
{
372
{
372
        uint8_t a,b,c,d;
373
        uint8_t a,b,c,d;
373
        uint8_t ptr = 0;
374
        uint8_t ptr = 0;
374
        uint8_t x,y,z;
375
        uint8_t x,y,z;
375
        while(len)
376
        while(len)
376
        {
377
        {
377
                a = rxd_buffer[ptrIn++] - '=';
378
                a = rxd_buffer[ptrIn++] - '=';
378
                b = rxd_buffer[ptrIn++] - '=';
379
                b = rxd_buffer[ptrIn++] - '=';
379
                c = rxd_buffer[ptrIn++] - '=';
380
                c = rxd_buffer[ptrIn++] - '=';
380
                d = rxd_buffer[ptrIn++] - '=';
381
                d = rxd_buffer[ptrIn++] - '=';
381
                if(ptrIn > max - 2) break;
382
                if(ptrIn > max - 2) break;
382
 
383
 
383
                x = (a << 2) | (b >> 4);
384
                x = (a << 2) | (b >> 4);
384
                y = ((b & 0x0f) << 4) | (c >> 2);
385
                y = ((b & 0x0f) << 4) | (c >> 2);
385
                z = ((c & 0x03) << 6) | d;
386
                z = ((c & 0x03) << 6) | d;
386
 
387
 
387
                if(len--) ptrOut[ptr++] = x; else break;
388
                if(len--) ptrOut[ptr++] = x; else break;
388
                if(len--) ptrOut[ptr++] = y; else break;
389
                if(len--) ptrOut[ptr++] = y; else break;
389
                if(len--) ptrOut[ptr++] = z; else break;
390
                if(len--) ptrOut[ptr++] = z; else break;
390
        }
391
        }
391
}
392
}
392
 
393
 
393
 
394
 
394
// --------------------------------------------------------------------------
395
// --------------------------------------------------------------------------
395
int uart_putchar (int8_t c)
396
int uart_putchar (int8_t c)
396
{
397
{
397
        // if tx is not enabled return immediatly
398
        // if tx is not enabled return immediatly
398
        if(!(UCSR0B & (1 << TXEN0))) return (0);
399
        if(!(UCSR0B & (1 << TXEN0))) return (0);
399
        if (c == '\n') uart_putchar('\r');
400
        if (c == '\n') uart_putchar('\r');
400
        // wait until previous character was send
401
        // wait until previous character was send
401
        loop_until_bit_is_set(UCSR0A, UDRE0);
402
        loop_until_bit_is_set(UCSR0A, UDRE0);
402
        // send character
403
        // send character
403
        UDR0 = c;
404
        UDR0 = c;
404
        return (0);
405
        return (0);
405
}
406
}
406
 
407
 
407
 
408
 
408
// --------------------------------------------------------------------------
409
// --------------------------------------------------------------------------
409
void USART0_ProcessRxData(void)
410
void USART0_ProcessRxData(void)
410
{
411
{
411
        // if data in the rxd buffer are not locked immediately return
412
        // if data in the rxd buffer are not locked immediately return
412
        if(!rxd_buffer_locked) return;
413
        if(!rxd_buffer_locked) return;
413
 
414
 
414
        uint8_t tmp_char_arr2[2]; // local char buffer
415
        uint8_t tmp_char_arr2[2]; // local char buffer
415
 
416
 
416
        switch(rxd_buffer[2])
417
        switch(rxd_buffer[2])
417
        {
418
        {
418
           case 'w':// Attitude
419
           case 'w':// Attitude
419
                        Decode64((uint8_t *) &ExternData, sizeof(ExternData), 3, ReceivedBytes);
420
                        Decode64((uint8_t *) &ExternData, sizeof(ExternData), 3, ReceivedBytes);
420
                        RequestCompassHeading = TRUE;
421
                        RequestFlags |= COMPASS_HEADING;
421
                        break;
422
                        break;
422
 
423
 
423
                case 'b': // extern control
424
                case 'b': // extern control
424
                case 'c': // extern control with debug request
425
                case 'c': // extern control with debug request
425
                        Decode64((uint8_t *) &ExternControl,sizeof(ExternControl), 3,ReceivedBytes);
426
                        Decode64((uint8_t *) &ExternControl,sizeof(ExternControl), 3,ReceivedBytes);
426
                        #define KEY1    0x01
427
                        #define KEY1    0x01
427
                        #define KEY2    0x02
428
                        #define KEY2    0x02
428
                        #define KEY3    0x04
429
                        #define KEY3    0x04
429
                        #define KEY4    0x08
430
                        #define KEY4    0x08
430
                        #define KEY5    0x10
431
                        #define KEY5    0x10
431
                        // use right arrow at display for switching the calstate
432
                        // use right arrow at display for switching the calstate
432
                        if(ExternControl.RemoteButtons & KEY2)
433
                        if(ExternControl.RemoteButtons & KEY2)
433
                        {
434
                        {
434
                                ExternData.CalState++;
435
                                ExternData.CalState++;
435
                                if(ExternData.CalState == 6) ExternData.CalState = 0;
436
                                if(ExternData.CalState == 6) ExternData.CalState = 0;
436
                        }
437
                        }
437
                        ExternData.Attitude[0] = ExternControl.Par1;
438
                        ExternData.Attitude[0] = ExternControl.Par1;
438
            ExternData.Attitude[1] = ExternControl.Par2;
439
            ExternData.Attitude[1] = ExternControl.Par2;
439
            PC_Connected = 255;
440
            PC_Connected = 255;
440
                        break;
441
                        break;
441
 
442
 
442
                case 'h':// x-1 display columns
443
                case 'h':// x-1 display columns
443
                        PC_Connected = 255;
444
                        PC_Connected = 255;
444
                        break;
445
                        break;
445
 
446
 
446
                case 'v': // get version and board release
447
                case 'v': // get version and board release
447
                        RequestVerInfo = TRUE;
448
                        RequestFlags |= VERSION_INFO;
448
                        PC_Connected = 255;
449
                        PC_Connected = 255;
449
                        break;
450
                        break;
450
 
451
 
451
                case 'a':// Labels of the Analog Debug outputs
452
                case 'a':// Labels of the Analog Debug outputs
452
                        Decode64((uint8_t *) &tmp_char_arr2[0], sizeof(tmp_char_arr2), 3, ReceivedBytes);
453
                        Decode64((uint8_t *) &tmp_char_arr2[0], sizeof(tmp_char_arr2), 3, ReceivedBytes);
453
                        RequestDebugLabel = tmp_char_arr2[0];
454
                        RequestDebugLabel = tmp_char_arr2[0];
-
 
455
                        RequestFlags |= DEBUG_LABEL;
454
                        PC_Connected = 255;
456
                        PC_Connected = 255;
455
                        break;
457
                        break;
456
 
458
 
457
                case 'g':// get debug data
459
                case 'g':// get debug data
458
                        RequestDebugData = TRUE;
460
                        RequestFlags |= DEBUG_DATA;
459
                        PC_Connected = 255;
461
                        PC_Connected = 255;
460
                        break;
462
                        break;
461
        }
463
        }
462
        // unlock the rxd buffer after processing
464
        // unlock the rxd buffer after processing
463
        rxd_buffer_locked = FALSE;
465
        rxd_buffer_locked = FALSE;
464
}
466
}
465
 
467
 
466
 
468
 
467
 
469
 
468
//---------------------------------------------------------------------------------------------
470
//---------------------------------------------------------------------------------------------
469
void USART0_TransmitTxData(void)
471
void USART0_TransmitTxData(void)
470
{
472
{
471
        if(!(UCSR0B & (1 << TXEN0))) return;
473
        if(!(UCSR0B & (1 << TXEN0))) return;
472
 
474
 
473
        if(!txd_complete) return;
475
        if(!txd_complete) return;
474
 
476
 
475
    if(CheckDelay(Debug_Timer) && txd_complete)
477
    if(CheckDelay(Debug_Timer))
476
    {
478
    {
477
                SetDebugValues();
479
                SetDebugValues();
478
                SendOutData('D',MySlaveAddr,(uint8_t *) &DebugOut,sizeof(DebugOut));
480
                SendOutData('D',MySlaveAddr,(uint8_t *) &DebugOut,sizeof(DebugOut));
479
                Debug_Timer = SetDelay(250);
481
                Debug_Timer = SetDelay(250);
480
    }
482
    }
481
 
483
 
482
    if(RequestDebugLabel != 255)
484
    if(RequestFlags & DEBUG_LABEL)
483
    {
485
    {
484
                SendOutData('A',RequestDebugLabel + '0',(uint8_t *) ANALOG_LABEL[RequestDebugLabel],16);
486
                SendOutData('A',RequestDebugLabel + '0',(uint8_t *) ANALOG_LABEL[RequestDebugLabel],16);
485
                RequestDebugLabel = 255;
487
                RequestDebugLabel = 255;
-
 
488
                RequestFlags &= ~DEBUG_LABEL;
486
        }
489
        }
487
 
490
 
488
        if(RequestVerInfo && txd_complete)
491
        if(RequestFlags & VERSION_INFO)
489
    {
492
    {
490
                SendOutData('V',MySlaveAddr,(uint8_t *) &VersionInfo, sizeof(VersionInfo));
493
                SendOutData('V',MySlaveAddr,(uint8_t *) &VersionInfo, sizeof(VersionInfo));
491
                RequestVerInfo = FALSE;
494
                RequestFlags &= ~VERSION_INFO;
492
    }
495
    }
493
 
496
 
494
        if(RequestDebugData && txd_complete)
497
        if(RequestFlags & DEBUG_DATA)
495
        {
498
        {
496
                SetDebugValues();
499
                SetDebugValues();
497
                SendOutData('G',MySlaveAddr,(uint8_t *) &ExternControl,sizeof(ExternControl));
500
                SendOutData('G',MySlaveAddr,(uint8_t *) &ExternControl,sizeof(ExternControl));
498
                RequestDebugData = FALSE;
501
                RequestFlags &= ~DEBUG_DATA;
499
        }
502
        }
500
 
503
 
501
    if(RequestCompassHeading && txd_complete)
504
    if(RequestFlags & COMPASS_HEADING)
502
        {
505
        {
503
                SendOutData('K',MySlaveAddr,(uint8_t *) &I2C_Heading, sizeof(I2C_Heading));
506
                SendOutData('K',MySlaveAddr,(uint8_t *) &I2C_Heading, sizeof(I2C_Heading));
504
                RequestCompassHeading = FALSE;
507
                RequestFlags &= ~COMPASS_HEADING;
505
        }
508
        }
506
}
509
}
507
 
510