
#define DEBUGO

#ifdef __USE_CMSIS
#include "LPC17xx.h"
#endif

#include "system_LPC17xx.h"

#include "lwip/tcp_impl.h" //definice tcp/ip servisnich intervalu
#include "lwip/udp.h"
#include "ethernetif.h" //definice sitoveho rozhrani
#include "lwip/netif.h"
#include "lwip/memp.h"
#include "httpd.h"
#include "onewire.h"
#include "ds18b20.h"
#include "lwip/stats.h"

#define IP1 192
#define IP2 168
#define IP3 1
#define IP4 28

#define GW1 192
#define GW2 168
#define GW3 1
#define GW4 1

#define MASK1 255
#define MASK2 255
#define MASK3 255
#define MASK4 0

void lwip_init(void);

/* SysTick Interrupt Handler (1ms) */
void SysTick_Handler (void);

static struct netif  lpc17xx_netif_data;
static struct netif *lpc17xx_netif = &lpc17xx_netif_data;

static u32_t         last_arp_time;
static u32_t         last_tcpslow_time;
static u32_t         last_tcpfast_time;

/* Server-Side Include (SSI) demo ..........................................*/
static char const * const ssi_tags[] = {
    "s_xmit",
    "s_recv",
    "s_fw",
    "s_drop",
    "s_chkerr",
    "s_lenerr",
    "s_memerr",
    "s_rterr",
    "s_proerr",
    "s_opterr",
    "s_err",
};

static int ssi_handler(int iIndex, char *pcInsert, int iInsertLen);

volatile u32_t systick_counter;				/* counts 1ms timeTicks */

/* Common Gateway Interface (CG) demo .....................................*/
static char const *cgi_display(int index, int numParams, char const *param[], char const *value[]);

static tCGI const cgi_handlers[] = {
    { "/display.cgi", &cgi_display },
};

int main(void) {
	
	uint32_t curTicks;

	SysTick_Config(SystemCoreClock/1000 - 1); /* Generate interrupt each 1 ms   */

	SystemInit();
	ow_init();
	lwip_init();
	httpd_init();
	http_set_ssi_handler(&ssi_handler, ssi_tags, 11);
	http_set_cgi_handlers(cgi_handlers, 1);

	while(1) {
		curTicks = systick_counter;

		ethernetif_input(lpc17xx_netif);

		if (curTicks - last_arp_time > ARP_TMR_INTERVAL)
		{
			etharp_tmr();
			last_arp_time = curTicks;
		}

		if (curTicks - last_tcpfast_time > TCP_FAST_INTERVAL)
		{
			last_tcpfast_time = curTicks;
			tcp_fasttmr();
		}

		if (curTicks - last_tcpslow_time > TCP_SLOW_INTERVAL)
		{
			last_tcpslow_time = curTicks;
			tcp_slowtmr();
		}
	}

	return 0 ;
}

void lwip_init(void)
{
	struct ip_addr ipaddr, netmask, gw;

	mem_init();
	memp_init();
	pbuf_init();
	etharp_init();
	ip_init();
	udp_init();
	tcp_init();

	IP4_ADDR(&gw, GW1,GW2,GW3,GW4);
	IP4_ADDR(&ipaddr, IP1,IP2,IP3,IP4);
	IP4_ADDR(&netmask, MASK1,MASK2,MASK3,MASK4);

#ifdef DEBUGO
	printf("IP adresa: %d.%d.%d.%d\n", IP1,IP2,IP3,IP4);
	printf("Maska: %d.%d.%d.%d\n", MASK1,MASK2,MASK3,MASK4);
	printf("Brana: %d.%d.%d.%d\n", GW1,GW2,GW3,GW4);
#endif

	netif_set_default(netif_add(lpc17xx_netif, &ipaddr, &netmask, &gw, NULL, ethernetif_init, ethernet_input));
	netif_set_up(lpc17xx_netif);
}

void SysTick_Handler (void)
{
	systick_counter++;
}

/* Server-Side Include (SSI) handler .......................................*/
static int ssi_handler(int iIndex, char *pcInsert, int iInsertLen) {
    struct stats_proto *stats = &lwip_stats.link;
    STAT_COUNTER value = 0;

    switch (iIndex) {
        case 0:                                                 /* s_xmit   */
            value = "neco";
            break;
        case 1:                                                 /* s_recv   */
            value = stats->recv;
            break;
        case 2:                                                 /* s_fw     */
            value = stats->fw;
            break;
        case 3:                                                 /* s_drop   */
            value = stats->drop;
            break;
        case 4:                                                 /* s_chkerr */
            value = stats->chkerr;
            break;
        case 5:                                                 /* s_lenerr */
            value = stats->lenerr;
            break;
        case 6:                                                 /* s_memerr */
            value = stats->memerr;
            break;
        case 7:                                                 /* s_rterr  */
            value = stats->rterr;
            break;
        case 8:                                                 /* s_proerr */
            value = stats->proterr;
            break;
        case 9:                                                 /* s_opterr */
            value = stats->opterr;
            break;
        case 10:                                                /* s_err    */
            value = stats->err;
            break;
    }
    printf(pcInsert, LWIP_HTTPD_MAX_TAG_INSERT_LEN, "%d", value);
    return snprintf(pcInsert, LWIP_HTTPD_MAX_TAG_INSERT_LEN, "%d", value);
}

/* Common Gateway Iinterface (CG) handler ..................................*/
static char const *cgi_display(int index, int numParams, char const *param[], char const *value[])
{
    int i;
    for (i = 0; i < numParams; ++i) {
        if (strstr(param[i], "text") != (char *)0) {   /* param text found? */
            //TextEvt *te = Q_NEW(TextEvt, DISPLAY_CGI_SIG);
            //strncpy(te->text, value[i], Q_DIM(te->text));
            //QF_PUBLISH((QEvent *)te, AO_LwIPMgr);
        	printf("%s\n", value[i]);
        	ow_find_devices();
            return "/thank_you.htm";
        }
    }
    return (char *)0;/*no URI, HTTPD will send 404 error page to the browser*/
}
