#include #include #include #include #include #include #include #include "serial.h" #include "ethernet.h" #include "w5100.h" #include "socket.h" #define MAC_SIZE 6 #define IPV4_SIZE 4 #define PRESCALER 1024 #define NB_TICK 6250 #define DELAY 300 bool sleep = false; //Etat de l'interface : true = mode sommeil / false = mode eveillé unsigned char comMem[2] = {'\0'}; //Commande en mémoire unsigned char msg[2]; //Message qui sera envoyé via TCP typedef enum type_msg {TCP,UDP}type_msg; bool isTCP_received = false; // <- Msg TCP reçu ou non? Permet la réouverture de la socket TCP pour la réécoute TCP void init_led(void) { DDRD = 0xFF; if (sleep == true) // si IT dort { PORTD = 0x08; } else { PORTD = 0x00; } } void init_timer(void) { TCCR1B |= _BV(WGM12); TCCR1B |= _BV(CS12); // Facteur de division 1024 TCCR1B |= _BV(CS10); OCR1A = NB_TICK; TIMSK1 |= _BV(OCIE1A); } ISR(TIMER1_COMPA_vect) { if(sleep == false) PORTD ^= 0x20; } void request(SOCKET sock,uint8 rq[2],uint8 addr[IPV4_SIZE],type_msg type) { uint8 x = rq [0] & 0xE0; //Récupération de la commande x = x >> 5; uint16 y = rq[0] & 0x1F; //Récupération du pourcentage y = y << 8; y += rq[1]; float per = y*0.0122; if (type == UDP) { SOCKET s = 2; //Creation socket TCP pour réponse à la broadcast UDP switch(x) { case 0: // GETSTATUS + connection ( Reçu via UDP broadcast, mais on répond en TCP ! ) printf("Reception UDP getstatus\n"); if(socket(s,Sn_MR_TCP,2020,0) == 0) { printf("SOCKET TCP NON INITILIASEE \n"); break; } if (connect(s,addr,2020)) { _delay_ms(DELAY); //l'IT doit attendre un peu avant d'envoyer if (sleep==false) { strcpy(msg,"\x20\x01"); } else { strcpy(msg,"\x20\x00"); } send(s,msg,sizeof(char)*strlen(msg)); disconnect(s); } break; case 2: // SLEEP MODE ON/OFF if ((y == 0x0001) & (sleep == true)) { sleep = false; printf("MODE EVEILLE\n"); PORTD = PORTD ^ 0x08; } else if ((y == 0x0000) & (sleep == false)) { sleep = true; printf("MODE SOMMEIL\n"); PORTD = 0x08; } break; case 3: // GETCOMMAND if(socket(s,Sn_MR_TCP,2020,0) == 0) { printf("SOCKET TCP NON INITILIASEE \n"); break; } if (connect(s,addr,2020)) { _delay_ms(DELAY); //l'IT doit attendre un peu avant d'envoyer msg[0]=comMem[0]; msg[1]=comMem[1]; send(s,msg,sizeof(char)*strlen(msg)); disconnect(s); } break; case 5: // SETCOMMANDE if (sleep == false) { OCR1A = NB_TICK - 53*(int)per; comMem[0] = rq[0]; comMem[1] = rq [1]; //save } break; } } else if (type == TCP) { switch(x) { case 0: // GETSTATUS if (sleep==false) { strcpy(msg,"\x20\x01"); } else { strcpy(msg,"\x20\x00"); } send(sock,msg,sizeof(char)*strlen(msg)); disconnect(sock); break; case 2: // SLEEP MODE ON/OFF if ((y == 0x0001) & (sleep == true)) { sleep = false; printf("MODE EVEILLE\n"); PORTD = PORTD ^ 0x08; } else if ((y == 0x0000) & (sleep == false)) { sleep = true; printf("MODE SOMMEIL\n"); PORTD = 0x08; } disconnect(sock); break; case 3: // GETCOMMAND printf("Request ComMem\n"); strcpy(msg,comMem); send(sock,msg,sizeof(char)*strlen(msg)); disconnect(sock); break; case 5: // SETCOMMANDE if (sleep == false) { OCR1A = NB_TICK - 53*(int)per; comMem[0] = rq[0]; comMem[1] = rq [1]; //save } disconnect(sock); break; } } } int main(void) { /* VARIABLES */ SOCKET sUDP=0,sTCP=1; uint8_t mac[MAC_SIZE] = {0xA0,0xBD,0xCD,0xDD,0xED,0xFD}; // <- Adresse MAC de l'IT uint8_t ip[IPV4_SIZE] = {172,26,145,205}; // <- Adresse IPV4 de l'IT uint8_t gateway[4] = {172,26,145,35}; // <- Adresse passerelle uint8_t mask[4] = {255,255,255,0}; // <- Masque de sous réseau uint8_t buf[2]; // <- Sert à stocker les deux octets recus via TCP & UDP uint16_t datasize; // <- Sert à stocker la longueur du datagramme uint8_t addr[IPV4_SIZE]; // <- Sert à stocker l'adresse IP de l'émetteur uint16_t port; // <- Sert à stocker le port utilisé par l'émetteur type_msg type; // <- Enumeration : type de message recu {TCP,UDP} /* INITIALISATION */ init_led(); // <- Initialise les LEDS init_timer(); // <- Initialise le compteur pour la fréquence du clignotement LED init_printf(); // <- Initialise la communication série ethernet_init(mac,ip,gateway,mask); // <- Initialise le shield ethernet if (!socket(sUDP,Sn_MR_UDP,2020,0)) { return -1; } if (!socket(sTCP,Sn_MR_TCP,2020,0)) { return -1; } comMem[0] = 0xA0; comMem[1] = 0x00; // Commande en mémoire (default) listen(sTCP); /* BOUCLE PRINCIPALE */ while(1) { sei(); if (isTCP_received == true) { socket(sTCP,Sn_MR_TCP,2020,0); listen(sTCP); isTCP_received=false; } if (IINCHIP_READ(Sn_SR(sTCP)) == SOCK_ESTABLISHED) // Quelqu'un s'est connecté en TCP { cli(); while(!isTCP_received) // On boucle en attendant le message du client { if(recv(sTCP,buf,2)>0) { type=TCP; request(sTCP,buf,NULL,type); // On traite le message du client isTCP_received=true; } } } if((datasize=recvfrom(sUDP,buf,sizeof(buf),addr,&port)) == 8) // Quelqu'un a envoyé 2 octets via UDP { cli(); type=UDP; printf("MESSAGE RECU VIA UDP %x %x \n",buf[0],buf[1]); request(sUDP,buf,addr,type); // On traite le message du client } } close(sTCP); close(sUDP); return 0; }