Lines 20-25
Link Here
|
20 |
#include "http_config.h" |
20 |
#include "http_config.h" |
21 |
#include "http_connection.h" |
21 |
#include "http_connection.h" |
22 |
#include "http_protocol.h" |
22 |
#include "http_protocol.h" |
|
|
23 |
#include "http_request.h" |
24 |
#include "http_vhost.h" |
23 |
#include "http_log.h" |
25 |
#include "http_log.h" |
24 |
#include "apr_strings.h" |
26 |
#include "apr_strings.h" |
25 |
#include "apr_lib.h" |
27 |
#include "apr_lib.h" |
Lines 44-49
typedef struct {
Link Here
|
44 |
* from the proxy-via IP header value list) |
46 |
* from the proxy-via IP header value list) |
45 |
*/ |
47 |
*/ |
46 |
const char *proxies_header_name; |
48 |
const char *proxies_header_name; |
|
|
49 |
/** A header that may indicate user is using a |
50 |
* HTTPS connection to the reverse-proxy, and |
51 |
* the value that it must match for it to do so. |
52 |
*/ |
53 |
const char *secure_header_name; |
54 |
const char *secure_header_value; |
55 |
unsigned short secure_port; |
47 |
/** A list of trusted proxies, ideally configured |
56 |
/** A list of trusted proxies, ideally configured |
48 |
* with the most commonly encountered listed first |
57 |
* with the most commonly encountered listed first |
49 |
*/ |
58 |
*/ |
Lines 85-90
static void *merge_remoteip_server_config(apr_pool_t *p, void *globalv,
Link Here
|
85 |
config->proxymatch_ip = server->proxymatch_ip |
94 |
config->proxymatch_ip = server->proxymatch_ip |
86 |
? server->proxymatch_ip |
95 |
? server->proxymatch_ip |
87 |
: global->proxymatch_ip; |
96 |
: global->proxymatch_ip; |
|
|
97 |
config->secure_header_name = server->secure_header_name |
98 |
? server->secure_header_name |
99 |
: global->secure_header_name; |
100 |
config->secure_header_value = server->secure_header_value |
101 |
? server->secure_header_value |
102 |
: global->secure_header_value; |
103 |
config->secure_port = server->secure_port |
104 |
? server->secure_port |
105 |
: global->secure_port; |
88 |
return config; |
106 |
return config; |
89 |
} |
107 |
} |
90 |
|
108 |
|
Lines 106-111
static const char *proxies_header_name_set(cmd_parms *cmd, void *dummy,
Link Here
|
106 |
return NULL; |
124 |
return NULL; |
107 |
} |
125 |
} |
108 |
|
126 |
|
|
|
127 |
static const char *secure_header_set(cmd_parms *cmd, void *dummy, |
128 |
const char *name, const char *value) |
129 |
{ |
130 |
remoteip_config_t *config = ap_get_module_config(cmd->server->module_config, |
131 |
&remoteip_module); |
132 |
if (!name || !value) |
133 |
return "SecureIndicatorHeader requires header name and valid value"; |
134 |
|
135 |
config->secure_header_name = name; |
136 |
config->secure_header_value = value; |
137 |
return NULL; |
138 |
} |
139 |
|
140 |
static const char *secure_port_set(cmd_parms *cmd, void *dummy, const char *value) |
141 |
{ |
142 |
remoteip_config_t *config = ap_get_module_config(cmd->server->module_config, |
143 |
&remoteip_module); |
144 |
if (value) { |
145 |
char *tail; |
146 |
int intval; |
147 |
intval = apr_strtoi64(value, &tail, 0); |
148 |
if (errno == 0 && *tail == '\0' && intval > 0 && intval < 65536) { |
149 |
config->secure_port = (unsigned short) intval; |
150 |
return NULL; /* no error */ |
151 |
} |
152 |
} |
153 |
return "SecureIndicatorSSLPort must be an integer between 0 and 65536"; |
154 |
} |
155 |
|
109 |
/* Would be quite nice if APR exported this */ |
156 |
/* Would be quite nice if APR exported this */ |
110 |
/* apr:network_io/unix/sockaddr.c */ |
157 |
/* apr:network_io/unix/sockaddr.c */ |
111 |
static int looks_like_ip(const char *ipstr) |
158 |
static int looks_like_ip(const char *ipstr) |
Lines 229-234
static int remoteip_modify_request(request_rec *r)
Link Here
|
229 |
char *proxy_ips = NULL; |
276 |
char *proxy_ips = NULL; |
230 |
char *parse_remote; |
277 |
char *parse_remote; |
231 |
char *eos; |
278 |
char *eos; |
|
|
279 |
char *secure = NULL; |
232 |
unsigned char *addrbyte; |
280 |
unsigned char *addrbyte; |
233 |
|
281 |
|
234 |
/* If no RemoteIPInternalProxy, RemoteIPInternalProxyList, RemoteIPTrustedProxy |
282 |
/* If no RemoteIPInternalProxy, RemoteIPInternalProxyList, RemoteIPTrustedProxy |
Lines 394-399
static int remoteip_modify_request(request_rec *r)
Link Here
|
394 |
return OK; |
442 |
return OK; |
395 |
} |
443 |
} |
396 |
|
444 |
|
|
|
445 |
if (config->secure_header_name) { |
446 |
secure = (char *) apr_table_get(r->headers_in, config->secure_header_name); |
447 |
} |
448 |
|
449 |
if (secure) { |
450 |
if (!strcmp(secure, config->secure_header_value)) { |
451 |
apr_table_setn(r->subprocess_env, "HTTPS", "on"); |
452 |
} |
453 |
else { |
454 |
secure = NULL; |
455 |
} |
456 |
/* Header is available. Unset even if no match. */ |
457 |
apr_table_unset(r->headers_in, config->secure_header_name); |
458 |
} |
459 |
else { |
460 |
secure = NULL; |
461 |
} |
462 |
apr_table_setn(r->notes, "remoteip-secure", secure ? "1" : "0"); |
463 |
|
397 |
req->proxied_remote = remote; |
464 |
req->proxied_remote = remote; |
398 |
req->proxy_ips = proxy_ips; |
465 |
req->proxy_ips = proxy_ips; |
399 |
|
466 |
|
Lines 417-429
static int remoteip_modify_request(request_rec *r)
Link Here
|
417 |
|
484 |
|
418 |
ap_log_rerror(APLOG_MARK, APLOG_TRACE1, 0, r, |
485 |
ap_log_rerror(APLOG_MARK, APLOG_TRACE1, 0, r, |
419 |
req->proxy_ips |
486 |
req->proxy_ips |
420 |
? "Using %s as client's IP by proxies %s" |
487 |
? "Using %s as client's IP by %s proxies %s" |
421 |
: "Using %s as client's IP by internal proxies%s", |
488 |
: "Using %s as client's IP by %s internal proxies %s", |
422 |
req->useragent_ip, |
489 |
req->useragent_ip, |
|
|
490 |
secure ? "HTTPS" : "HTTP", |
423 |
(req->proxy_ips ? req->proxy_ips : "")); |
491 |
(req->proxy_ips ? req->proxy_ips : "")); |
424 |
return OK; |
492 |
return OK; |
425 |
} |
493 |
} |
426 |
|
494 |
|
|
|
495 |
static int remoteip_ssl_hook_Fixup(request_rec *r) |
496 |
{ |
497 |
request_rec *current_req = r; |
498 |
/* for internal redirect via mod_rewrite and other handlers */ |
499 |
int issecure = 0; |
500 |
while (current_req) { |
501 |
const char* secure = apr_table_get(current_req->notes, "remoteip-secure"); |
502 |
if (secure) { |
503 |
if (secure[0] == '1') |
504 |
issecure = 1; |
505 |
break; |
506 |
} |
507 |
current_req = current_req->prev; |
508 |
} |
509 |
|
510 |
if (issecure) |
511 |
apr_table_setn(r->subprocess_env, "HTTPS", "on"); |
512 |
return OK; |
513 |
} |
514 |
|
515 |
static const char* remoteip_read_scheme(const request_rec *r) |
516 |
{ |
517 |
request_rec *current_req = (request_rec *) r; |
518 |
/* for internal redirect via mod_rewrite and other handlers */ |
519 |
while (current_req) { |
520 |
const char* secure = apr_table_get(current_req->notes, "remoteip-secure"); |
521 |
if (secure) { |
522 |
if (secure[0] == '1') |
523 |
return "https"; |
524 |
return NULL; |
525 |
} |
526 |
current_req = current_req->prev; |
527 |
} |
528 |
// fallback to other handlers |
529 |
return NULL; |
530 |
} |
531 |
|
532 |
static unsigned short remoteip_read_port(const request_rec *r) |
533 |
{ |
534 |
request_rec *current_req = (request_rec *) r; |
535 |
while (current_req) { |
536 |
const char* secure = apr_table_get(r->notes, "remoteip-secure"); |
537 |
if (secure) { |
538 |
if (secure[0] != '1') |
539 |
return 0; |
540 |
|
541 |
remoteip_config_t *config = (remoteip_config_t *) |
542 |
ap_get_module_config(r->server->module_config, &remoteip_module); |
543 |
if (!config) { |
544 |
/* will probably never happen */ |
545 |
ap_log_rerror(APLOG_MARK, APLOG_WARNING, 0, r, |
546 |
"remoteip-secure note is set, but configuration is missing"); |
547 |
return 0; |
548 |
} |
549 |
return config->secure_port; |
550 |
} |
551 |
|
552 |
current_req = current_req->prev; |
553 |
} |
554 |
return 0; |
555 |
} |
556 |
|
427 |
static const command_rec remoteip_cmds[] = |
557 |
static const command_rec remoteip_cmds[] = |
428 |
{ |
558 |
{ |
429 |
AP_INIT_TAKE1("RemoteIPHeader", header_name_set, NULL, RSRC_CONF, |
559 |
AP_INIT_TAKE1("RemoteIPHeader", header_name_set, NULL, RSRC_CONF, |
Lines 447-458
static const command_rec remoteip_cmds[] =
Link Here
|
447 |
RSRC_CONF | EXEC_ON_READ, |
577 |
RSRC_CONF | EXEC_ON_READ, |
448 |
"The filename to read the list of internal proxies, " |
578 |
"The filename to read the list of internal proxies, " |
449 |
"see the RemoteIPInternalProxy directive"), |
579 |
"see the RemoteIPInternalProxy directive"), |
|
|
580 |
AP_INIT_TAKE2("SecureIndicatorHeader", secure_header_set, NULL, RSRC_CONF, |
581 |
"Specifies a request header and value that indicates a secure connection, " |
582 |
"e.g. \"X-Forwarded-Proto https\" or \"X-Secure-Connection on\""), |
583 |
AP_INIT_TAKE1("SecureIndicatorSSLPort", secure_port_set, NULL, RSRC_CONF, |
584 |
"Port to be used for redirections if SecureIndicatorHeader is set, " |
585 |
"Default is \"SecureInidcatorSSLPort 443\" "), |
450 |
{ NULL } |
586 |
{ NULL } |
451 |
}; |
587 |
}; |
452 |
|
588 |
|
453 |
static void register_hooks(apr_pool_t *p) |
589 |
static void register_hooks(apr_pool_t *p) |
454 |
{ |
590 |
{ |
455 |
ap_hook_post_read_request(remoteip_modify_request, NULL, NULL, APR_HOOK_FIRST); |
591 |
ap_hook_post_headers_parsed(remoteip_modify_request, NULL, NULL, APR_HOOK_FIRST); |
|
|
592 |
ap_hook_http_scheme(remoteip_read_scheme, NULL, NULL, APR_HOOK_FIRST); |
593 |
ap_hook_default_port(remoteip_read_port, NULL, NULL, APR_HOOK_FIRST); |
594 |
ap_hook_fixups(remoteip_ssl_hook_Fixup, NULL,NULL, APR_HOOK_MIDDLE); |
456 |
} |
595 |
} |
457 |
|
596 |
|
458 |
AP_DECLARE_MODULE(remoteip) = { |
597 |
AP_DECLARE_MODULE(remoteip) = { |