|
|
@@ -161,7 +161,7 @@ mg_static_assert(sizeof(void *) >= sizeof(int), "data type size check");
|
|
|
* file system.
|
|
|
* NO_FILES only disables the automatic mapping between URLs and local
|
|
|
* file names.
|
|
|
- * NO_FILESYSTEM = do not access any file at all. Useful for embedded
|
|
|
+ * NO_FILESYSTEMS = do not access any file at all. Useful for embedded
|
|
|
* devices without file system. Logging to files in not available
|
|
|
* (use callbacks instead) and API functions like mg_send_file are not
|
|
|
* available.
|
|
|
@@ -2253,7 +2253,7 @@ static const struct mg_option config_options[] = {
|
|
|
#if defined(USE_LUA) && defined(USE_WEBSOCKET)
|
|
|
{"lua_websocket_pattern", MG_CONFIG_TYPE_EXT_PATTERN, "**.lua$"},
|
|
|
#endif
|
|
|
- {"replace_asterisk_with_origin", MG_CONFIG_TYPE_BOOLEAN, "no"},
|
|
|
+ {"replace_asterisk_with_origin", MG_CONFIG_TYPE_BOOLEAN, "no"},
|
|
|
{"access_control_allow_origin", MG_CONFIG_TYPE_STRING, "*"},
|
|
|
{"access_control_allow_methods", MG_CONFIG_TYPE_STRING, "*"},
|
|
|
{"access_control_allow_headers", MG_CONFIG_TYPE_STRING, "*"},
|
|
|
@@ -4235,26 +4235,29 @@ send_cors_header(struct mg_connection *conn)
|
|
|
conn->dom_ctx->config[ACCESS_CONTROL_EXPOSE_HEADERS];
|
|
|
const char *cors_meth_cfg =
|
|
|
conn->dom_ctx->config[ACCESS_CONTROL_ALLOW_METHODS];
|
|
|
- const char *cors_repl_asterisk_with_orig_cfg =
|
|
|
- conn->dom_ctx->config[REPLACE_ASTERISK_WITH_ORIGIN];
|
|
|
-
|
|
|
- if (cors_orig_cfg && *cors_orig_cfg && origin_hdr && *origin_hdr && cors_repl_asterisk_with_orig_cfg && *cors_repl_asterisk_with_orig_cfg) {
|
|
|
- int cors_repl_asterisk_with_orig = mg_strcasecmp(cors_repl_asterisk_with_orig_cfg, "yes");
|
|
|
-
|
|
|
+ const char *cors_repl_asterisk_with_orig_cfg =
|
|
|
+ conn->dom_ctx->config[REPLACE_ASTERISK_WITH_ORIGIN];
|
|
|
+
|
|
|
+ if (cors_orig_cfg && *cors_orig_cfg && origin_hdr && *origin_hdr
|
|
|
+ && cors_repl_asterisk_with_orig_cfg
|
|
|
+ && *cors_repl_asterisk_with_orig_cfg) {
|
|
|
+ int cors_repl_asterisk_with_orig =
|
|
|
+ mg_strcasecmp(cors_repl_asterisk_with_orig_cfg, "yes");
|
|
|
+
|
|
|
/* Cross-origin resource sharing (CORS), see
|
|
|
* http://www.html5rocks.com/en/tutorials/cors/,
|
|
|
* http://www.html5rocks.com/static/images/cors_server_flowchart.png
|
|
|
* CORS preflight is not supported for files. */
|
|
|
if (cors_repl_asterisk_with_orig == 0 && cors_orig_cfg[0] == '*') {
|
|
|
mg_response_header_add(conn,
|
|
|
- "Access-Control-Allow-Origin",
|
|
|
- origin_hdr,
|
|
|
- -1);
|
|
|
+ "Access-Control-Allow-Origin",
|
|
|
+ origin_hdr,
|
|
|
+ -1);
|
|
|
} else {
|
|
|
mg_response_header_add(conn,
|
|
|
- "Access-Control-Allow-Origin",
|
|
|
- cors_orig_cfg,
|
|
|
- -1);
|
|
|
+ "Access-Control-Allow-Origin",
|
|
|
+ cors_orig_cfg,
|
|
|
+ -1);
|
|
|
}
|
|
|
}
|
|
|
|
|
|
@@ -15100,7 +15103,7 @@ handle_request(struct mg_connection *conn)
|
|
|
}
|
|
|
return;
|
|
|
}
|
|
|
-
|
|
|
+
|
|
|
|
|
|
/* 1.3. decode url (if config says so) */
|
|
|
if (should_decode_url(conn)) {
|
|
|
@@ -15128,11 +15131,10 @@ handle_request(struct mg_connection *conn)
|
|
|
}
|
|
|
remove_dot_segments(tmp);
|
|
|
ri->local_uri = tmp;
|
|
|
- #if !defined(NO_FILES) /* Only compute if later code can actually use it */
|
|
|
- /* Cache URI length once; recompute only if the buffer changes later. */
|
|
|
- uri_len = (int)strlen(ri->local_uri);
|
|
|
- #endif
|
|
|
-
|
|
|
+#if !defined(NO_FILES) /* Only compute if later code can actually use it */
|
|
|
+ /* Cache URI length once; recompute only if the buffer changes later. */
|
|
|
+ uri_len = (int)strlen(ri->local_uri);
|
|
|
+#endif
|
|
|
|
|
|
|
|
|
/* step 1. completed, the url is known now */
|
|
|
@@ -15186,18 +15188,20 @@ handle_request(struct mg_connection *conn)
|
|
|
const char *cors_acrm = get_header(ri->http_headers,
|
|
|
ri->num_headers,
|
|
|
"Access-Control-Request-Method");
|
|
|
- const char *cors_repl_asterisk_with_orig_cfg =
|
|
|
- conn->dom_ctx->config[REPLACE_ASTERISK_WITH_ORIGIN];
|
|
|
-
|
|
|
+ const char *cors_repl_asterisk_with_orig_cfg =
|
|
|
+ conn->dom_ctx->config[REPLACE_ASTERISK_WITH_ORIGIN];
|
|
|
+
|
|
|
/* Todo: check if cors_origin is in cors_orig_cfg.
|
|
|
* Or, let the client check this. */
|
|
|
|
|
|
if ((cors_meth_cfg != NULL) && (*cors_meth_cfg != 0)
|
|
|
&& (cors_orig_cfg != NULL) && (*cors_orig_cfg != 0)
|
|
|
&& (cors_origin != NULL) && (cors_acrm != NULL)
|
|
|
- && (cors_repl_asterisk_with_orig_cfg != NULL) && (*cors_repl_asterisk_with_orig_cfg != 0)) {
|
|
|
- int cors_repl_asterisk_with_orig = mg_strcasecmp(cors_repl_asterisk_with_orig_cfg, "yes");
|
|
|
-
|
|
|
+ && (cors_repl_asterisk_with_orig_cfg != NULL)
|
|
|
+ && (*cors_repl_asterisk_with_orig_cfg != 0)) {
|
|
|
+ int cors_repl_asterisk_with_orig =
|
|
|
+ mg_strcasecmp(cors_repl_asterisk_with_orig_cfg, "yes");
|
|
|
+
|
|
|
/* This is a valid CORS preflight, and the server is configured
|
|
|
* to handle it automatically. */
|
|
|
const char *cors_acrh =
|
|
|
@@ -15218,7 +15222,10 @@ handle_request(struct mg_connection *conn)
|
|
|
"Content-Length: 0\r\n"
|
|
|
"Connection: %s\r\n",
|
|
|
date,
|
|
|
- (cors_repl_asterisk_with_orig == 0 && cors_orig_cfg[0] == '*') ? cors_origin : cors_orig_cfg,
|
|
|
+ (cors_repl_asterisk_with_orig == 0
|
|
|
+ && cors_orig_cfg[0] == '*')
|
|
|
+ ? cors_origin
|
|
|
+ : cors_orig_cfg,
|
|
|
((cors_meth_cfg[0] == '*') ? cors_acrm : cors_meth_cfg),
|
|
|
suggest_connection_header(conn));
|
|
|
|
|
|
@@ -15610,7 +15617,7 @@ handle_request(struct mg_connection *conn)
|
|
|
|
|
|
/* 12. Directory uris should end with a slash */
|
|
|
if (file.stat.is_directory && (uri_len > 0)
|
|
|
- && (ri->local_uri[uri_len - 1] != '/')) {
|
|
|
+ && (ri->local_uri[uri_len - 1] != '/')) {
|
|
|
|
|
|
|
|
|
/* Path + server root */
|
|
|
@@ -15640,7 +15647,8 @@ handle_request(struct mg_connection *conn)
|
|
|
len++;
|
|
|
}
|
|
|
|
|
|
- /* Append with size of space left for query string + null terminator */
|
|
|
+ /* Append with size of space left for query string + null
|
|
|
+ * terminator */
|
|
|
size_t max_append = buflen - len - 1;
|
|
|
strncat(new_path, ri->query_string, max_append);
|
|
|
}
|
|
|
@@ -18907,12 +18915,12 @@ get_uri_type(const char *uri)
|
|
|
for (i = 0; uri[i] != 0; i++) {
|
|
|
/* Check for CRLF injection attempts */
|
|
|
if (uri[i] == '%') {
|
|
|
- if (uri[i+1] == '0' && (uri[i+2] == 'd' || uri[i+2] == 'D')) {
|
|
|
+ if (uri[i + 1] == '0' && (uri[i + 2] == 'd' || uri[i + 2] == 'D')) {
|
|
|
/* Found %0d (CR) */
|
|
|
DEBUG_TRACE("CRLF injection attempt detected: %s\r\n", uri);
|
|
|
return 0;
|
|
|
}
|
|
|
- if (uri[i+1] == '0' && (uri[i+2] == 'a' || uri[i+2] == 'A')) {
|
|
|
+ if (uri[i + 1] == '0' && (uri[i + 2] == 'a' || uri[i + 2] == 'A')) {
|
|
|
/* Found %0a (LF) */
|
|
|
DEBUG_TRACE("CRLF injection attempt detected: %s\r\n", uri);
|
|
|
return 0;
|