Subversion Repositories HomeAutomation

Rev

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

Rev 225 Rev 228
Line 2... Line 2...
2
#include "avr_cfg.h"
2
#include "avr_cfg.h"
3
#include <inttypes.h>
3
#include <inttypes.h>
-
 
4
#include <avr/io.h>
4
#include <avr/interrupt.h>
5
#include <avr/interrupt.h>
5
#include <avr/wdt.h>
6
#include <avr/wdt.h>
6
#include <avr/boot.h>
-
 
7
#include <avr/pgmspace.h>
7
#include <avr/pgmspace.h>
8
#include <avr/io.h>
-
 
9
#include <stdio.h>
8
#include <stdio.h>
10
#include "app_vectors.h"
9
#include "flash.h"
-
 
10
#include "vectors.h" // Must be included after sfr_defs.h
11
 
11
 
12
//---------------------------------------------------------------------------
12
//---------------------------------------------------------------------------
13
// Globals
13
// Globals
14
 
14
 
15
volatile long gMilliSecTick;
15
volatile long gMilliSecTick;
16
 
16
 
17
//---------------------------------------------------------------------------
17
//---------------------------------------------------------------------------
18
// Function definitions for the exported interface
18
// Function definitions for the exported interface
19
 
19
 
20
void reset(void) {
20
void reset(void) {
21
    //Just loop and let the watchdog reset
21
    //Just loop and let the watchdog reset
22
    cli();
22
    cli();
23
    while(1);
23
    while(1);
24
};
24
};
25
 
25
 
26
void bios_putchar(char c) {
26
void bios_putchar(char c) {
27
    #if defined(__AVR_ATmega8__)
-
 
28
    loop_until_bit_is_set(UCSRA, UDRE);
-
 
29
    UDR = c;
-
 
30
    #elif defined(__AVR_ATmega88__)
-
 
31
    loop_until_bit_is_set(UCSR0A, UDRE0);
-
 
32
    UDR0 = c;
27
    UART_PUTCHAR(c);
33
    #endif
-
 
34
};
28
};
35
 
29
 
36
char bios_getchar(void) {
30
char bios_getchar(void) {
37
    #if defined(__AVR_ATmega8__)
-
 
38
    loop_until_bit_is_set(UCSRA, RXC);
-
 
39
    return UDR;
31
    char c;
40
    #elif defined(__AVR_ATmega88__)
32
    UART_GETCHAR(c)
41
    loop_until_bit_is_set(UCSR0A, RXC0);
-
 
42
    return UDR0;
33
    return c;
43
    #endif
-
 
44
};
34
};
45
 
35
 
46
long timebase_get(void) {
36
long timebase_get(void) {
47
    uint8_t sreg;
37
    uint8_t sreg;
48
    long res;
38
    long res;
49
   
39
   
50
    //Disable interrupts while reading tick count
40
    //Disable interrupts while reading tick count
51
    sreg=SREG;
41
    sreg=SREG;
52
    cli();
42
    cli();
53
   
43
   
54
    res = gMilliSecTick;
44
    res = gMilliSecTick;
55
   
-
 
56
    SREG=sreg;
-
 
57
   
-
 
58
    return res;
-
 
59
}
-
 
60
 
-
 
61
//---------------------------------------------------------------------------
-
 
62
// Function definitions for the private functions
-
 
63
 
-
 
64
static uint16_t flash_prev_addr;
-
 
65
 
-
 
66
void flash_flush_buffer() {
-
 
67
    uint8_t sreg;
-
 
68
   
-
 
69
    // Disable interrupts.
-
 
70
   
-
 
71
    sreg = SREG;
-
 
72
    cli();
-
 
73
   
-
 
74
    eeprom_busy_wait();
-
 
75
   
-
 
76
    boot_page_erase(flash_prev_addr);
-
 
77
    boot_spm_busy_wait();      // Wait until the memory is erased.
-
 
78
   
45
   
79
    boot_page_write(flash_prev_addr);     // Store buffer in flash page.
-
 
80
    boot_spm_busy_wait();       // Wait until the memory is written.
-
 
81
 
-
 
82
    // Reenable RWW-section again. We need this if we want to jump back
-
 
83
    // to the application after bootloading.
-
 
84
 
-
 
85
    boot_rww_enable ();
-
 
86
 
-
 
87
    // Re-enable interrupts (if they were ever enabled).
-
 
88
 
-
 
89
    SREG = sreg;
46
    SREG=sreg;
90
}
-
 
91
 
-
 
92
void flash_load_buffer(uint16_t addr) {
-
 
93
    //TODO: Load current flash page contents into temporary buffer to implement
-
 
94
    // flash read-modify-writes with word granularity. (If possible, the data
-
 
95
    // sheet is a little fuzzy about this.)
-
 
96
}
-
 
97
 
-
 
98
void flash_write_word(uint16_t addr, uint16_t word) {
-
 
99
   
-
 
100
    if ((addr / SPM_PAGESIZE) != (flash_prev_addr / SPM_PAGESIZE)) {
-
 
101
        flash_flush_buffer();
-
 
102
        flash_load_buffer(addr);
-
 
103
    }
-
 
104
   
-
 
105
    boot_page_fill(addr, word);
-
 
106
    flash_prev_addr = addr;
-
 
107
}    
-
 
108
 
47
   
109
void flash_init() {
-
 
110
    flash_prev_addr = 0xffff;
48
    return res;
111
}
49
}
-
 
