static void root_service(httpd_conn_t *conn, struct hrequest_t *req) { httpd_send_header(conn, 200, HTTP_STATUS_200_REASON_PHRASE); http_output_stream_write_string(conn->out, "<html>" "<head>" "<title>nanoHTTP server examples</title>" "</head>" "<body>" "<h1>nanoHTTP server examples</h1>" "<ul>" "<li><a href=\"/\">Simple service</a></li>" "<li><a href=\"/secure\">Secure service</a> (try: bob/builder)</li>" "<li><a href=\"/headers\">Request headers</a></li>" "<li><a href=\"/mime\">MIME service</a></li>" "<li>" "<form action=\"/post\" method=\"post\" enctype=\"multipart/form-data\">" "<fieldset>" "<legend>Upload file</legend>" "<input name=\"Text\" type=\"text\" value=\"test-field\"? " "<input name=\"File\" type=\"file\" accept=\"text/*\"> " "<input value=\"Submit\" type=\"submit\">" "</fieldset>" "</form>" "</li>" "<li><a href=\"/not_existent\">The default service</a></li>" "<li><a href=\"/nhttp\">Admin page</a> (try -NHTTPDadmin on the command line)</li>" "</ul>" "</body>" "</html>"); }
static void headers_service(httpd_conn_t *conn, struct hrequest_t *req) { hpair_t *walker; char buf[512]; int len; httpd_send_header(conn, 200, HTTP_STATUS_200_REASON_PHRASE); http_output_stream_write_string(conn->out, "<html>" "<head>" "<title>Request headers</title>" "</head>" "<body>" "<h1>Request headers</h1>" "<ul>"); for (walker=req->header; walker; walker=walker->next) { len = snprintf(buf, 512, "<li>%s: %s</li>", walker->key, walker->value); http_output_stream_write(conn->out, buf, len); } http_output_stream_write_string(conn->out, "</ul>" "</body>" "</html>"); }
static herror_t _httpd_send_html_message(httpd_conn_t *conn, int reason, const char *phrase, const char *msg) { const char const *tmpl = "<html>" "<head>" "<title>%s</title>" "</head>" "<body>" "<h3>%s</h3>" "<hr/>" "<div>Message: '%s'</div>" "</body>" "</html>"; char buf[4096]; char slen[5]; int len; len = snprintf(buf, 4096, tmpl, phrase, phrase, msg); snprintf(slen, 5, "%d", len); httpd_set_header(conn, HEADER_CONTENT_LENGTH, slen); httpd_send_header(conn, reason, phrase); return http_output_stream_write(conn->out, buf, len); }
static void secure_service(httpd_conn_t *conn, struct hrequest_t *req) { httpd_send_header(conn, 200, HTTP_STATUS_200_REASON_PHRASE); http_output_stream_write_string(conn->out, "<html>" "<head>" "<title>Secure ressource!</title>" "</head>" "<body>" "<h1>Authenticated access!!!</h1>" "</body>" "</html>"); return; }
static void post_service(httpd_conn_t *conn, struct hrequest_t *req) { if (req->method == HTTP_REQUEST_POST) { unsigned char buffer[1024]; long len, total; httpd_send_header(conn, 200, HTTP_STATUS_200_REASON_PHRASE); http_output_stream_write_string(conn->out, "<html>" "<head>" "<title>POST service</title>" "</head>" "<body>" "<h1>You posted</h1>" "<pre>"); if (req->content_type && req->content_type->type) { len = sprintf(buffer, "<p>Content-Type: %s</p>", req->content_type->type); http_output_stream_write(conn->out, buffer, len); } while (http_input_stream_is_ready(req->in)) { len = http_input_stream_read(req->in, buffer, 1024); http_output_stream_write(conn->out, buffer, len); total += len; } http_output_stream_write_string(conn->out, "</pre>"); len = sprintf(buffer, "<p>Received %li bytes</p>", total); http_output_stream_write(conn->out, buffer, len); http_output_stream_write_string(conn->out, "</body>" "</html>"); } else { httpd_send_not_implemented(conn, "post_service"); } }
/** Begin MIME multipart/related POST Returns: H_OK or error flag */ herror_t httpd_mime_send_header(httpd_conn_t * conn, const char *related_start, const char *related_start_info, const char *related_type, int code, const char *text) { char buffer[300]; char temp[250]; char boundary[250]; /* Set Content-type Set multipart/related parameter type=..; start=.. ; start-info= ..; boundary=... using sprintf instead of snprintf because visual c does not support snprintf */ sprintf(buffer, "multipart/related;"); if (related_type) { snprintf(temp, 75, " type=\"%s\";", related_type); strcat(buffer, temp); } if (related_start) { snprintf(temp, 250, " start=\"%s\";", related_start); strcat(buffer, temp); } if (related_start_info) { snprintf(temp, 250, " start-info=\"%s\";", related_start_info); strcat(buffer, temp); } _httpd_mime_get_boundary(conn, boundary); snprintf(temp, 250, " boundary=\"%s\"", boundary); strcat(buffer, temp); httpd_set_header(conn, HEADER_CONTENT_TYPE, buffer); return httpd_send_header(conn, code, text); }
int httpd_handle_file(httpd_request_t *req_p, struct fs *fs) { const char *anchor = "/"; char tmp[HTTPD_MAX_URI_LENGTH+1]; const char *encoding = NULL; char *msg_in, *ptr, *type = NULL; int err, msg_in_len = HTTPD_MAX_MESSAGE - 1, conn = req_p->sock; int ret; msg_in = os_mem_alloc(HTTPD_MAX_MESSAGE + 2); if (!msg_in) { httpd_e("Failed to allocate memory for file handling"); /* Check what needs to be returned */ return -WM_FAIL; } memset(msg_in, 0, HTTPD_MAX_MESSAGE + 2); SYS_FILE_DECL; if (!fs) { /* The filesystem wasn't mounted properly */ httpd_send_hdr_from_str(conn, http_header_404, CONTENT_TYPE_PLAIN, encoding, NO_CACHE_HEADERS, UNUSED_PARAM); httpd_send_default_headers(conn, req_p->wsgi->hdr_fields); httpd_send_crlf(conn); httpd_send(conn, FILE_NOT_FOUND, sizeof(FILE_NOT_FOUND)); ret = WM_SUCCESS; goto out; } struct ftfs_super *f_super = fs_to_ftfs_sb(fs); /* Ensure that the anchor is the first part of the filename */ ptr = strstr(req_p->filename, anchor); if (ptr == NULL || ptr != req_p->filename) { httpd_d("No anchor in filename\r\n"); ret = httpd_send_error(conn, HTTP_500); goto out; } /* Zap the anchor from the filename */ ptr = req_p->filename + strlen(anchor); err = 0; /* anchors are only across directory boundaries */ if (*ptr != '/') req_p->filename[err++] = '/'; while (*ptr && (*ptr != '?')) { req_p->filename[err] = *ptr; ptr++; err++; } req_p->filename[err] = '\0'; /* "/" implies a request for index.html */ if (strncmp(req_p->filename, "/", 2) == 0) { strncpy(req_p->filename, http_index_html, sizeof(http_index_html)); } /* Find if .gz version exists for file, if it is then serve that */ type = strrchr(req_p->filename, ISO_period); if (type) { strncpy(tmp, req_p->filename, sizeof(tmp)); strncat(tmp, ".gz", 3); httpd_d("Look for gz file if it exists: %s\r\n", tmp); if (htsys_file_open(fs, tmp, sys_filep) == WM_SUCCESS) { /* Gzipped version exists, serve that */ httpd_d("Serve gzipped file\r\n"); strncpy(req_p->filename, tmp, HTTPD_MAX_URI_LENGTH + 1); encoding = ".gz"; htsys_close(fs, sys_filep); } } ret = httpd_parse_hdr_tags(req_p, conn, msg_in, msg_in_len); if (ret < 0) { httpd_d("Parsing headers failed \r\n"); ret = httpd_send_error(conn, HTTP_500); goto out; } /* It is not a WSGI, check to see if the file exists */ if (htsys_file_open(fs, req_p->filename, sys_filep) == -WM_FAIL) { httpd_w("file not found: %s\r\n", req_p->filename); ret = httpd_send_hdr_from_str(conn, http_header_404, type, encoding, NO_CACHE_HEADERS, UNUSED_PARAM); httpd_send_default_headers(conn, req_p->wsgi->hdr_fields); httpd_send_crlf(conn); if (ret != WM_SUCCESS) goto out; ret = htsys_file_open(fs, http_404_html, sys_filep); if (ret == WM_SUCCESS) { ret = httpd_send_file(fs, conn, sys_filep); goto out; } else httpd_w("No local 404 file. Sending empty 404" " response.\r\n"); } else { /* Ok, the file exists, is it a script html or just html */ g_wm_stats.wm_hd_file++; if (req_p->if_none_match && (f_super->fs_crc32 == req_p->etag_val)) { /* We do not need the file handle now */ htsys_close(fs, sys_filep); /* Send Not Modified header */ /* Send header prologue */ ret = httpd_send(conn, http_header_304_prologue, strlen(http_header_304_prologue)); if (ret != WM_SUCCESS) goto out; httpd_send_header(conn, "Server", "Marvell-WM"); httpd_send_header(conn, "Connection", "Close"); /* Send ETag */ int len; const char *h = httpd_get_etag_hdr(req_p->etag_val, &len); ret = httpd_send(conn, h, len); if (ret != WM_SUCCESS) goto out; /* Close the header */ ret = httpd_send_crlf(conn); goto out; } else { ret = httpd_send_hdr_from_str(conn, http_header_200, type, encoding, SEND_CACHE_HEADERS, f_super->fs_crc32); httpd_send_default_headers(conn, req_p->wsgi->hdr_fields); httpd_send_crlf(conn); if (ret != WM_SUCCESS) goto out; ptr = strchr(req_p->filename, ISO_period); if (ptr != NULL && strncmp(ptr, http_shtml, sizeof(http_shtml) - 1) == 0) { httpd_d("Handling script: %s", req_p->filename); ret = handle_script(fs, req_p, conn, sys_filep, msg_in); htsys_close(fs, sys_filep); if (ret != WM_SUCCESS) { httpd_d("Script failed\r\n"); goto out; } } else { ret = httpd_send_file(fs, conn, sys_filep); if (ret != WM_SUCCESS) goto out; } } } ret = httpd_send_last_chunk(conn); out: os_mem_free(msg_in); return ret; }