diff --git a/CMakeLists.txt b/CMakeLists.txt index 4f8e76c6..aed5a407 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -278,7 +278,7 @@ set(SOURCES lib/context.c lib/sha-1.c lib/alloc.c - ) + lib/header.c) if (NOT LWS_WITHOUT_CLIENT) list(APPEND SOURCES diff --git a/lib/server.c b/lib/server.c index d8f00c2e..0e868670 100644 --- a/lib/server.c +++ b/lib/server.c @@ -838,210 +838,13 @@ try_pollout: goto fail; return 0; - + fail: libwebsocket_close_and_free_session(context, wsi, LWS_CLOSE_STATUS_NOSTATUS); return 1; } -#include "lextable-strings.h" - -const unsigned char *lws_token_to_string(enum lws_token_indexes token) -{ - if ((unsigned int)token >= ARRAY_SIZE(set)) - return NULL; - - return (unsigned char *)set[token]; -} - -int lws_add_http_header_by_name(struct libwebsocket_context *context, - struct libwebsocket *wsi, - const unsigned char *name, - const unsigned char *value, - int length, - unsigned char **p, - unsigned char *end) -{ -#ifdef LWS_USE_HTTP2 - if (wsi->mode == LWS_CONNMODE_HTTP2_SERVING) - return lws_add_http2_header_by_name(context, wsi, name, value, length, p, end); -#endif - if (name) { - while (*p < end && *name) - *((*p)++) = *name++; - - if (*p == end) - return 1; - - *((*p)++) = ' '; - } - if (*p + length + 3 >= end) - return 1; - - memcpy(*p, value, length); - *p += length; - - *((*p)++) = '\x0d'; - *((*p)++) = '\x0a'; - - return 0; -} - -int lws_finalize_http_header(struct libwebsocket_context *context, - struct libwebsocket *wsi, - unsigned char **p, - unsigned char *end) -{ -#ifdef LWS_USE_HTTP2 - if (wsi->mode == LWS_CONNMODE_HTTP2_SERVING) - return 0; -#endif - - if ((long)(end - *p) < 3) - return 1; - - *((*p)++) = '\x0d'; - *((*p)++) = '\x0a'; - - return 0; -} - -int lws_add_http_header_by_token(struct libwebsocket_context *context, - struct libwebsocket *wsi, - enum lws_token_indexes token, - const unsigned char *value, - int length, - unsigned char **p, - unsigned char *end) -{ - const unsigned char *name; -#ifdef LWS_USE_HTTP2 - if (wsi->mode == LWS_CONNMODE_HTTP2_SERVING) - return lws_add_http2_header_by_token(context, wsi, token, value, length, p, end); -#endif - name = lws_token_to_string(token); - if (!name) - return 1; - - return lws_add_http_header_by_name(context, wsi, name, value, length, p, end); -} - -int lws_add_http_header_content_length(struct libwebsocket_context *context, - struct libwebsocket *wsi, - unsigned long content_length, - unsigned char **p, - unsigned char *end) -{ - char b[24]; - int n; - - n = sprintf(b, "%lu", content_length); - if (lws_add_http_header_by_token(context, wsi, WSI_TOKEN_HTTP_CONTENT_LENGTH, (unsigned char *)b, n, p, end)) - return 1; - wsi->u.http.content_length = content_length; - wsi->u.http.content_remain = content_length; - - return 0; -} - -static const char *err400[] = { - "Bad Request", - "Unauthorized", - "Payment Required", - "Forbidden", - "Not Found", - "Method Not Allowed", - "Not Acceptable", - "Proxy Auth Required", - "Request Timeout", - "Conflict", - "Gone", - "Length Required", - "Precondition Failed", - "Request Entity Too Large", - "Request URI too Long", - "Unsupported Media Type", - "Requested Range Not Satisfiable", - "Expectation Failed" -}; - -static const char *err500[] = { - "Internal Server Error", - "Not Implemented", - "Bad Gateway", - "Service Unavailable", - "Gateway Timeout", - "HTTP Version Not Supported" -}; - -int lws_add_http_header_status(struct libwebsocket_context *context, - struct libwebsocket *wsi, - unsigned int code, - unsigned char **p, - unsigned char *end) -{ - unsigned char code_and_desc[60]; - const char *description = ""; - int n; - -#ifdef LWS_USE_HTTP2 - if (wsi->mode == LWS_CONNMODE_HTTP2_SERVING) - return lws_add_http2_header_status(context, wsi, code, p, end); -#endif - if (code >= 400 && code < (400 + ARRAY_SIZE(err400))) - description = err400[code - 400]; - if (code >= 500 && code < (500 + ARRAY_SIZE(err500))) - description = err500[code - 500]; - - n = sprintf((char *)code_and_desc, "HTTP/1.0 %u %s", code, description); - - return lws_add_http_header_by_name(context, wsi, NULL, code_and_desc, n, p, end); -} - -/** - * libwebsockets_return_http_status() - Return simple http status - * @context: libwebsockets context - * @wsi: Websocket instance (available from user callback) - * @code: Status index, eg, 404 - * @html_body: User-readable HTML description < 1KB, or NULL - * - * Helper to report HTTP errors back to the client cleanly and - * consistently - */ -LWS_VISIBLE int libwebsockets_return_http_status( - struct libwebsocket_context *context, struct libwebsocket *wsi, - unsigned int code, const char *html_body) -{ - int n, m; - - unsigned char *p = context->service_buffer + LWS_SEND_BUFFER_PRE_PADDING; - unsigned char *start = p; - unsigned char *end = p + sizeof(context->service_buffer) - - LWS_SEND_BUFFER_PRE_PADDING; - - if (!html_body) - html_body = ""; - - if (lws_add_http_header_status(context, wsi, code, &p, end)) - return 1; - if (lws_add_http_header_by_token(context, wsi, WSI_TOKEN_HTTP_SERVER, (unsigned char *)"libwebsockets", 13, &p, end)) - return 1; - if (lws_add_http_header_by_token(context, wsi, WSI_TOKEN_HTTP_CONTENT_TYPE, (unsigned char *)"text/html", 9, &p, end)) - return 1; - if (lws_finalize_http_header(context, wsi, &p, end)) - return 1; - - m = libwebsocket_write(wsi, start, p - start, LWS_WRITE_HTTP_HEADERS); - if (m != (int)(p - start)) - return 1; - - n = sprintf((char *)start, "