50
 
-
 
51
//---------------------------------------------------------------------------
-
 
52
// Function definitions for the private functions
112
 
53
 
113
static int console_getchar(FILE *stream) {
54
static int console_getchar(FILE *stream) {
114
    return bios->can_receive();
55
    return bios_getchar();
115
}
56
}
116
 
57
 
117
static int console_putchar(char c, FILE *stream) {
58
static int console_putchar(char c, FILE *stream) {
118
    bios->can_send(c);
59
    bios_putchar(c);
119
    return 0;
60
    return 0;
120
}
61
}
121
 
62
 
122
static FILE bios_stdio = FDEV_SETUP_STREAM(console_putchar, console_getchar,
63
static FILE bios_stdio = FDEV_SETUP_STREAM(console_putchar, console_getchar,
123
                                         _FDEV_SETUP_RW);
64
                                         _FDEV_SETUP_RW);
Line 135... Line 76...
135
 
76
 
136
int main() {
77
int main() {
137
    void (*app_reset)(void) = 0;
78
    void (*app_reset)(void) = 0;
138
   
79
   
139
    // Setup USART for debug channel
80
    // Setup USART for debug channel
140
    #if defined(__AVR_ATmega8__)
-
 
141
    UCSRB = _BV(RXEN)|_BV(TXEN);
81
    UART_INIT();
142
    UBRRL = (F_CPU / 16 / F_BAUD) - 1;
-
 
143
    #elif defined(__AVR_ATmega88__)
-
 
144
    UCSR0B = _BV(RXEN0)|_BV(TXEN0);
-
 
145
    UBRR0L = (F_CPU / 16 / F_BAUD) - 1;
-
 
146
    #endif
-
 
147
    stdout = &bios_stdio;
82
    stdout = &bios_stdio;
148
    stdin = &bios_stdio;
83
    stdin = &bios_stdio;
149
   
84
   
150
    // Initialize a suitable hardware timer to create a 1KHz interrupt.
85
    // Initialize a suitable hardware timer to create a 1KHz interrupt.
151
    TIMEBASE_INIT();
86
    TIMEBASE_INIT();
Line 153... Line 88...
153
    // Enable watchdog timer to protect against an application locking the
88
    // Enable watchdog timer to protect against an application locking the
154
    // node by leaving interrupts disabled. 
89
    // node by leaving interrupts disabled. 
155
    wdt_enable(WDTO_500MS);
90
    wdt_enable(WDTO_500MS);
156
   
91
   
157
    // Move interrupt vectors to start of bootloader section and enable interrupts
92
    // Move interrupt vectors to start of bootloader section and enable interrupts
158
    #if defined(__AVR_ATmega8__)
-
 
159
    GICR = _BV(IVCE);
-
 
160
    GICR = _BV(IVSEL);
-
 
161
    #elif defined(__AVR_ATmega88__)
-
 
162
    MCUCR = _BV(IVCE);
93
    IVSEL_REG = _BV(IVCE);
163
    MCUCR = _BV(IVSEL);
94
    IVSEL_REG = _BV(IVSEL);
164
    #endif
-
 
165
    sei();
95
    sei();
166
   
96
   
167
    printf("AVR BIOS\n");
97
    printf("AVR BIOS\n");
168
   
98
   
169
    if (pgm_read_word(0) != 0xffff) {
99
    if (pgm_read_word(0) != 0xffff) {