2020-07-11 12:41:08 +02:00
|
|
|
#include <avr/io.h>
|
2020-07-27 21:39:29 +02:00
|
|
|
#include <avr/interrupt.h>
|
2020-07-19 18:40:44 +02:00
|
|
|
#include <avr/pgmspace.h>
|
2020-07-27 21:39:29 +02:00
|
|
|
#include <util/delay.h>
|
2020-07-19 18:40:44 +02:00
|
|
|
#include "oled-display/lcd.h"
|
2020-07-27 21:39:29 +02:00
|
|
|
#include "input.h"
|
|
|
|
#include "systick.h"
|
2020-07-30 17:11:48 +02:00
|
|
|
#include "batmon.h"
|
2020-07-30 19:57:46 +02:00
|
|
|
#include "pm.h"
|
2020-07-11 12:41:08 +02:00
|
|
|
|
2020-07-31 19:07:11 +02:00
|
|
|
#define TIME_POWEROFF 5000
|
|
|
|
|
2020-07-19 18:40:44 +02:00
|
|
|
#define PORT_SPI(t) t##B
|
|
|
|
#define PIN_SPI_CS (1 << 2)
|
|
|
|
|
2020-07-27 21:39:29 +02:00
|
|
|
int dbg = 0;
|
|
|
|
|
|
|
|
void spi_init()
|
|
|
|
{
|
|
|
|
SPCR = (1 << SPE);
|
|
|
|
SPSR = (1 << SPI2X);
|
|
|
|
DDRB |= (1 << 4);
|
|
|
|
}
|
|
|
|
|
2020-07-28 21:54:20 +02:00
|
|
|
#define Y_MAX (DISPLAY_HEIGHT / 8 - 1)
|
2020-07-27 21:39:29 +02:00
|
|
|
uint8_t spi_proc()
|
2020-07-11 12:41:08 +02:00
|
|
|
{
|
2020-07-19 21:20:30 +02:00
|
|
|
static uint8_t new_data = 0;
|
2020-07-19 18:40:44 +02:00
|
|
|
static uint8_t x = 0;
|
2020-07-28 21:54:20 +02:00
|
|
|
static uint8_t y = Y_MAX;
|
2020-07-19 18:40:44 +02:00
|
|
|
uint8_t spi_cs;
|
2020-07-28 21:54:20 +02:00
|
|
|
static uint8_t spdr_next = 0;
|
2020-07-27 21:39:29 +02:00
|
|
|
|
2020-07-19 18:40:44 +02:00
|
|
|
spi_cs = !(PORT_SPI(PIN) & PIN_SPI_CS);
|
2020-07-27 21:39:29 +02:00
|
|
|
|
2020-07-19 18:40:44 +02:00
|
|
|
if (spi_cs) {
|
|
|
|
if (SPSR & (1 << SPIF)) {
|
2020-07-28 21:54:20 +02:00
|
|
|
switch (y) {
|
2020-07-30 16:23:23 +02:00
|
|
|
case Y_MAX - 1:
|
2020-07-30 17:11:48 +02:00
|
|
|
spdr_next = batmon_get_voltage();
|
2020-07-28 21:54:20 +02:00
|
|
|
break;
|
|
|
|
}
|
2020-07-30 16:23:23 +02:00
|
|
|
SPDR = spdr_next;
|
2020-07-19 18:40:44 +02:00
|
|
|
lcd_set_buffer(x, y, SPDR);
|
|
|
|
if (y == 0) {
|
2020-07-28 21:54:20 +02:00
|
|
|
y = Y_MAX;
|
2020-07-19 18:40:44 +02:00
|
|
|
x++;
|
2020-07-19 21:20:30 +02:00
|
|
|
if (x == DISPLAY_WIDTH) {
|
2020-07-19 18:40:44 +02:00
|
|
|
x = 0;
|
2020-07-19 21:20:30 +02:00
|
|
|
new_data = 1; // Only update the display if a full frame was received
|
|
|
|
}
|
2020-07-19 18:40:44 +02:00
|
|
|
} else {
|
|
|
|
y--;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
} else {
|
2020-07-19 21:20:30 +02:00
|
|
|
if (new_data) {
|
2020-07-19 18:40:44 +02:00
|
|
|
lcd_display();
|
2020-07-19 21:20:30 +02:00
|
|
|
new_data = 0;
|
2020-07-28 21:54:20 +02:00
|
|
|
} else if ((y == Y_MAX - 3) && (x == 0)) { // If the last one was a I/O frame
|
|
|
|
input_clear_events();
|
2020-07-19 18:40:44 +02:00
|
|
|
}
|
|
|
|
x = 0;
|
2020-07-28 21:54:20 +02:00
|
|
|
y = Y_MAX;
|
|
|
|
SPDR = get_switch_event();
|
|
|
|
spdr_next = get_rotary_delta();
|
2020-07-19 18:40:44 +02:00
|
|
|
}
|
2020-07-27 21:39:29 +02:00
|
|
|
|
|
|
|
return spi_cs;
|
2020-07-19 18:40:44 +02:00
|
|
|
}
|
|
|
|
|
2020-07-30 19:57:46 +02:00
|
|
|
void lcd_title(const char *msg1, const char *msg2)
|
2020-07-27 21:39:29 +02:00
|
|
|
{
|
2020-07-30 19:57:46 +02:00
|
|
|
lcd_clrscr();
|
2020-07-19 18:40:44 +02:00
|
|
|
lcd_gotoxy(0, 0);
|
|
|
|
lcd_puts_p(PSTR("== Internet Radio =="));
|
|
|
|
lcd_drawLine(0, 9, 120, 9, WHITE);
|
|
|
|
lcd_gotoxy(0, 2);
|
2020-07-30 19:57:46 +02:00
|
|
|
lcd_puts_p(msg1);
|
2020-07-19 18:40:44 +02:00
|
|
|
lcd_gotoxy(0, 3);
|
2020-07-30 19:57:46 +02:00
|
|
|
lcd_puts_p(msg2);
|
2020-07-19 18:40:44 +02:00
|
|
|
lcd_display();
|
2020-07-27 21:39:29 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
int main()
|
|
|
|
{
|
2020-07-30 19:57:46 +02:00
|
|
|
char *post_msg;
|
2020-07-30 21:41:50 +02:00
|
|
|
uint8_t sched = 0;
|
2020-07-30 19:57:46 +02:00
|
|
|
|
|
|
|
MCUSR &= ~(1 << WDRF);
|
|
|
|
WDTCSR = (1 << WDCE);
|
2020-07-27 21:39:29 +02:00
|
|
|
cli();
|
2020-07-31 18:23:58 +02:00
|
|
|
_delay_ms(25);
|
2020-07-27 21:39:29 +02:00
|
|
|
|
2020-07-30 19:57:46 +02:00
|
|
|
suspend();
|
|
|
|
|
2020-07-31 19:07:11 +02:00
|
|
|
pm_init();
|
2020-07-30 19:57:46 +02:00
|
|
|
lcd_init(LCD_DISP_ON);
|
|
|
|
lcd_title(PSTR("Starting IOC Rev."), PSTR(GITREV));
|
2020-07-27 21:39:29 +02:00
|
|
|
spi_init();
|
|
|
|
systick_init();
|
|
|
|
input_init();
|
2020-07-30 17:11:48 +02:00
|
|
|
batmon_init();
|
2020-07-30 19:57:46 +02:00
|
|
|
if (post_msg = post()) {
|
|
|
|
lcd_title(PSTR("POST Error!"), post_msg);
|
|
|
|
_delay_ms(2000);
|
|
|
|
reset();
|
|
|
|
}
|
|
|
|
|
2020-07-31 19:07:11 +02:00
|
|
|
lcd_title(PSTR("Starting up."), PSTR("Please wait."));
|
|
|
|
pm_sbc_on();
|
2020-07-19 18:40:44 +02:00
|
|
|
_delay_ms(10);
|
2020-07-31 20:49:40 +02:00
|
|
|
timer_set(TIMID_POWEROFF, MS_TO_TICKS(TIME_POWEROFF));
|
2020-07-31 19:07:11 +02:00
|
|
|
|
|
|
|
lcd_title(PSTR("Starting up."), PSTR("Please wait..."));
|
2020-07-27 21:39:29 +02:00
|
|
|
|
2020-07-19 18:40:44 +02:00
|
|
|
while (1) {
|
2020-07-27 21:39:29 +02:00
|
|
|
if (!spi_proc()) {
|
2020-07-30 21:41:50 +02:00
|
|
|
switch (sched) {
|
|
|
|
case 0:
|
|
|
|
timer_proc();
|
|
|
|
break;
|
|
|
|
case 1:
|
|
|
|
input_proc();
|
|
|
|
break;
|
2020-07-31 19:07:11 +02:00
|
|
|
case 2:
|
|
|
|
if (get_sbc_state())
|
|
|
|
timer_set(TIMID_POWEROFF, MS_TO_TICKS(TIME_POWEROFF));
|
|
|
|
if (timer_expired(TIMID_POWEROFF))
|
|
|
|
reset();
|
2020-07-30 21:41:50 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
sched = sched + 1;
|
2020-07-31 19:07:11 +02:00
|
|
|
if (sched == 5) {
|
2020-07-30 21:41:50 +02:00
|
|
|
sched = 0;
|
|
|
|
if (batmon_proc())
|
|
|
|
reset();
|
2020-07-27 21:39:29 +02:00
|
|
|
}
|
2020-07-19 18:40:44 +02:00
|
|
|
}
|
|
|
|
return 0;
|
2020-07-11 12:41:08 +02:00
|
|
|
}
|