Subversion Repositories HomeAutomation

Rev

Rev 248 | Show entire file | Regard whitespace | Details | Blame | Last modification | View Log | SVN | RSS feed

Rev 248 Rev 250
Line 6... Line 6...
6
#include <avr/wdt.h>
6
#include <avr/wdt.h>
7
#include <avr/pgmspace.h>
7
#include <avr/pgmspace.h>
8
#include <stdio.h>
8
#include <stdio.h>
9
#include "flash.h"
9
#include "flash.h"
10
#include "vectors.h" // Must be included after sfr_defs.h but before any ISR()
10
#include "vectors.h" // Must be included after sfr_defs.h but before any ISR()
11
#include "can.h"
11
#include "mcp2515/mcp2515.h"
12
 
-
 
13
#define FUNCTmask       0x1E000000
-
 
14
#define FUNCTshift      25
-
 
15
#define FUNCCmask       0x01FF8000
-
 
16
#define FUNCCshift      15
-
 
17
#define NIDmask         0x00007E00
-
 
18
#define NIDshift        9
-
 
19
#define SIDmask         0x000001FF
-
 
20
#define SIDshift        0
-
 
21
 
-
 
22
#define FUNCTbios       0x00
-
 
23
 
-
 
24
#define FUNCCstartprg   0x81
-
 
25
#define FUNCCprgdata    0x82
-
 
26
#define FUNCCstopprg    0x83
-
 
27
 
-
 
28
#define PRG_STATE_IDLE          0
-
 
29
#define PRG_STATE_PROGRAMMING   1
-
 
30
 
-
 
31
 
12
 
32
//---------------------------------------------------------------------------
13
//---------------------------------------------------------------------------
33
// Globals
14
// Globals
34
 
15
 
35
volatile long gMilliSecTick;
16
volatile long gMilliSecTick;
36
 
17
 
37
//---------------------------------------------------------------------------
18
//---------------------------------------------------------------------------
38
// Function definitions for the exported interface
19
// Function definitions for the exported interface
39
 
20
 
40
void reset(void) {
21
void reset(void) {
41
    //Just loop and let the watchdog reset
22
    //Just loop and let the watchdog reset
42
    cli();
23
    cli();
43
    while(1);
24
    while(1);
44
};
25
}
45
 
26
 
46
void bios_putchar(char c) {
27
void bios_putchar(char c) {
47
    UART_PUTCHAR(c);
28
    UART_PUTCHAR(c);
48
};
29
}
49
 
30
 
50
char bios_getchar(void) {
31
char bios_getchar(void) {
51
    char c;
32
    char c;
52
    UART_GETCHAR(c)
33
    UART_GETCHAR(c)
53
    return c;
34
    return c;
54
};
35
}
55
 
36
 
56
long timebase_get(void) {
37
long timebase_get(void) {
57
    uint8_t sreg;
38
    uint8_t sreg;
58
    long res;
39
    long res;
59
   
40
   
Line 65... Line 46...
65
   
46
   
66
    SREG=sreg;
47
    SREG=sreg;
67
   
48
   
68
    return res;
49
    return res;
69
}
50
}
-
 
51
 
-
 
52
// TODO: Insert can driver's Can_Send directly in bios interface.
-
 
53
Can_Return_t can_send(Can_Message_t* msg) {
-
 
54
    return CAN_FAIL;
-
 
55
}
-
 
56
 
-
 
57
//Can_Return_t can_receive(Can_Message_t *msg) {
-
 
58
//  return CAN_FAIL;
-
 
59
//}
70
 
60
 
71
//---------------------------------------------------------------------------
61
//---------------------------------------------------------------------------
72
// Function definitions for the private functions
62
// Function definitions for the private functions
73
 
63
 
