#include <avr/io.h>
#include <avr/interrupt.h>
#include <avr/pgmspace.h>
#include <avr/eeprom.h>
#include <avr/wdt.h>
#include "usbdrv.h"
#include "oddebug.h"
#include <util/delay.h>
#define EEPROM_LOCATION (void *)37
#define DEBOUNCE_TIME 5
static void outputByte(uchar b)
{
PORTC = (PORTC & ~0x7f) | (b & 0x7f);}
static void tdelay(void)
{
_delay_ms(DEBOUNCE_TIME);
usbPoll();
_delay_ms(DEBOUNCE_TIME);
usbPoll();
_delay_ms(DEBOUNCE_TIME);
usbPoll();
_delay_ms(DEBOUNCE_TIME);
usbPoll();
_delay_ms(DEBOUNCE_TIME);
usbPoll();
_delay_ms(DEBOUNCE_TIME);
usbPoll();
_delay_ms(DEBOUNCE_TIME);
usbPoll();
}
static void toggleOutput(int outnr)
{
uchar status = eeprom_read_byte(EEPROM_LOCATION);
status ^= _BV(outnr);
eeprom_write_byte(EEPROM_LOCATION, status);
outputByte(status);
tdelay();
tdelay();
tdelay();
tdelay();
tdelay();
tdelay();
}
static void checkButton(uchar port, int pin, int out)
{
if (bit_is_clear(port, pin))
{
tdelay();
if (bit_is_clear(port, pin))
{
toggleOutput(out);
}
}
}
static void checkButtons(void)
{
checkButton(PIND,0,0);
checkButton(PIND,1,1);
checkButton(PIND,3,2);
checkButton(PIND,4,3);
checkButton(PIND,6,4);
checkButton(PIND,7,5);
}
static void computeOutputStatus(void)
{
uchar status = eeprom_read_byte(EEPROM_LOCATION);
outputByte(status);
}
USB_PUBLIC uchar usbFunctionSetup(uchar data[8])
{
usbRequest_t *rq = (void *)data;
uchar status = eeprom_read_byte(EEPROM_LOCATION);
static uchar replyBuf[2];
usbMsgPtr = replyBuf;
if(rq->bRequest == 0){
replyBuf[0] = rq->wValue.bytes[0];
replyBuf[1] = rq->wValue.bytes[1];
return 2;
}
if(rq->bRequest == 1){
replyBuf[0] = status;
replyBuf[1] = 0;
return 2;
}
if(rq->bRequest == 2 || rq->bRequest == 3){
uchar bit = rq->wIndex.bytes[0] & 7;
uchar mask = 1 << bit;
if(rq->bRequest == 2){
status |= mask;
eeprom_write_byte(EEPROM_LOCATION, status);
}else{
status &= ~mask;
eeprom_write_byte(EEPROM_LOCATION, status);
}
}
computeOutputStatus();
return 0;
}
#if !defined TCCR0 && defined TCCR0B
#define TCCR0 TCCR0B
#endif
#if !defined TIFR && defined TIFR0
#define TIFR TIFR0
#endif
int main(void)
{
uchar i;
DDRD = 0;
DDRC = 0xf3;
DDRB = 0;
PORTD = 0;
PORTB = 0;
PORTC = 0;
computeOutputStatus();
usbDeviceDisconnect();
i = 0;
while(--i){
_delay_ms(2);
}
usbDeviceConnect();
usbInit();
sei();
for(;;){
usbPoll();
checkButtons();
}
return 0;
}