90 lines
3.2 KiB
C
Executable File
90 lines
3.2 KiB
C
Executable File
#include <avr/io.h>
|
||
#include <avr/interrupt.h>
|
||
#include <util/delay.h>
|
||
|
||
#define Link1pin PB2 // Пин оптопары светодиода линка
|
||
#define Link2pin PB1 // Пин оптопары светодиода линка
|
||
|
||
#define PLCPWRpin PB4 // Питание PLC
|
||
#define EXTPWRpin PB0 // Питание модема
|
||
|
||
#define MODE_WAIT_LINK 1
|
||
#define MODE_LINK_UP 2
|
||
#define MODE_SLEEP 3
|
||
|
||
uint8_t cur_mode = 0; // Текущий режим
|
||
uint8_t new_mode = 0; // Новый режим
|
||
|
||
volatile uint16_t timer = 0;
|
||
|
||
ISR(TIM0_OVF_vect)
|
||
{
|
||
if(timer > 0)
|
||
{
|
||
timer--;
|
||
}
|
||
}
|
||
|
||
uint8_t check_link(void) // Проверка линка
|
||
{
|
||
if(!(PINB & (1 << Link1pin)) || !(PINB & (1 << Link2pin))) // Если горит хотя бы один светодиод линка
|
||
{
|
||
return 1; // То возвращаем 1
|
||
}
|
||
else // Если нет
|
||
{
|
||
return 0; // То возвращаем 0
|
||
}
|
||
}
|
||
|
||
int main(void)
|
||
{
|
||
DDRB &= ~((1<<Link1pin)|(1<<Link2pin)); // Пины к которым подключена оптопара - на вход
|
||
DDRB |= (1<<PLCPWRpin)|(1<<EXTPWRpin); // Пины управления транзисторами - на выход
|
||
PORTB |= (1<<Link1pin)|(1<<Link2pin)|(1<<PLCPWRpin); // Подтяжка выходов оптопар, управление внешним питанием(выключенное состояние, NPN)
|
||
PORTB &= ~(1<<EXTPWRpin); // Управление питанием PLC, выключенное состояние (P-канал)
|
||
new_mode = MODE_WAIT_LINK; // Переходи в режим ожидания линка
|
||
TCCR0B |= (1<<CS02)|(1<<CS00); // Делитель на 1024
|
||
TIMSK0 |= (1<<TOIE0); // Разрешаем прерывание по переполнению
|
||
sei(); // Разрешаем прерывания
|
||
while(1)
|
||
{
|
||
if(cur_mode != new_mode) // Переключение режимов
|
||
{
|
||
if(new_mode == MODE_WAIT_LINK)
|
||
{
|
||
PORTB &= ~(1<<PLCPWRpin); // PLC ON
|
||
timer = 270; // +- 60 сек
|
||
}
|
||
if(new_mode == MODE_LINK_UP)
|
||
{
|
||
PORTB |= (1<<EXTPWRpin); // Modem ON
|
||
timer = 270; // +- 60 сек
|
||
}
|
||
if(new_mode == MODE_SLEEP)
|
||
{
|
||
PORTB &= ~(1<<EXTPWRpin); // Modem OFF
|
||
PORTB |= (1<<PLCPWRpin); // PLC OFF
|
||
timer = 1350; // +- 5 минут
|
||
}
|
||
cur_mode = new_mode;
|
||
}
|
||
if (cur_mode == MODE_WAIT_LINK && check_link() == 1 && timer < 180) // Если мы в режиме ожидания линка и линк есть
|
||
{
|
||
new_mode = MODE_LINK_UP; // То переходим в рабочий режим
|
||
}
|
||
if (cur_mode == MODE_LINK_UP && check_link() == 1) // Если мы в рабочем режиме и линк есть
|
||
{
|
||
timer = 270; // +- 60 сек, то не даем таймеру обнулиться
|
||
}
|
||
if(timer == 0 && (cur_mode == MODE_WAIT_LINK || cur_mode == MODE_LINK_UP)) // Если таймер истек, а линка нет
|
||
{
|
||
new_mode = MODE_SLEEP; // То переходи в режим сна
|
||
}
|
||
if(timer == 0 && cur_mode == MODE_SLEEP) // Если спим и таймер истек
|
||
{
|
||
new_mode = MODE_WAIT_LINK; // То переходим в режим ожидания линка
|
||
}
|
||
}
|
||
}
|