|
|
| version 1.1.1.1, 2013/10/14 10:32:47 | version 1.1.1.3, 2016/11/02 10:35:00 |
|---|---|
| Line 1 | Line 1 |
| #include "first.h" | |
| #include "base.h" | #include "base.h" |
| #include "log.h" | #include "log.h" |
| #include "buffer.h" | #include "buffer.h" |
| #include "response.h" | |
| #include "plugin.h" | #include "plugin.h" |
| Line 28 | Line 31 |
| typedef struct { | typedef struct { |
| unsigned short max_conns; | unsigned short max_conns; |
| unsigned short silent; | unsigned short silent; |
| buffer *location; | |
| } plugin_config; | } plugin_config; |
| typedef struct { | typedef struct { |
| Line 58 FREE_FUNC(mod_evasive_free) { | Line 62 FREE_FUNC(mod_evasive_free) { |
| for (i = 0; i < srv->config_context->used; i++) { | for (i = 0; i < srv->config_context->used; i++) { |
| plugin_config *s = p->config_storage[i]; | plugin_config *s = p->config_storage[i]; |
| if (NULL == s) continue; | |
| buffer_free(s->location); | |
| free(s); | free(s); |
| } | } |
| free(p->config_storage); | free(p->config_storage); |
| Line 75 SETDEFAULTS_FUNC(mod_evasive_set_defaults) { | Line 83 SETDEFAULTS_FUNC(mod_evasive_set_defaults) { |
| config_values_t cv[] = { | config_values_t cv[] = { |
| { "evasive.max-conns-per-ip", NULL, T_CONFIG_SHORT, T_CONFIG_SCOPE_CONNECTION }, /* 0 */ | { "evasive.max-conns-per-ip", NULL, T_CONFIG_SHORT, T_CONFIG_SCOPE_CONNECTION }, /* 0 */ |
| { "evasive.silent", NULL, T_CONFIG_BOOLEAN, T_CONFIG_SCOPE_CONNECTION }, /* 1 */ | { "evasive.silent", NULL, T_CONFIG_BOOLEAN, T_CONFIG_SCOPE_CONNECTION }, /* 1 */ |
| { "evasive.location", NULL, T_CONFIG_STRING, T_CONFIG_SCOPE_CONNECTION }, /* 2 */ | |
| { NULL, NULL, T_CONFIG_UNSET, T_CONFIG_SCOPE_UNSET } | { NULL, NULL, T_CONFIG_UNSET, T_CONFIG_SCOPE_UNSET } |
| }; | }; |
| p->config_storage = calloc(1, srv->config_context->used * sizeof(specific_config *)); | p->config_storage = calloc(1, srv->config_context->used * sizeof(plugin_config *)); |
| for (i = 0; i < srv->config_context->used; i++) { | for (i = 0; i < srv->config_context->used; i++) { |
| data_config const* config = (data_config const*)srv->config_context->data[i]; | |
| plugin_config *s; | plugin_config *s; |
| s = calloc(1, sizeof(plugin_config)); | s = calloc(1, sizeof(plugin_config)); |
| s->max_conns = 0; | s->max_conns = 0; |
| s->silent = 0; | s->silent = 0; |
| s->location = buffer_init(); | |
| cv[0].destination = &(s->max_conns); | cv[0].destination = &(s->max_conns); |
| cv[1].destination = &(s->silent); | cv[1].destination = &(s->silent); |
| cv[2].destination = s->location; | |
| p->config_storage[i] = s; | p->config_storage[i] = s; |
| if (0 != config_insert_values_global(srv, ((data_config *)srv->config_context->data[i])->value, cv)) { | if (0 != config_insert_values_global(srv, config->value, cv, i == 0 ? T_CONFIG_SCOPE_SERVER : T_CONFIG_SCOPE_CONNECTION)) { |
| return HANDLER_ERROR; | return HANDLER_ERROR; |
| } | } |
| } | } |
| Line 108 static int mod_evasive_patch_connection(server *srv, c | Line 120 static int mod_evasive_patch_connection(server *srv, c |
| PATCH(max_conns); | PATCH(max_conns); |
| PATCH(silent); | PATCH(silent); |
| PATCH(location); | |
| /* skip the first, the global context */ | /* skip the first, the global context */ |
| for (i = 1; i < srv->config_context->used; i++) { | for (i = 1; i < srv->config_context->used; i++) { |
| Line 125 static int mod_evasive_patch_connection(server *srv, c | Line 138 static int mod_evasive_patch_connection(server *srv, c |
| PATCH(max_conns); | PATCH(max_conns); |
| } else if (buffer_is_equal_string(du->key, CONST_STR_LEN("evasive.silent"))) { | } else if (buffer_is_equal_string(du->key, CONST_STR_LEN("evasive.silent"))) { |
| PATCH(silent); | PATCH(silent); |
| } else if (buffer_is_equal_string(du->key, CONST_STR_LEN("evasive.location"))) { | |
| PATCH(location); | |
| } | } |
| } | } |
| } | } |
| Line 138 URIHANDLER_FUNC(mod_evasive_uri_handler) { | Line 153 URIHANDLER_FUNC(mod_evasive_uri_handler) { |
| size_t conns_by_ip = 0; | size_t conns_by_ip = 0; |
| size_t j; | size_t j; |
| if (con->uri.path->used == 0) return HANDLER_GO_ON; | if (buffer_is_empty(con->uri.path)) return HANDLER_GO_ON; |
| mod_evasive_patch_connection(srv, con, p); | mod_evasive_patch_connection(srv, con, p); |
| Line 185 URIHANDLER_FUNC(mod_evasive_uri_handler) { | Line 200 URIHANDLER_FUNC(mod_evasive_uri_handler) { |
| "turned away. Too many connections."); | "turned away. Too many connections."); |
| } | } |
| con->http_status = 403; | if (!buffer_is_empty(p->conf.location)) { |
| response_header_overwrite(srv, con, CONST_STR_LEN("Location"), CONST_BUF_LEN(p->conf.location)); | |
| con->http_status = 302; | |
| con->file_finished = 1; | |
| } else { | |
| con->http_status = 403; | |
| } | |
| con->mode = DIRECT; | con->mode = DIRECT; |
| return HANDLER_FINISHED; | return HANDLER_FINISHED; |
| } | } |