//
// AVR IO pin operations
// Homelab library
//
// Department of Mechatronics
// Tallinn University of Technology
// ITT Group
// © Copyrights 2014
//

#include "pin.h"

pin LED0		__attribute__ ((weak))	= PIN(Q,2);
pin led_debug	__attribute__ ((weak))	= PIN(Q,2);
pin LED1		__attribute__ ((weak))	= PIN(H,5);
pin led_green	__attribute__ ((weak))	= PIN(H,5);
pin LED2		__attribute__ ((weak))	= PIN(H,4);
pin led_yellow	__attribute__ ((weak))	= PIN(H,4);
pin LED3		__attribute__ ((weak))	= PIN(H,3);
pin led_red		__attribute__ ((weak))	= PIN(H,3);

pin S0			__attribute__ ((weak))	= PIN(Q,3);
pin S1			__attribute__ ((weak))	= PIN(H,2);
pin S2			__attribute__ ((weak))	= PIN(H,1);
pin S3			__attribute__ ((weak))	= PIN(H,0);

//
// Function for filtering bounces on pin connected to the button
//
bool pin_get_debounced_value_proto(pin button, delay_function_ptr ms_delay_function)
{
    unsigned char buffer = 0xAA;
    unsigned char timeout = 100;

    // Wait until pin state is determined or timeout
    while (timeout-- > 0)
    {
        // Keep 8 bit FIFO buffer for pin value
        buffer <<= 1;
        buffer |= (pin_get_value(button) ? 0x01 : 0x00);

        // If all 8 bits are 1, the state is certainly true
        if (buffer == 0xFF)
        {
            return true;
        }

        // If all 8 bits are 0, the state is certainly false
        if (buffer == 0x00)
        {
            return false;
        }

        // Delay 1 ms
        ms_delay_function(1);
    }

    // On timeout return false
    return false;
}

bool button_read(pin button)
{
    unsigned char buffer = 0xAA;
    unsigned char timeout = 100;

    // Ootame, kuni nupu olek on selgunud või oleku selgitamine aegunud
    while (timeout-- > 0)
    {
        // 8-kohalise (bitise) olekupuhvri pidamine
        // Kõik eelmised olekud (bitid) nihutatakse vasakule
        // ja paremale lisatakse uus olek (bitt).
        buffer <<= 1;
        buffer |= (pin_get_value(button) ? 0x01 : 0x00);

        // Kui kõik 8 bitti on madalad, siis
        // nupp on kindlasti üleval
        if (buffer == 0xFF)
        {
            return 0;
        }

        // Kui kõik 8 bitti on kõrged, siis
        // nupp on kindlasti alla vajutatud
        if (buffer == 0x00)
        {
            return 1;
        }

        // Paus 1 millisekund
        // See funktsioon sisaldub Kodulabori teegis
        _delay_ms(1);
    }
    // Kui olekut ei õnnestunud välja selgitada, siis oletame,
    // et nuppu ei vajutatud
    return 0;
}

//
// Helper function for tracking compiled code
//
void supervisor_check(unsigned int repeat)
{
    uint8_t i=0;
    pin led_green = PIN(C, 5);
    pin led_yellow = PIN(C, 4);
    pin led_red = PIN(C, 3);

    pin_setup_output(led_green);
    pin_setup_output(led_yellow);
    pin_setup_output(led_red);

    while (i < repeat)
    {
        pin_clear(led_green);
        pin_clear(led_yellow);
        pin_clear(led_red);
        sw_delay_ms(250);
        pin_set(led_green);
        pin_set(led_yellow);
        pin_set(led_red);
        sw_delay_ms(250);
        i++;
    }
}

