static PT_THREAD(handle_output(struct httpd_state *s)) { char *ptr; PT_BEGIN(&s->outputpt); #if DEBUGLOGIC httpd_strcpy(s->filename,httpd_indexfn); #endif if(!httpd_fs_open(s->filename, &s->file)) { httpd_strcpy(s->filename, httpd_404fn); httpd_fs_open(s->filename, &s->file); PT_WAIT_THREAD(&s->outputpt, send_headers(s, httpd_404notf)); PT_WAIT_THREAD(&s->outputpt, send_file(s)); } else { PT_WAIT_THREAD(&s->outputpt, send_headers(s, httpd_200ok)); ptr = strchr(s->filename, ISO_period); if((ptr != NULL && httpd_strncmp(ptr, httpd_shtml, 6) == 0) || httpd_strcmp(s->filename,httpd_indexfn)==0) { PT_INIT(&s->scriptpt); PT_WAIT_THREAD(&s->outputpt, handle_script(s)); } else { PT_WAIT_THREAD(&s->outputpt, send_file(s)); } } PSOCK_CLOSE(&s->sout); PT_END(&s->outputpt); }
/*---------------------------------------------------------------------------*/ static unsigned short make_tcp_stats(void *arg) { static const char httpd_cgi_tcpstat1[] HTTPD_STRING_ATTR = "<tr align=\"center\"><td>%d</td><td>"; static const char httpd_cgi_tcpstat2[] HTTPD_STRING_ATTR = "-%u</td><td>%s</td><td>%u</td><td>%u</td><td>%c %c</td></tr>\r\n"; static const char httpd_cgi_tcpstat3[] HTTPD_STRING_ATTR = "[Room for %d more]"; struct uip_conn *conn; struct httpd_state *s = (struct httpd_state *)arg; char tstate[20]; uint16_t numprinted; if (s->u.count==UIP_CONNS){ for(numprinted = 0; numprinted < UIP_CONNS; numprinted++ ) { if((uip_conns[numprinted].tcpstateflags & UIP_TS_MASK) != UIP_CLOSED) s->u.count--; } return(httpd_snprintf((char *)uip_appdata, uip_mss(), httpd_cgi_tcpstat3, s->u.count)); } conn = &uip_conns[s->u.count]; numprinted = httpd_snprintf((char *)uip_appdata, uip_mss(), httpd_cgi_tcpstat1, uip_htons(conn->lport)); numprinted += httpd_cgi_sprint_ip6(conn->ripaddr, uip_appdata + numprinted); httpd_strcpy(tstate,states[conn->tcpstateflags & UIP_TS_MASK]); numprinted += httpd_snprintf((char *)uip_appdata + numprinted, uip_mss() - numprinted, httpd_cgi_tcpstat2, uip_htons(conn->rport), tstate, conn->nrtx, conn->timer, (uip_outstanding(conn))? '*':' ', (uip_stopped(conn))? '!':' '); return numprinted; }
static PT_THREAD(handle_output(struct httpd_state *s)) { char *ptr; PT_BEGIN(&s->outputpt); #if DEBUGLOGIC httpd_strcpy(s->filename,httpd_indexfn); #endif if(!httpd_fs_open(s->filename, &s->file)) { httpd_strcpy(s->filename, httpd_404fn); httpd_fs_open(s->filename, &s->file); PT_WAIT_THREAD(&s->outputpt, send_headers(s, httpd_404notf)); PT_WAIT_THREAD(&s->outputpt, send_file(s)); } else { PRINTF("s->state: %d\r\n", s->state); if(s->state == STATE_OUTPUT) { PT_WAIT_THREAD(&s->outputpt, send_headers(s, httpd_200ok)); ptr = strchr(s->filename, ISO_period); if((ptr != NULL && httpd_strncmp(ptr, httpd_shtml, 6) == 0) || httpd_strcmp(s->filename,httpd_indexfn)==0) { PT_INIT(&s->scriptpt); PT_WAIT_THREAD(&s->outputpt, handle_script(s)); } else { PT_WAIT_THREAD(&s->outputpt, send_file(s)); } } else { // state == STATE_OUTPUT_ERROR if(s->error_number == 413) { // Send the error message file instead. httpd_strcpy(s->filename, httpd_413fn); httpd_fs_open(s->filename, &s->file); PT_WAIT_THREAD(&s->outputpt, send_headers(s, httpd_413error)); PT_WAIT_THREAD(&s->outputpt, send_file(s)); } // other error messages can be added here. } } PSOCK_CLOSE(&s->sout); PT_END(&s->outputpt); }
static PT_THREAD(handle_input(struct httpd_state *s)) { PSOCK_BEGIN(&s->sin); PSOCK_READTO(&s->sin, ISO_space); if(httpd_strncmp(s->inputbuf, httpd_get, 4) != 0) { PSOCK_CLOSE_EXIT(&s->sin); } PSOCK_READTO(&s->sin, ISO_space); if(s->inputbuf[0] != ISO_slash) { PSOCK_CLOSE_EXIT(&s->sin); } if(s->inputbuf[1] == ISO_space) { httpd_strcpy(s->filename, httpd_indexfn); } else { s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0; strncpy(s->filename, &s->inputbuf[0], sizeof(s->filename)); { /* Look for ?, if found strip file name and send any following text to the LCD */ uint8_t i; for (i=0;i<sizeof(s->inputbuf);i++) { if (s->inputbuf[i]=='?') { raven_lcd_show_text(&s->inputbuf[i]); if (i<sizeof(s->filename)) s->filename[i]=0; // s->inputbuf[i]=0; //allow multiple beeps with multiple ?'s } if (s->inputbuf[i]==0) break; } } } webserver_log_file(&uip_conn->ripaddr, s->filename); s->state = STATE_OUTPUT; while(1) { PSOCK_READTO(&s->sin, ISO_nl); if(httpd_strncmp(s->inputbuf, httpd_ref, 8) == 0) { s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0; petsciiconv_topetscii(s->inputbuf, PSOCK_DATALEN(&s->sin) - 2); webserver_log(s->inputbuf); } } PSOCK_END(&s->sin); }
/*---------------------------------------------------------------------------*/ static unsigned short make_processes(void *p) { static const char httpd_cgi_proc[] HTTPD_STRING_ATTR = "<tr align=\"center\"><td>%p</td><td>%s</td><td>%p</td><td>%s</td></tr>\r\n"; char name[40],tstate[20]; strncpy(name, PROCESS_NAME_STRING((struct process *)p), 40); petsciiconv_toascii(name, 40); httpd_strcpy(tstate,states[9 + ((struct process *)p)->state]); return httpd_snprintf((char *)uip_appdata, uip_mss(), httpd_cgi_proc, p, name, // *((char **) &(((struct process *)p)->thread)), * (char **)(&(((struct process *)p)->thread)), //minimal net tstate); }
static PT_THREAD(handle_input(struct httpd_state *s)) { PSOCK_BEGIN(&s->sin); PSOCK_READTO(&s->sin, ISO_space); if(httpd_strncmp(s->inputbuf, httpd_get, 4) != 0) { PSOCK_CLOSE_EXIT(&s->sin); } PSOCK_READTO(&s->sin, ISO_space); if(s->inputbuf[0] != ISO_slash) { PSOCK_CLOSE_EXIT(&s->sin); } if(s->inputbuf[1] == ISO_space) { httpd_strcpy(s->filename, httpd_indexfn); } else { s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0; strncpy(s->filename, &s->inputbuf[0], sizeof(s->filename)); } webserver_log_file(&uip_conn->ripaddr, s->filename); s->state = STATE_OUTPUT; while(1) { PSOCK_READTO(&s->sin, ISO_nl); if(httpd_strncmp(s->inputbuf, httpd_ref, 8) == 0) { s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0; petsciiconv_topetscii(s->inputbuf, PSOCK_DATALEN(&s->sin) - 2); webserver_log(s->inputbuf); } } PSOCK_END(&s->sin); }
static PT_THREAD(handle_input(struct httpd_state *s)) { int found = 0; PSOCK_BEGIN(&s->sin); PSOCK_READTO(&s->sin, ISO_space); if(httpd_strncmp(s->inputbuf, httpd_get, 4) == 0) { PSOCK_READTO(&s->sin, ISO_space); if(s->inputbuf[0] != ISO_slash) { PSOCK_CLOSE_EXIT(&s->sin); } if(s->inputbuf[1] == ISO_space) { httpd_strcpy(s->filename, httpd_indexfn); } else { s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0; strncpy(s->filename, &s->inputbuf[0], sizeof(s->filename)); /* Look for ?, if found strip file name and send any following text to the LCD */ uint8_t i; for (i=0;i<sizeof(s->inputbuf);i++) { if (s->inputbuf[i]=='?') { if (i<sizeof(s->filename)) s->filename[i]=0; // s->inputbuf[i]=0; //allow multiple beeps with multiple ?'s } if (s->inputbuf[i]==0) break; } } } else if(httpd_strncmp(s->inputbuf, httpd_post, 5) == 0) { PSOCK_READTO(&s->sin, ISO_space); if(s->inputbuf[0] != ISO_slash) { PSOCK_CLOSE_EXIT(&s->sin); } if (httpd_strncmp(&s->inputbuf[1], httpd_config_file, sizeof(httpd_config_file)-1) == 0) { s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0; strncpy(s->filename, &s->inputbuf[0], sizeof(s->filename)); /* Look for ?, if found strip file name*/ uint8_t i; for (i=0;i<sizeof(s->inputbuf);i++) { if (s->inputbuf[i]=='?') { if (i<sizeof(s->filename)) s->filename[i]=0; } if (s->inputbuf[i]==0) break; } //parse config data found = 0; //look for the combination "\r\n\r\n"; the post data follow thereafter while (!found) { PSOCK_READTO(&s->sin, ISO_nl); PSOCK_READTO(&s->sin, ISO_cr); if (PSOCK_DATALEN(&s->sin) == 1) { PSOCK_READTO(&s->sin, ISO_nl); found=1; } } PSOCK_READTO(&s->sin, ISO_equal); //check for domain_name PSOCK_READTO(&s->sin, ISO_amper); if(s->inputbuf[0] != ISO_amper) { char tmp[nvm_size(domain_name)]; memset(tmp, 0, sizeof (tmp)); memcpy(tmp, s->inputbuf, PSOCK_DATALEN(&s->sin) - 1); nvm_write_block(domain_name, tmp, sizeof(tmp)); } PSOCK_READTO(&s->sin, ISO_equal); //check for relay_default_state PSOCK_READTO(&s->sin, ISO_amper); if(s->inputbuf[0] == '1') set_relay_default(0); else if (s->inputbuf[0] == '0') set_relay_default(1); #if S0_ENABLE PSOCK_READTO(&s->sin, ISO_equal); //check for s0 calibration value PSOCK_READTO(&s->sin, ISO_amper); if(s->inputbuf[0] != ISO_amper) { metering_set_s0_calibration((uint16_t)atoi(s->inputbuf)); } #endif } else if (httpd_strncmp(&s->inputbuf[1], httpd_socket_status_file, sizeof(httpd_socket_status_file)-1) == 0) { // toggle button has been pressed s->inputbuf[PSOCK_DATALEN(&s->sin) - 1] = 0; strncpy(s->filename, &s->inputbuf[0], sizeof(s->filename)); /* Look for ?, if found strip file name*/ uint8_t i; for (i=0;i<sizeof(s->inputbuf);i++) { if (s->inputbuf[i]=='?') { if (i<sizeof(s->filename)) s->filename[i]=0; } if (s->inputbuf[i]==0) break; } relay_toggle(); } else { PSOCK_CLOSE_EXIT(&s->sin); } } else { PSOCK_CLOSE_EXIT(&s->sin); } webserver_log_file(&uip_conn->ripaddr, s->filename); s->state = (s->state == STATE_ERROR) ? STATE_OUTPUT_ERROR : STATE_OUTPUT; while(1) { PSOCK_READTO(&s->sin, ISO_nl); if(httpd_strncmp(s->inputbuf, httpd_ref, 8) == 0) { s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0; petsciiconv_topetscii(s->inputbuf, PSOCK_DATALEN(&s->sin) - 2); webserver_log(s->inputbuf); } } PSOCK_END(&s->sin); }
/*---------------------------------------------------------------------------*/ static PT_THREAD(send_headers(struct httpd_state *s, const char *statushdr)) { char *ptr; PSOCK_BEGIN(&s->sout); PSOCK_GENERATOR_SEND(&s->sout, generate_status, (char *) statushdr); ptr = strrchr(s->filename, ISO_period); if (httpd_strncmp("4", statushdr, 1) == 0) { //404 PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_htm); } else if (ptr == NULL) { #if WEBSERVER_CONF_BIN PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_bin); #else PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_htm); #endif } else { ptr++; #if WEBSERVER_CONF_INCLUDE || WEBSERVER_CONF_CGI if (httpd_strncmp(ptr, &httpd_mime_htm[5], 3) == 0 || httpd_strncmp(ptr, &httpd_str_shtml[1], 4) == 0) { #else if (httpd_strncmp(ptr, &httpd_mime_htm[5], 3) == 0) { #endif PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_htm); #if WEBSEVER_CONF_CSS } else if (httpd_strcmp(ptr, &httpd_mime_css[5]) == 0) { PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_css); #endif #if WEBSERVER_CONF_PNG } else if (httpd_strcmp(ptr, &httpd_mime_png[6]) == 0) { PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_png); #endif #if WEBSERVER_CONF_GIF } else if (httpd_strcmp(ptr, &httpd_mime_gif[6]) == 0) { PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_gif); #endif #if WEBSERVER_CONF_JPG } else if (httpd_strcmp(ptr, httpd_mime_jpg) == 0) { PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_jpg); #endif #if WEBSERVER_CONF_TXT } else { PSOCK_GENERATOR_SEND(&s->sout, generate_header, &httpd_mime_txt); #endif } } PSOCK_END(&s->sout); } /*---------------------------------------------------------------------------*/ static PT_THREAD(handle_output(struct httpd_state *s)) { char *ptr; PT_BEGIN(&s->outputpt); #if DEBUGLOGIC httpd_strcpy(s->filename, httpd_str_indexfn); #endif s->fd = httpd_fs_open(s->filename, HTTPD_FS_READ); if (s->fd == -1) { // Opening file failed. /* TODO: try index.htm ? */ #if WEBSERVER_CONF_INCLUDE || WEBSERVER_CONF_CGI /* If index.html not found try index.htm */ if (httpd_strcmp(s->filename, httpd_str_indexfn) == 0) { httpd_strcpy(s->filename, httpd_str_indexfn3); } s->fd = httpd_fs_open(s->filename, HTTPD_FS_READ); if (s->fd != -1) { goto sendfile; } /* If index.html not found try index.shtml */ if (httpd_strcmp(s->filename, httpd_str_indexfn) == 0) { httpd_strcpy(s->filename, httpd_str_indexsfn); } s->fd = httpd_fs_open(s->filename, HTTPD_FS_READ); if (s->fd == -1) { PRINTD("Opening %s failed\n", s->filename); goto psock_close; } else { goto sendfile; } #endif /* If nothing was found, send 404 page */ httpd_strcpy(s->filename, httpd_str_404fn); s->fd = httpd_fs_open(s->filename, HTTPD_FS_READ); PT_WAIT_THREAD(&s->outputpt, send_headers(s, httpd_str_404notf)); PT_WAIT_THREAD(&s->outputpt, send_file(s)); } else { // Opening file succeeded. sendfile: PT_WAIT_THREAD(&s->outputpt, send_headers(s, httpd_str_200ok)); #if WEBSERVER_CONF_INCLUDE || WEBSERVER_CONF_CGI /* If filename ends with .shtml, scan file for script includes or cgi */ ptr = strchr(s->filename, ISO_period); if ((ptr != NULL && httpd_strncmp(ptr, httpd_str_shtml, 6) == 0) || httpd_strcmp(s->filename, httpd_str_indexfn) == 0) { PT_INIT(&s->scriptpt); PT_WAIT_THREAD(&s->outputpt, handle_scripts(s)); } else { #else if (1) { #endif PT_WAIT_THREAD(&s->outputpt, send_file(s)); httpd_fs_close(s->fd); } } psock_close: PSOCK_CLOSE(<y & s->sout); PT_END(&s->outputpt); } /*---------------------------------------------------------------------------*/ #if WEBSERVER_CONF_PASSQUERY char httpd_query[WEBSERVER_CONF_PASSQUERY]; #endif static PT_THREAD(handle_input(struct httpd_state *s)) { PSOCK_BEGIN(&s->sin); PSOCK_READTO(&s->sin, ISO_space); if (httpd_strncmp(s->inputbuf, httpd_str_get, 4) != 0) { PSOCK_CLOSE_EXIT(&s->sin); } PSOCK_READTO(&s->sin, ISO_space); if (s->inputbuf[0] != ISO_slash) { PSOCK_CLOSE_EXIT(&s->sin); } if (s->inputbuf[1] == ISO_space) { httpd_strcpy(s->filename, httpd_str_indexfn); } else { uint8_t i; for (i = 0; i<sizeof (s->filename) + 1; i++) { if (i >= (PSOCK_DATALEN(&s->sin) - 1)) break; if (s->inputbuf[i] == ISO_space) break; #if WEBSERVER_CONF_PASSQUERY /* Query string is left in the httpd_query buffer until zeroed by the application! */ if (s->inputbuf[i] == ISO_qmark) { strncpy(httpd_query, &s->inputbuf[i + 1], sizeof (httpd_query)); break; } #endif s->filename[i] = s->inputbuf[i]; } s->filename[i] = 0; } #if WEBSERVER_CONF_LOG webserver_log_file(&uip_conn->ripaddr, s->filename); // webserver_log(httpd_query); #endif #if WEBSERVER_CONF_LOADTIME s->pagetime = clock_time(); #endif s->state = STATE_OUTPUT; while (1) { PSOCK_READTO(&s->sin, ISO_nl); #if WEBSERVER_CONF_LOG && WEBSERVER_CONF_REFERER if (httpd_strncmp(s->inputbuf, httpd_str_ref, 8) == 0) { s->inputbuf[PSOCK_DATALEN(&s->sin) - 2] = 0; petsciiconv_topetscii(s->inputbuf, PSOCK_DATALEN(&s->sin) - 2); webserver_log(s->inputbuf); } #endif } PSOCK_END(&s->sin); }