Ignition monitoring by level interrupt on PB4.
This commit is contained in:
parent
a8d7b7a282
commit
18913f5f6a
41
README.md
Normal file
41
README.md
Normal file
@ -0,0 +1,41 @@
|
|||||||
|
# AVR Toolchain
|
||||||
|
|
||||||
|
## Prerequisites
|
||||||
|
|
||||||
|
```shell
|
||||||
|
apt install flex byacc bison build-essential apt install libgmp-dev libmpfr-dev libmpc-dev
|
||||||
|
```
|
||||||
|
|
||||||
|
## Binutils
|
||||||
|
|
||||||
|
```shell
|
||||||
|
$ wget http://ftp.gnu.org/gnu/binutils/binutils-2.33.1.tar.xz
|
||||||
|
$ tar xvf binutils-2.33.1.tar.xz
|
||||||
|
$ cd binutils-2.33.1
|
||||||
|
$ ./configure --target=avr --program-prefix="avr-"
|
||||||
|
$ make -j4
|
||||||
|
$ make install
|
||||||
|
```
|
||||||
|
|
||||||
|
## GCC
|
||||||
|
|
||||||
|
```shell
|
||||||
|
$ wget ftp://ftp.fu-berlin.de/unix/languages/gcc/releases/gcc-9.2.0/gcc-9.2.0.tar.xz
|
||||||
|
$ tar cvf gcc-9.2.0.tar.xz
|
||||||
|
$ mkdir avrgcc-9.2.0
|
||||||
|
$ cd avrgcc-9.2.0
|
||||||
|
$ ../gcc-9.2.0/configure --target=avr --enable-languages=c,c++ --disable-libssp
|
||||||
|
$ make -j4
|
||||||
|
$ make install
|
||||||
|
```
|
||||||
|
|
||||||
|
## avr-libc
|
||||||
|
|
||||||
|
```shell
|
||||||
|
$ wget http://download.savannah.gnu.org/releases/avr-libc/avr-libc-2.0.0.tar.bz2
|
||||||
|
$ tar xvf avr-libc-2.0.0.tar.bz2
|
||||||
|
$ cd avr-libc-2.0.0
|
||||||
|
$ ./configure --host=avr
|
||||||
|
$ make -j4
|
||||||
|
$ make install
|
||||||
|
```
|
110
src/main.c
110
src/main.c
@ -1,37 +1,115 @@
|
|||||||
|
#include <stdbool.h>
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
|
|
||||||
#define F_CPU 1000000UL
|
#define F_CPU 1000000UL
|
||||||
|
|
||||||
#include <avr/interrupt.h>
|
#include <avr/interrupt.h>
|
||||||
#include <avr/io.h>
|
#include <avr/io.h>
|
||||||
|
#include <avr/power.h>
|
||||||
#include <avr/sleep.h>
|
#include <avr/sleep.h>
|
||||||
#include <avr/wdt.h>
|
#include <avr/wdt.h>
|
||||||
#include <util/delay.h>
|
|
||||||
|
|
||||||
volatile int tick;
|
#define MOSI_PIN 0
|
||||||
|
#define MISO_PIN 1
|
||||||
|
#define SCK_PIN 2
|
||||||
|
#define POWER_PIN 3
|
||||||
|
#define IGNITION_PIN 4
|
||||||
|
|
||||||
int main(void)
|
#define SHUTDOWN_TIME_MS 5000UL
|
||||||
|
|
||||||
|
#define ignition_on() (PINB & (1 << IGNITION_PIN))
|
||||||
|
#define power_on() (PINB & (1 << POWER_PIN))
|
||||||
|
|
||||||
|
bool is_shutdown;
|
||||||
|
volatile uint32_t tick;
|
||||||
|
|
||||||
|
enum power {
|
||||||
|
off = 0,
|
||||||
|
on
|
||||||
|
};
|
||||||
|
|
||||||
|
void setup_gpio()
|
||||||
{
|
{
|
||||||
cli();
|
|
||||||
tick = 0;
|
|
||||||
DDRB = 0xff;
|
DDRB = 0xff;
|
||||||
|
PORTB = 0;
|
||||||
|
DDRB &= ~(1 << IGNITION_PIN);
|
||||||
|
PORTB |= (1 << IGNITION_PIN); // enable pull-up
|
||||||
|
|
||||||
|
GIMSK |= (1 << PCIE); // Enable Pin Change Interrupts
|
||||||
|
PCMSK |= (1 << IGNITION_PIN); // Use PB4 as interrupt pin
|
||||||
|
}
|
||||||
|
|
||||||
|
void setup_timer0()
|
||||||
|
{
|
||||||
TCCR0A = (1 << WGM01);
|
TCCR0A = (1 << WGM01);
|
||||||
TCCR0B = (1 << CS01);
|
TCCR0B = (1 << CS01); // prescaler = 8
|
||||||
TIMSK |= (1 << OCIE0A); // enable compare match interrupt
|
TIMSK |= (1 << OCIE0A); // enable compare match interrupt
|
||||||
|
|
||||||
// ((1000000 / 8) / 1000) = 125
|
// ((1000000 / 8) / 1000) = 125
|
||||||
OCR0A = 125 - 1;
|
OCR0A = 125 - 1;
|
||||||
|
}
|
||||||
|
|
||||||
// TIMSK |= (1 << TOIE0);
|
void setup_watchdog()
|
||||||
|
{
|
||||||
|
MCUSR &= ~(1 << WDRF);
|
||||||
|
WDTCR = (1 << WDCE) | (1 << WDE);
|
||||||
|
WDTCR = (1 << WDIE) | (1 << WDP2) | (1 << WDP1);
|
||||||
|
}
|
||||||
|
|
||||||
|
void switch_power(enum power power)
|
||||||
|
{
|
||||||
|
if(power) {
|
||||||
|
PORTB |= (1 << POWER_PIN);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
PORTB &= ~(1 << POWER_PIN);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int main(void)
|
||||||
|
{
|
||||||
|
uint32_t shutdown_expire = 0;
|
||||||
|
tick = 0;
|
||||||
|
is_shutdown = false;
|
||||||
|
setup_gpio();
|
||||||
|
setup_timer0();
|
||||||
|
|
||||||
|
ADCSRA = 0;
|
||||||
|
ADCSRB = 0;
|
||||||
|
|
||||||
|
set_sleep_mode(SLEEP_MODE_PWR_DOWN);
|
||||||
|
|
||||||
sei();
|
sei();
|
||||||
|
|
||||||
while(1) {
|
while(1) {
|
||||||
if(tick >= 1000) {
|
if(ignition_on()) {
|
||||||
PORTB ^= (1 << PB4);
|
if(!power_on()) {
|
||||||
tick = 0;
|
switch_power(on);
|
||||||
|
is_shutdown = false;
|
||||||
|
}
|
||||||
|
sleep_enable();
|
||||||
|
sleep_cpu();
|
||||||
|
sleep_disable();
|
||||||
|
} else {
|
||||||
|
if(!is_shutdown) {
|
||||||
|
is_shutdown = true;
|
||||||
|
shutdown_expire = tick + SHUTDOWN_TIME_MS;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if(shutdown_expire < tick) {
|
||||||
|
if(power_on()) {
|
||||||
|
switch_power(off);
|
||||||
|
}
|
||||||
|
// setup_watchdog();
|
||||||
|
sleep_enable();
|
||||||
|
sleep_cpu();
|
||||||
|
sleep_disable();
|
||||||
|
// wdt_disable();
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -39,3 +117,15 @@ ISR(TIM0_COMPA_vect)
|
|||||||
{
|
{
|
||||||
tick++;
|
tick++;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// wake up by level interrupt on PB4
|
||||||
|
ISR(PCINT0_vect)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
// wake up by watchdog interrupt
|
||||||
|
ISR(WDT_vect)
|
||||||
|
{
|
||||||
|
WDTCR |= (1 << WDIE);
|
||||||
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user