#include // |Mac adress| const char SSDP_RESPONSE[] PROGMEM = "HTTP/1.1 200 OK\r\nCACHE-CONTROL: max-age=1200\r\nEXT:\r\nSERVER:Arduino\r\nST: upnp:rootdevice\r\nUSN: uuid:abcdefgh-7dec-11d0-a765-7499692d3040\r\nLOCATION: http://"; //dont forget our mac adress USN: uuid:abcdefgh-7dec-11d0-a765-Mac addr const char SSDP_RESPONSE_XML[] PROGMEM = "/??\r\n\r\n"; // here is the adress of xml file /?? in this exemple but you could use another /upnp.xml\r\n\r\n const char XML_DESCRIP[] PROGMEM = "HTTP/1.1 200 OK\r\nContent-Type: text/xml\r\n\r\n\rurn:schemas-upnp-org:device:BinaryLight:1/ArduinoFredycpuhttp://fredycpu.pro1uuid:abcdefgh-7dec-11d0-a765-7499692d3040 "; const char SSDP_NOTIFY[] PROGMEM = "NOTIFY * HTTP/1.1\r\nHOST: 239.255.255.250:1900\r\nCACHE-CONTROL: max-age=1200\r\nNT: upnp:rootdevice\r\nUSN: uuid:abcdefga-7dec-11d0-a765-7499692d3040::upnp:rootdevice\r\nNTS: ssdp:alive\r\nSERVER: Arduino UPnP/1.0\r\nLOCATION: http://"; //dont forget our mac adress USN: uuid:abcdefgh-7dec-11d0-a765-Mac addr // in XML_DESCRIP // urn:schemas-upnp-org:device:BinaryLight:1 // declare as home automation // in XML_DESCRIP // Arduino // declare the name of the service here Arduino // in XML_DESCRIP // / // adress of the page who would opened on service double click ,you could use http://ip but if you use dhcp it's better so and dont wase memory // this is the entire protocol, but you can try to use SSDP_NOTIFY as SSDP_RESPONSE with most systems will work and you can free a bit of flash mem. static byte myip[] = { 192,168,0,67 }; static byte gwip[] = { 192,168,0,250 }; static byte ssdp[] = { 239,255,255,250 }; static byte mymac[] = { 0x74,0x99,0x69,0x2D,0x30,0x40 }; // if you change it you must update SSDP_RESPONSE and XML_DESCRIP byte Ethernet::buffer[750]; // tcp ip send and receive buffer unsigned long timer=9999; const char pageA[] PROGMEM = "HTTP/1.0 200 OK\r\n" "Content-Type: text/html\r\n" "\r\n" "" "" "multipackets Test" "" "" "Start here
" "Image test
" "

packet 1

" "

" "the first packet send " "

" ; const char pageB[] PROGMEM = "

packet 2

" "

" "if you read this it mean it works" "

" ; const char pageC[] PROGMEM = "

packet 3

" "

" "if you read this it mean it works" "

" ; const char pageD[] PROGMEM = "

packet 4

" "

" "if you read this it mean it works" "

" ; void setup(){ ether.begin(sizeof Ethernet::buffer, mymac , 10);// 53 for the mega ethernet shield and 10 for normal ethernet shield ether.staticSetup(myip, gwip); ENC28J60::disableMulticast(); //disable multicast filter means enable multicast reception Serial.begin(115200); } void loop(){ wait: word pos = ether.packetLoop(ether.packetReceive()); // check if valid tcp data is received if (pos) { char* data = (char *) Ethernet::buffer + pos; if (strncmp("GET / ", data, 6) == 0) { ether.httpServerReplyAck(); // send ack to the request memcpy_P(ether.tcpOffset(), pageA, sizeof pageA); // send first packet and not send the terminate flag ether.httpServerReply_with_flags(sizeof pageA - 1,TCP_FLAGS_ACK_V); memcpy_P(ether.tcpOffset(), pageB, sizeof pageB); // send second packet and not send the terminate flag ether.httpServerReply_with_flags(sizeof pageB - 1,TCP_FLAGS_ACK_V); memcpy_P(ether.tcpOffset(), pageC, sizeof pageC); // send thirdt packet and not send the terminate flag ether.httpServerReply_with_flags(sizeof pageC - 1,TCP_FLAGS_ACK_V); memcpy_P(ether.tcpOffset(), pageD, sizeof pageD); // send fourth packet and send the terminate flag ether.httpServerReply_with_flags(sizeof pageD - 1,TCP_FLAGS_ACK_V|TCP_FLAGS_FIN_V); goto wait; } if (strncmp("GET /??", data, 7) == 0) { // description of services (normaly an xml file but here .....) ether.httpServerReplyAck(); memcpy_P(Ethernet::buffer + TCP_OPTIONS_P,XML_DESCRIP, sizeof XML_DESCRIP); ether.httpServerReply_with_flags(sizeof XML_DESCRIP - 1 ,TCP_FLAGS_ACK_V|TCP_FLAGS_FIN_V); goto wait; } if (strncmp("M-SEARCH", data, 8) == 0) { // service discovery request comes here (udp protocol) ssdpresp(); goto wait; } } if (((millis()-timer)>50000)||(timer>millis())) { timer=millis(); ssdpnotify(); } } void ssdpresp() { //response to m-search byte ip_dst[4]; unsigned int port_dst=Ethernet::buffer[34]*256+Ethernet::buffer[35];//extract source port of request for( int i=0; i<4;i++) { //extract source IP of request ip_dst[i]=Ethernet::buffer[i+26]; } int udppos = UDP_DATA_P; EtherCard::udpPrepare(1900,ip_dst,port_dst); memcpy_P(Ethernet::buffer + udppos, SSDP_RESPONSE, sizeof SSDP_RESPONSE); udppos = udppos + sizeof SSDP_RESPONSE-1; addip(udppos); } void ssdpnotify() { //Notification int udppos = UDP_DATA_P; EtherCard::udpPrepare(1900,ssdp,1900); memcpy_P(Ethernet::buffer + udppos, SSDP_NOTIFY, sizeof SSDP_NOTIFY); udppos = udppos + sizeof SSDP_NOTIFY-1; addip(udppos); } void addip(int udppos) { // add current ip to the request and send it int adr; for(int i=0;i<4;i++) { // extract the current ip of arduino adr = ether.myip[i]/100; if (adr) { Ethernet::buffer[udppos]=adr+48; udppos++; } adr=(ether.myip[i]%100)/10; if (adr) { Ethernet::buffer[udppos]=adr+48; udppos++; } adr=ether.myip[i]%10; Ethernet::buffer[udppos]=adr+48; udppos++; Ethernet::buffer[udppos]=46; udppos++; //"." } udppos--;//erase the last point memcpy_P(Ethernet::buffer + udppos,SSDP_RESPONSE_XML,sizeof SSDP_RESPONSE_XML); udppos = udppos + sizeof SSDP_RESPONSE_XML; udppos--; EtherCard::udpTransmit(udppos-UDP_DATA_P); // send all to the computer who make the request on her ip and port who make the request }