74
static int console_getchar(FILE *stream) {
64
static int console_getchar(FILE *stream) {
Line 85... Line 75...
85
   
75
   
86
 
76
 
87
//---------------------------------------------------------------------------
77
//---------------------------------------------------------------------------
88
// Interrupt Service Routines
78
// Interrupt Service Routines
89
// Read app_vectors.h!
79
// Read app_vectors.h!
90
 
80
 
91
ISR(TIMEBASE_VECTOR) {
81
ISR(TIMEBASE_VECTOR) {
92
    TIMEBASE_COUNTER -= TIMEBASE_RELOAD;
82
    TIMEBASE_COUNTER -= TIMEBASE_RELOAD;
93
    gMilliSecTick++;
83
    gMilliSecTick++;
94
    wdt_reset();
84
    wdt_reset();
-
 
85
}
-
 
86
 
-
 
87
void Can_Process(Can_Message_t* msg) {
-
 
88
    if (msg->ExtendedFlag && ((msg->Id & CAN_FUNCT_MASK) == CAN_MSG_TYPE_BIOS)) {
-
 
89
        printf("BIOS received msg!\n");
-
 
90
    } else if (bios->can_callback) {
-
 
91
        printf("Calling app callback.\n");
-
 
92
        bios->can_callback(msg);
-
 
93
    } else {
-
 
94
        printf("BIOS received application msg but no handler installed!\n");
-
 
95
    }
95
}
96
}
96
 
97
 
97
int main() {
98
int main() {
98
    void (*app_reset)(void) = 0;
99
    void (*app_reset)(void) = 0;
99
   
100
   
Line 114... Line 115...
114
    IVSEL_REG = _BV(IVSEL);
115
    IVSEL_REG = _BV(IVSEL);
115
    sei();
116
    sei();
116
   
117
   
117
    printf("AVR BIOS\n");
118
    printf("AVR BIOS\n");
118
   
119
   
-
 
120
    if (pgm_read_word(0) != 0xffff) {
-
 
121
        printf("Starting application.\n");
-
 
122
        app_reset();
-
 
123
    }
-
 
124
   
-
 
125
    printf("No application found.\n");
119
   
126
   
-
 
127
    printf("\n------------------------------------------------------------\n");
-
 
128
    printf(  "   CAN Test: Periodic Transmission\n");
-
 
129
    printf(  "------------------------------------------------------------\n");
-
 
130
   
120
    printf("CanInit...");
131
    printf("CanInit...\n");
121
    if (Can_Init() != CAN_OK) {
132
    if (Can_Init() != CAN_OK) {
122
        printf("FAILED!\n");
133
        printf("FAILED!\n");
123
    }
134
    }
124
    else {
135
    else {
125
        printf("OK!\n");
136
        printf("OK!\n");
126
    }
137
    }
127
   
138
   
128
    uint32_t timeStamp = 0;
139
    uint32_t timeStamp = 0;
129
   
140
   
130
    Can_Message_t txMsg;
141
    Can_Message_t txMsg;
131
    Can_Message_t rxMsg;
-
 
132
    //The databytes are just what happens to be in the memory. They are never set.
142
    //The databytes are just what happens to be in the memory. They are never set.
133
    txMsg.RemoteFlag = 0;
143
    txMsg.RemoteFlag = 0;
134
    txMsg.ExtendedFlag = 1;
144
    txMsg.ExtendedFlag = 1;
135
 
-
 
-
 
145
#define NODENUMBER 2
-
 
146
#if NODENUMBER == 1
136
    txMsg.Id = 15;
147
    txMsg.Id = 16;
137
    txMsg.DataLength = 2;
148
    txMsg.DataLength = 2;
138
   
-
 
-
 
149
#elif NODENUMBER == 2
139
    uint16_t address;
150
    txMsg.Id = 32;
140
    uint16_t lastoffset=0x0;
151
    txMsg.DataLength = 5;
-
 
152
#else
141
    uint8_t prg_state=PRG_STATE_IDLE;
153
# error NODENUMBER not set!
-
 
154
#endif
142
   
155
   
143
    uint8_t i;
-
 
144
    /* main loop */
156
    /* main loop */
145
    while (1) {
157
    while (1) {
146
        /* service the CAN routines */
-
 
147
        Can_Service();
-
 
148
       
158
       
149
        /* send CAN message and check for CAN errors once every second */
159
        /* send CAN message and check for CAN errors once every second */
150
        if ((timebase_get() - timeStamp) >= 10000) {
160
        if ((timebase_get() - timeStamp) >= 1000) {
151
            timeStamp = timebase_get();
161
            timeStamp = timebase_get();
152
 
-
 
153
            /* send txMsg */
162
            /* send txMsg */
154
            //txMsg.Id++;
163
            txMsg.Id++;
155
            Can_Send(&txMsg);
164
            Can_Send(&txMsg);
156
           
-
 
157
            if (prg_state==PRG_STATE_IDLE) {
-
 
158
                if (pgm_read_word(0) != 0xffff) {
-
 
159
                    printf("Starting application.\n");
-
 
160
                    app_reset();
-
 
161
                }
-
 
162
                printf("No application found.\n");
-
 
163
            }
-
 
164
        }
-
 
165
       
-
 
166
        /* check if any messages have been received */
-
 
167
        while (Can_Receive(&rxMsg) == CAN_OK) {
-
 
168
            printf("BIOS Received: ID=%lx, DLC=%u, EXT=%u, RTR=%u, ", rxMsg.Id, (uint16_t)(rxMsg.DataLength), (uint16_t)(rxMsg.ExtendedFlag), (uint16_t)(rxMsg.RemoteFlag));
-
 
169
            printf("data={ ");
-
 
170
            for (i=0; i<rxMsg.DataLength; i++) {
-
 
171
                printf("%x ", rxMsg.Data.bytes[i]);
-
 
172
            }
-
 
173
            printf("}\n");
-
 
174
           
-
 
175
            if ((rxMsg.Id & FUNCTmask) == ((uint32_t)FUNCTbios<<FUNCTshift)) {
-
 
176
                //printf("Got 'bios package'\n");
-
 
177
                //om mottagen data är bois-data (detta borde redan filtrerats i can_receive?)
-
 
178
                if ((prg_state==PRG_STATE_IDLE) && ((rxMsg.Id & FUNCCmask) == ((uint32_t)FUNCCstartprg<<FUNCCshift)) && (rxMsg.DataLength == 6)) {
-
 
179
                    //om mottagen data har funktionskoden starta programmering
-
 
180
 
-
 
181
                    //ska kolla om nod-id i IDENT stämmer med nodens id
-
 
182
                    //om ok:
-
 
183
                    prg_state=PRG_STATE_PROGRAMMING;
-
 
184
                    address = rxMsg.Data.bytes[2];
-
 
185
                    address |= rxMsg.Data.bytes[3];
-
 
186
                    printf("Got 'start programming' at address %x\n", address);
-
 
187
                } else if (prg_state==PRG_STATE_PROGRAMMING) {
-
 
188
                    if ((rxMsg.Id & FUNCCmask) == ((uint32_t)FUNCCprgdata<<FUNCCshift)) {
-
 
189
                        //om mottagen data har funktionskoden programdata
-
 
190
                        uint16_t tmpaddress = rxMsg.Data.bytes[0] + (rxMsg.Data.bytes[1] << 8);
-
 
191
                        if (tmpaddress >= lastoffset) {
-
 
192
                            tmpaddress += address;
-
 
193
                            printf("Got 'programdatapacket' at offset %x\n", tmpaddress);
-
 
194
                            for (i=2; i<rxMsg.DataLength; i+=2) {
-
 
195
                                flash_write_word(tmpaddress, rxMsg.Data.bytes[i] + (rxMsg.Data.bytes[i+1] << 8));
-
 
196
                                tmpaddress+=2;
-
 
197
                            }
-
 
198
                            printf("Setting lastoffset to %x\n", tmpaddress);
-
 
199
                            lastoffset = tmpaddress;
-
 
200
                        }
-
 
201
                    } else if ((rxMsg.Id & FUNCCmask) == ((uint32_t)FUNCCstopprg<<FUNCCshift)) {
-
 
202
                        flash_flush_buffer();
-
 
203
                        prg_state=PRG_STATE_IDLE;
-
 
204
                        lastoffset=0x0;
-
 
205
                        //beräkna crc på all programdata mellan address och address+lastoffset
-
 
206
                        printf("Got 'end programming'\n");
-
 
207
                    }
-
 
208
                }
-
 
209
            }
-
 
210
           
-
 
211
            //if (rxMsg.Id % 20 == 19) reset();
-
 
212
        }
165
        }
213
    }
166
    }
214
 
167
 
215
    return 0;
168
    return 0;
216
}
169
}