/*------------------------------------------------------------*/ /* Sample task of http */ /*------------------------------------------------------------*/ #include #include #include #include #include "lwip/sys.h" #include "lwip/api.h" #include "lwip/httpd.h" //by ming 2005-01 add counter & runtimer u32_t runtime=0; u32_t counter=0; void httpd_init(void); /*-----------------------------------------------------------------------------------*/ static void conn_err(void *arg, err_t err) { struct http_state *hs; hs = arg; mem_free(hs); } /*-----------------------------------------------------------------------------------*/ static void close_conn(struct tcp_pcb *pcb, struct http_state *hs) { tcp_arg(pcb, NULL); tcp_sent(pcb, NULL); tcp_recv(pcb, NULL); mem_free(hs); tcp_close(pcb); } /*-----------------------------------------------------------------------------------*/ static void send_data(struct tcp_pcb *pcb, struct http_state *hs) { err_t err; u16_t len; /* We cannot send more data than space available in the send buffer. */ if(tcp_sndbuf(pcb) < hs->left) { len = tcp_sndbuf(pcb); } else { len = hs->left; } do { err = tcp_write(pcb, hs->file, len, 0); if(err == ERR_MEM) { len /= 2; } } while(err == ERR_MEM && len > 1); if(err == ERR_OK) { hs->file += len; hs->left -= len; } } /*-----------------------------------------------------------------------------------*/ static err_t http_poll(void *arg, struct tcp_pcb *pcb) { struct http_state *hs; hs = arg; /* printf("Polll\n");*/ if(hs == NULL) { /* printf("Null, close\n");*/ tcp_abort(pcb); return ERR_ABRT; } else { ++hs->retries; if(hs->retries == 4) { tcp_abort(pcb); return ERR_ABRT; } send_data(pcb, hs); } return ERR_OK; } /*-----------------------------------------------------------------------------------*/ static err_t http_sent(void *arg, struct tcp_pcb *pcb, u16_t len) { struct http_state *hs; hs = arg; hs->retries = 0; if(hs->left > 0) { send_data(pcb, hs); } else { close_conn(pcb, hs); } return ERR_OK; } /*-----------------------------------------------------------------------------------*/ static err_t http_recv(void *arg, struct tcp_pcb *pcb, struct pbuf *p, err_t err) { int i; char *data; struct http_state *hs; //by ming 2005.01 u8_t hour,min,sec; u16_t day; hs = arg; if(err == ERR_OK && p != NULL) { /* Inform TCP that we have taken the data. */ tcp_recved(pcb, p->tot_len); if(hs->file == NULL) { data = p->payload; if(*data =='G') { for(i = 0; i < 40; i++) { if( ((char *)data + 4)[i] == ' ' || ((char *)data + 4)[i] == '\r' || ((char *)data + 4)[i] == '\n') { ((char *)data + 4)[i] = 0; }// if }//for // if it was GET dsp.jpg if ((*(data+5) =='d') && (*(data+6) =='s') && (*(data+7) =='p')) { //hs->file = (char *)&jpeg; //hs->left = sizeof(jpeg); } // if it was GET dsk.jpg (large one) else if ((*(data+5) =='d') && (*(data+6) =='s') && (*(data+7) =='k')) { //hs->file = (char *)&large; //hs->left = sizeof(large); } // GET other files else { hs->file = (char *)&demo; hs->left = sizeof(demo); /* //----------------------------------------------------------------- //counter counter ++; sprintf(&demo[517],"%.6d",counter); //runtime runtime = OSTimeGet() / 80; ///100; //tmp by millin 2005.01.23 sec = runtime % 60; min = (runtime / 60) % 60; hour = (runtime / 3600) % 24; day = (runtime / 3600) / 24; sprintf(&demo[573],"%.3d:%.2d:%.2d:%.2d",day,hour,min,sec); //-----------------------------------------------------------------*/ } pbuf_free(p); send_data(pcb, hs); /* Tell TCP that we wish be to informed of data that has been successfully sent by a call to the http_sent() function. */ tcp_sent(pcb, http_sent); } //if(*data =='G') else { pbuf_free(p); close_conn(pcb, hs); } //else if(*data =='G') } //if(hs->file == NULL) else { pbuf_free(p); } } if(err == ERR_OK && p == NULL) { close_conn(pcb, hs); } return ERR_OK; } /*-----------------------------------------------------------------------------------*/ static err_t http_accept(void *arg, struct tcp_pcb *pcb, err_t err) { struct http_state *hs; tcp_setprio(pcb, TCP_PRIO_MIN); /* Allocate memory for the structure that holds the state of the connection. */ hs = mem_malloc(sizeof(struct http_state)); if(hs == NULL) { return ERR_MEM; } /* Initialize the structure. */ hs->file = NULL; hs->left = 0; hs->retries = 0; /* Tell TCP that this is the structure we wish to be passed for our callbacks. */ tcp_arg(pcb, hs); /* Tell TCP that we wish to be informed of incoming data by a call to the http_recv() function. */ tcp_recv(pcb, http_recv); tcp_err(pcb, conn_err); tcp_poll(pcb, http_poll, 4); return ERR_OK; } /*-----------------------------------------------------------------------------------*/ void httpd_init(void) { struct tcp_pcb *pcb; //by ming 2005.1 OSTimeSet((u32_t) 0x00000000); counter = (u32_t) 0x00000000; pcb = tcp_new(); tcp_bind(pcb, IP_ADDR_ANY, 80); pcb = tcp_listen(pcb); tcp_accept(pcb, http_accept); } char sendBuf[129]={0}; static err_t http_recv2(void *arg, struct tcp_pcb *pcb, struct pbuf *p, err_t err) { int i; char *data; struct http_state *hs; //by ming 2005.01 u8_t hour,min,sec; u16_t day; struct pbuf *q=NULL; int len=0; hs = arg; if(err == ERR_OK && p != NULL) { /* Inform TCP that we have taken the data. */ tcp_recved(pcb, p->tot_len); q=p; while(q) { data = q->payload; if(data) { len = q->len; while(len--) { sendBuf[len-1]=data[len-1]; } sendBuf[len]=0; hs->file = (char *)&sendBuf; hs->left = q->len; send_data(pcb, hs); // break; /* Tell TCP that we wish be to informed of data that has been successfully sent by a call to the http_sent() function. */ // tcp_sent(pcb, http_sent); } q=q->next; } pbuf_free(p); } if(err == ERR_OK && p == NULL) { // close_conn(pcb, hs); } return ERR_OK; } static err_t http_accept2(void *arg, struct tcp_pcb *pcb, err_t err) { struct http_state *hs; tcp_setprio(pcb, TCP_PRIO_MIN); /* Allocate memory for the structure that holds the state of the connection. */ hs = mem_malloc(sizeof(struct http_state)); if(hs == NULL) { return ERR_MEM; } /* Initialize the structure. */ hs->file = NULL; hs->left = 0; hs->retries = 0; /* Tell TCP that this is the structure we wish to be passed for our callbacks. */ tcp_arg(pcb, hs); /* Tell TCP that we wish to be informed of incoming data by a call to the http_recv() function. */ tcp_recv(pcb, http_recv2); tcp_err(pcb, conn_err); tcp_poll(pcb, http_poll, 4); return ERR_OK; } void httpdecho_init(void) { struct tcp_pcb *pcb; //by ming 2005.1 OSTimeSet((u32_t) 0x00000000); counter = (u32_t) 0x00000000; pcb = tcp_new(); tcp_bind(pcb, IP_ADDR_ANY, 80); pcb = tcp_listen(pcb); tcp_accept(pcb, http_accept2); }