Apache HTTPD
mod_nw_ssl.c
Go to the documentation of this file.
1/* Licensed to the Apache Software Foundation (ASF) under one or more
2 * contributor license agreements. See the NOTICE file distributed with
3 * this work for additional information regarding copyright ownership.
4 * The ASF licenses this file to You under the Apache License, Version 2.0
5 * (the "License"); you may not use this file except in compliance with
6 * the License. You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17/*
18 * based on mod_tls.c - Apache SSL/TLS module for NetWare by Mike Gardiner.
19 *
20 * This module gives Apache the ability to do SSL/TLS with a minimum amount
21 * of effort. All of the SSL/TLS logic is already on NetWare versions 5 and
22 * above and is interfaced through WinSock on NetWare. As you can see in
23 * the code below SSL/TLS sockets can be created with three WinSock calls.
24 *
25 * To load, simply place the module in the modules directory under the main
26 * apache tree. Then add a "SecureListen" with two arguments. The first
27 * argument is an address and/or port. The second argument is the key pair
28 * name as created in ConsoleOne.
29 *
30 * Examples:
31 *
32 * SecureListen 443 "SSL CertificateIP"
33 * SecureListen 123.45.67.89:443 mycert
34 *
35 * The module also supports RFC 2817 / TLS Upgrade for HTTP 1.1.
36 * For this add a "NWSSLUpgradeable" with two arguments. The first
37 * argument is an address and/or port. The second argument is the key pair
38 * name as created in ConsoleOne.
39 *
40 * Examples:
41 *
42 * NWSSLUpgradeable 8080 "SSL CertificateIP"
43 * NWSSLUpgradeable 123.45.67.89:8080 mycert
44 *
45 */
46
47#define WS_SSL
48
49#define MAX_ADDRESS 512
50#define MAX_KEY 80
51
52
53#include "httpd.h"
54#include "http_config.h"
55#include "http_connection.h"
56#include "http_core.h"
57#include "http_log.h"
58#include "http_protocol.h"
59#include "http_request.h"
60#include "ap_listen.h"
61#include "apr_strings.h"
62#include "apr_portable.h"
63#include "apr_optional.h"
64
65#include <unilib.h>
66
67#ifndef SO_TLS_UNCLEAN_SHUTDOWN
68#define SO_TLS_UNCLEAN_SHUTDOWN 0
69#endif
70
71/* The ssl_var_lookup() optional function retrieves SSL environment
72 * variables. */
76 char *));
77
78/* An optional function which returns non-zero if the given connection
79 * is using SSL/TLS. */
81
82/* The ssl_proxy_enable() and ssl_engine_disable() optional functions
83 * are used by mod_proxy to enable use of SSL for outgoing
84 * connections. */
87
88#define strEQ(s1,s2) (strcmp(s1,s2) == 0)
89#define strNE(s1,s2) (strcmp(s1,s2) != 0)
90#define strEQn(s1,s2,n) (strncmp(s1,s2,n) == 0)
91#define strNEn(s1,s2,n) (strncmp(s1,s2,n) != 0)
92
93#define strcEQ(s1,s2) (strcasecmp(s1,s2) == 0)
94#define strcNE(s1,s2) (strcasecmp(s1,s2) != 0)
95#define strcEQn(s1,s2,n) (strncasecmp(s1,s2,n) == 0)
96#define strcNEn(s1,s2,n) (strncasecmp(s1,s2,n) != 0)
97
98#define strIsEmpty(s) (s == NULL || s[0] == NUL)
99
100
101module AP_MODULE_DECLARE_DATA nwssl_module;
102
107
110 struct sockaddr_in local_addr; /* local IP address and port */
111 int fd;
112 int used; /* Only used during restart */
115 char *addr;
117};
118
125
131
136
139static int numcerts = 0;
142
144
145#define get_nwssl_cfg(srv) (NWSSLSrvConfigRec *) ap_get_module_config(srv->module_config, &nwssl_module)
146
147
149{
150 int i;
151 char **rootcerts = (char **)certlist->elts;
152
155
156 for (i = 0; i < numcerts; ++i) {
158 unistr = (unicode_t*)apr_palloc(p, strlen(rootcerts[i])*4);
160 certarray[i] = unistr;
161 }
162}
163
164/*
165 * Parses a host of the form <address>[:port]
166 * :port is permitted if 'port' is not NULL
167 */
168static unsigned long parse_addr(const char *w, unsigned short *ports)
169{
170 struct hostent *hep;
171 unsigned long my_addr;
172 char *p;
173
174 p = strchr(w, ':');
175 if (ports != NULL) {
176 *ports = 0;
177 if (p != NULL && strcmp(p + 1, "*") != 0)
178 *ports = atoi(p + 1);
179 }
180
181 if (p != NULL)
182 *p = '\0';
183 if (strcmp(w, "*") == 0) {
184 if (p != NULL)
185 *p = ':';
186 return htonl(INADDR_ANY);
187 }
188
189 my_addr = apr_inet_addr((char *)w);
190 if (my_addr != INADDR_NONE) {
191 if (p != NULL)
192 *p = ':';
193 return my_addr;
194 }
195
196 hep = gethostbyname(w);
197
198 if ((!hep) || (hep->h_addrtype != AF_INET || !hep->h_addr_list[0])) {
199 /* XXX Should be echoing by h_errno the actual failure, no?
200 * ap_log_error would be good here. Better yet - APRize.
201 */
202 fprintf(stderr, "Cannot resolve host name %s --- exiting!\n", w);
203 exit(1);
204 }
205
206 if (hep->h_addr_list[1]) {
207 fprintf(stderr, "Host %s has multiple addresses ---\n", w);
208 fprintf(stderr, "you must choose one explicitly for use as\n");
209 fprintf(stderr, "a secure port. Exiting!!!\n");
210 exit(1);
211 }
212
213 if (p != NULL)
214 *p = ':';
215
216 return ((struct in_addr *) (hep->h_addr))->s_addr;
217}
218
220{
221 seclisten_rec *sl;
222
223 for (sl = ap_seclisteners; sl; sl = sl->next) {
224 if (!memcmp(&sl->local_addr, &lr->local_addr, sizeof(sl->local_addr))) {
225 sl->used = 1;
226 return sl->fd;
227 }
228 }
229 return -1;
230}
231
232static char *get_port_key(conn_rec *c)
233{
234 seclistenup_rec *sl;
235
236 for (sl = ap_seclistenersup; sl; sl = sl->next) {
237 if ((sl->port == (c->local_addr)->port) &&
238 ((strcmp(sl->addr, "0.0.0.0") == 0) ||
239 (strcmp(sl->addr, c->local_ip) == 0))) {
240 return sl->key;
241 }
242 }
243 return NULL;
244}
245
247 const struct sockaddr_in *server,
248 char* key, int mutual, server_rec *sconf)
249{
250 int s;
251 char addr[MAX_ADDRESS];
252 struct sslserveropts opts;
253 unsigned int optParam;
255
256 if (server->sin_addr.s_addr != htonl(INADDR_ANY))
257 apr_snprintf(addr, sizeof(addr), "address %s port %d",
258 inet_ntoa(server->sin_addr), ntohs(server->sin_port));
259 else
260 apr_snprintf(addr, sizeof(addr), "port %d", ntohs(server->sin_port));
261
262 /* note that because we're about to slack we don't use psocket */
264
265 SecureProtoInfo.iAddressFamily = AF_INET;
266 SecureProtoInfo.iSocketType = SOCK_STREAM;
267 SecureProtoInfo.iProtocol = IPPROTO_TCP;
268 SecureProtoInfo.iSecurityScheme = SECURITY_PROTOCOL_SSL;
269
272
273 if (s == INVALID_SOCKET) {
275 APLOGNO(02120)
276 "make_secure_socket: failed to get a socket for %s",
277 addr);
278 return -1;
279 }
280
281 if (!mutual) {
283
284 if (WSAIoctl(s, SO_SSL_SET_FLAGS, (char *)&optParam,
285 sizeof(optParam), NULL, 0, NULL, NULL, NULL)) {
287 APLOGNO(02121)
288 "make_secure_socket: for %s, WSAIoctl: "
289 "(SO_SSL_SET_FLAGS)", addr);
290 return -1;
291 }
292 }
293
294 opts.cert = key;
295 opts.certlen = strlen(key);
296 opts.sidtimeout = 0;
297 opts.sidentries = 0;
298 opts.siddir = NULL;
299
300 if (WSAIoctl(s, SO_SSL_SET_SERVER, (char *)&opts, sizeof(opts),
301 NULL, 0, NULL, NULL, NULL) != 0) {
303 APLOGNO(02122)
304 "make_secure_socket: for %s, WSAIoctl: "
305 "(SO_SSL_SET_SERVER)", addr);
306 return -1;
307 }
308
309 if (mutual) {
310 optParam = 0x07; /* SO_SSL_AUTH_CLIENT */
311
312 if (WSAIoctl(s, SO_SSL_SET_FLAGS, (char*)&optParam, sizeof(optParam),
313 NULL, 0, NULL, NULL, NULL)) {
315 APLOGNO(02123)
316 "make_secure_socket: for %s, WSAIoctl: "
317 "(SO_SSL_SET_FLAGS)", addr);
318 return -1;
319 }
320 }
321
323 WSAIoctl(s, SO_SSL_SET_FLAGS, (char *)&optParam, sizeof(optParam),
324 NULL, 0, NULL, NULL, NULL);
325
326 return s;
327}
328
330{
331 int rcode;
332 struct tlsclientopts sWS2Opts;
333 struct nwtlsopts sNWTLSOpts;
334 struct sslserveropts opts;
335 unsigned long ulFlags;
336 SOCKET sock;
338
340
341 /* zero out buffers */
342 memset((char *)&sWS2Opts, 0, sizeof(struct tlsclientopts));
343 memset((char *)&sNWTLSOpts, 0, sizeof(struct nwtlsopts));
344
345 /* turn on ssl for the socket */
347 rcode = WSAIoctl(sock, SO_TLS_SET_FLAGS, &ulFlags, sizeof(unsigned long),
348 NULL, 0, NULL, NULL, NULL);
349 if (SOCKET_ERROR == rcode) {
350 ap_log_error(APLOG_MARK, APLOG_ERR, 0, c->base_server, APLOGNO(02124)
351 "Error: %d with WSAIoctl(flag SO_TLS_ENABLE)",
353 return rcode;
354 }
355
357 WSAIoctl(sock, SO_TLS_SET_FLAGS, &ulFlags, sizeof(unsigned long),
358 NULL, 0, NULL, NULL, NULL);
359
360 /* setup the socket for SSL */
361 memset (&sWS2Opts, 0, sizeof(sWS2Opts));
362 memset (&sNWTLSOpts, 0, sizeof(sNWTLSOpts));
363 sWS2Opts.options = &sNWTLSOpts;
364
365 if (numcerts) {
366 sNWTLSOpts.walletProvider = WAL_PROV_DER; /* the wallet provider defined in wdefs.h */
367 sNWTLSOpts.TrustedRootList = certarray; /* array of certs in UNICODE format */
368 sNWTLSOpts.numElementsInTRList = numcerts; /* number of certs in TRList */
369 }
370 else {
371 /* setup the socket for SSL */
372 unicpy(keyFileName, L"SSL CertificateIP");
373 sWS2Opts.wallet = keyFileName; /* no client certificate */
374 sWS2Opts.walletlen = unilen(keyFileName);
375
376 sNWTLSOpts.walletProvider = WAL_PROV_KMO; /* the wallet provider defined in wdefs.h */
377 }
378
379 /* make the IOCTL call */
381 sizeof(struct tlsclientopts), NULL, 0, NULL,
382 NULL, NULL);
383
384 /* make sure that it was successful */
385 if (SOCKET_ERROR == rcode ) {
386 ap_log_error(APLOG_MARK, APLOG_ERR, 0, c->base_server, APLOGNO(02125)
387 "Error: %d with WSAIoctl(SO_TLS_SET_CLIENT)",
389 }
390 return rcode;
391}
392
394{
395 int rcode;
396 struct tlsserveropts sWS2Opts;
397 struct nwtlsopts sNWTLSOpts;
398 unicode_t SASKey[512];
399 unsigned long ulFlag;
400
401 memset((char *)&sWS2Opts, 0, sizeof(struct tlsserveropts));
402 memset((char *)&sNWTLSOpts, 0, sizeof(struct nwtlsopts));
403
406 sizeof(unsigned long), NULL, 0, NULL, NULL, NULL);
407 if (rcode) {
409 "Error: %d with WSAIoctl(SO_TLS_SET_FLAGS, SO_TLS_ENABLE)",
411 goto ERR;
412 }
413
414
417 sizeof(unsigned long),NULL, 0, NULL, NULL, NULL);
418
419 if (rcode) {
421 "Error: %d with WSAIoctl(SO_TLS_SET_FLAGS, SO_TLS_SERVER)",
423 goto ERR;
424 }
425
427
428 /* setup the tlsserveropts struct */
429 sWS2Opts.wallet = SASKey;
430 sWS2Opts.walletlen = unilen(SASKey);
431 sWS2Opts.sidtimeout = 0;
432 sWS2Opts.sidentries = 0;
433 sWS2Opts.siddir = NULL;
434 sWS2Opts.options = &sNWTLSOpts;
435
436 /* setup the nwtlsopts structure */
437
438 sNWTLSOpts.walletProvider = WAL_PROV_KMO;
439 sNWTLSOpts.keysList = NULL;
440 sNWTLSOpts.numElementsInKeyList = 0;
441 sNWTLSOpts.reservedforfutureuse = NULL;
442 sNWTLSOpts.reservedforfutureCRL = NULL;
443 sNWTLSOpts.reservedforfutureCRLLen = 0;
444 sNWTLSOpts.reserved1 = NULL;
445 sNWTLSOpts.reserved2 = NULL;
446 sNWTLSOpts.reserved3 = NULL;
447
450 &sWS2Opts,
451 sizeof(struct tlsserveropts),
452 NULL,
453 0,
454 NULL,
455 NULL,
456 NULL);
457 if (SOCKET_ERROR == rcode) {
459 "Error: %d with WSAIoctl(SO_TLS_SET_SERVER)", WSAGetLastError());
460 goto ERR;
461 }
462
463ERR:
464 return rcode;
465}
466
467static const char *set_secure_listener(cmd_parms *cmd, void *dummy,
468 const char *ips, const char* key,
469 const char* mutual)
470{
471 NWSSLSrvConfigRec* sc = get_nwssl_cfg(cmd->server);
472 const char *err = ap_check_cmd_context(cmd, GLOBAL_ONLY);
473 char *ports, *addr;
474 unsigned short port;
475 seclisten_rec *new;
476 ap_listen_rec **walk;
478 int found_listener = 0;
479
480
481 if (err != NULL)
482 return err;
483
484 ports = strchr(ips, ':');
485
486 if (ports != NULL) {
487 if (ports == ips)
488 return "Missing IP address";
489 else if (ports[1] == '\0')
490 return "Address must end in :<port-number>";
491
492 *(ports++) = '\0';
493 }
494 else {
495 ports = (char*)ips;
496 }
497
498 new = apr_pcalloc(cmd->server->process->pool, sizeof(seclisten_rec));
499 new->local_addr.sin_family = AF_INET;
500
501 if (ports == ips) {
502 new->local_addr.sin_addr.s_addr = htonl(INADDR_ANY);
503 addr = apr_pstrdup(cmd->server->process->pool, "0.0.0.0");
504 }
505 else {
506 new->local_addr.sin_addr.s_addr = parse_addr(ips, NULL);
507 addr = apr_pstrdup(cmd->server->process->pool, ips);
508 }
509
510 port = atoi(ports);
511
512 if (!port)
513 return "Port must be numeric";
514
515 /* If the specified addr:port was created previously, put the listen
516 socket record back on the ap_listeners list so that the socket
517 will be reused rather than recreated */
518 for (walk = &nw_old_listeners; *walk;) {
519 sa = (*walk)->bind_addr;
520 if (sa) {
521 ap_listen_rec *new;
523
524 oldport = sa->port;
525 /* If both ports are equivalent, then if their names are equivalent,
526 * then we will re-use the existing record.
527 */
528 if (port == oldport &&
529 ((!addr && !sa->hostname) ||
530 ((addr && sa->hostname) && !strcmp(sa->hostname, addr)))) {
531 new = *walk;
532 *walk = new->next;
533 new->next = ap_listeners;
534 ap_listeners = new;
535 found_listener = 1;
536 continue;
537 }
538 }
539
540 walk = &(*walk)->next;
541 }
542
544
545 /* If we found a pre-existing listen socket record, then there
546 is no need to create a new secure listen socket record. */
547 if (found_listener) {
548 return NULL;
549 }
550
551 new->local_addr.sin_port = htons(port);
552 new->fd = -1;
553 new->used = 0;
554 new->next = ap_seclisteners;
555 strcpy(new->key, key);
556 new->mutual = (mutual) ? 1 : 0;
557 new->addr = addr;
558 new->port = port;
559 ap_seclisteners = new;
560 return NULL;
561}
562
564 const char *ips, const char* key)
565{
566 NWSSLSrvConfigRec* sc = get_nwssl_cfg(cmd->server);
567 const char *err = ap_check_cmd_context(cmd, GLOBAL_ONLY);
568 char *ports, *addr;
569 unsigned short port;
570 seclistenup_rec *new;
571
572 if (err != NULL)
573 return err;
574
575 ports = strchr(ips, ':');
576
577 if (ports != NULL) {
578 if (ports == ips)
579 return "Missing IP address";
580 else if (ports[1] == '\0')
581 return "Address must end in :<port-number>";
582
583 *(ports++) = '\0';
584 }
585 else {
586 ports = (char*)ips;
587 }
588
589 if (ports == ips) {
590 addr = apr_pstrdup(cmd->pool, "0.0.0.0");
591 }
592 else {
593 addr = apr_pstrdup(cmd->pool, ips);
594 }
595
596 port = atoi(ports);
597
598 if (!port)
599 return "Port must be numeric";
600
602
603 new = apr_pcalloc(cmd->pool, sizeof(seclistenup_rec));
604 new->next = ap_seclistenersup;
605 strcpy(new->key, key);
606 new->addr = addr;
607 new->port = port;
608 ap_seclistenersup = new;
609
610 return err;
611}
612
614{
617
618 /* Remove our secure listener from the listener list */
619 for (lr = ap_listeners; lr; lr = lr->next) {
620 /* slr is at the head of the list */
621 if (lr == slr) {
623 break;
624 }
625 /* slr is somewhere in between or at the end*/
626 if (lr->next == slr) {
627 lr->next = slr->next;
628 break;
629 }
630 }
631 return APR_SUCCESS;
632}
633
634static const char *set_trusted_certs(cmd_parms *cmd, void *dummy, char *arg)
635{
636 char **ptr = (char **)apr_array_push(certlist);
637
638 *ptr = arg;
639 return NULL;
640}
641
643 apr_pool_t *ptemp)
644{
646 ap_listen_rec **walk;
649 int found;
650
651 /* Pull all of the listeners that were created by mod_nw_ssl out of the
652 ap_listeners list so that the normal listen socket processing does
653 automatically close them */
656
657 for (secwalk = &ap_seclisteners; *secwalk;) {
658 found = 0;
659 for (walk = &ap_listeners; *walk;) {
660 sa = (*walk)->bind_addr;
661 if (sa) {
662 ap_listen_rec *new;
665
666 oldport = sa->port;
667 /* If both ports are equivalent, then if their names are equivalent,
668 * then we will re-use the existing record.
669 */
670 if ((*secwalk)->port == oldport &&
671 ((!(*secwalk)->addr && !sa->hostname) ||
672 (((*secwalk)->addr && sa->hostname) && !strcmp(sa->hostname, (*secwalk)->addr)))) {
673 /* Move the listen socket from ap_listeners to nw_old_listeners */
674 new = *walk;
675 *walk = new->next;
676 new->next = nw_old_listeners;
677 nw_old_listeners = new;
678
679 /* Move the secure socket record to ap_old_seclisterners */
680 secnew = *secwalk;
681 *secwalk = secnew->next;
684 found = 1;
685 break;
686 }
687 }
688
689 walk = &(*walk)->next;
690 }
691 if (!found && &(*secwalk)->next) {
692 secwalk = &(*secwalk)->next;
693 }
694 }
695
696 /* Restore the secure socket records list so that the post config can
697 process all of the sockets normally */
700 certlist = apr_array_make(pconf, 1, sizeof(char *));
701
702 /* Now that we have removed all of the mod_nw_ssl created socket records,
703 allow the normal listen socket handling to occur.
704 NOTE: If for any reason mod_nw_ssl is removed as a built-in module,
705 the following call must be put back into the pre-config handler of the
706 MPM. It is only here to ensure that mod_nw_ssl fixes up the listen
707 socket list before anything else looks at it. */
709
710 return OK;
711}
712
714{
715
716 if (apr_table_get(c->notes, "nwconv-ssl")) {
718 }
719 else {
721
722 csd_data->csd = (apr_socket_t*)csd;
723 csd_data->is_secure = 0;
724 ap_set_module_config(c->conn_config, &nwssl_module, (void*)csd_data);
725 }
726
727 return OK;
728}
729
731 apr_pool_t *ptemp, server_rec *s)
732{
733 seclisten_rec* sl;
735 apr_socket_t* sd;
738 int found;
739 ap_listen_rec *walk;
742
743 /* Walk the old listeners list and compare it to the secure
744 listeners list and remove any secure listener records that
745 are not being reused */
746 for (walk = nw_old_listeners; walk; walk = walk->next) {
747 sa = walk->bind_addr;
748 if (sa) {
749 ap_listen_rec *new;
751
752 oldport = sa->port;
754 unsigned short port = secwalk->port;
755 char *addr = secwalk->addr;
756 /* If both ports are equivalent, then if their names are equivalent,
757 * then we will re-use the existing record.
758 */
759 if (port == oldport &&
760 ((!addr && !sa->hostname) ||
761 ((addr && sa->hostname) && !strcmp(sa->hostname, addr)))) {
762 if (secwalk == ap_seclisteners) {
764 }
765 else {
767 }
768 apr_socket_close(walk->sd);
769 walk->active = 0;
770 break;
771 }
772 else {
774 }
775 }
776 }
777 }
778
779 for (sl = ap_seclisteners; sl != NULL; sl = sl->next) {
780 /* If we find a pre-existing listen socket and it has already been
781 created, then no need to go any further, just reuse it. */
782 if (((sl->fd = find_secure_listener(sl)) >= 0) && (sl->used)) {
783 continue;
784 }
785
786 if (sl->fd < 0)
787 sl->fd = make_secure_socket(s->process->pool, &sl->local_addr, sl->key, sl->mutual, s);
788
789 if (sl->fd >= 0) {
791
792 sock_info.os_sock = &(sl->fd);
793 sock_info.local = (struct sockaddr*)&(sl->local_addr);
794 sock_info.remote = NULL;
795 sock_info.family = APR_INET;
796 sock_info.type = SOCK_STREAM;
797
798 apr_os_sock_make(&sd, &sock_info, s->process->pool);
799
800 lr = apr_pcalloc(s->process->pool, sizeof(ap_listen_rec));
801
802 if (lr) {
803 lr->sd = sd;
804 if ((status = apr_sockaddr_info_get(&lr->bind_addr, sl->addr, APR_UNSPEC, sl->port, 0,
805 s->process->pool)) != APR_SUCCESS) {
807 "alloc_listener: failed to set up sockaddr for %s:%d", sl->addr, sl->port);
809 }
810 lr->next = ap_listeners;
813 }
814 } else {
816 }
817 }
818
819 for (slu = ap_seclistenersup; slu; slu = slu->next) {
820 /* Check the listener list for a matching upgradeable listener */
821 found = 0;
822 for (lr = ap_listeners; lr; lr = lr->next) {
823 if (slu->port == lr->bind_addr->port) {
824 found = 1;
825 break;
826 }
827 }
828 if (!found) {
830 "No Listen directive found for upgradeable listener %s:%d", slu->addr, slu->port);
831 }
832 }
833
834 build_cert_list(s->process->pool);
835
836 return OK;
837}
838
840{
842 new->sltable = apr_table_make(p, 5);
843 new->slutable = apr_table_make(p, 5);
844 return new;
845}
846
847static void *nwssl_config_server_merge(apr_pool_t *p, void *basev, void *addv)
848{
852 return merged;
853}
854
855static int compare_ipports(void *rec, const char *key, const char *value)
856{
857 conn_rec *c = (conn_rec*)rec;
858
859 if (value &&
860 ((strcmp(value, "0.0.0.0") == 0) || (strcmp(value, c->local_ip) == 0)))
861 {
862 return 0;
863 }
864 return 1;
865}
866
867static int isSecureConnEx (const server_rec *s, const conn_rec *c, const apr_table_t *t)
868{
869 char port[8];
870
871 itoa((c->local_addr)->port, port, 10);
872 if (!apr_table_do(compare_ipports, (void*)c, t, port, NULL)) {
873 return 1;
874 }
875
876 return 0;
877}
878
879static int isSecureConn (const server_rec *s, const conn_rec *c)
880{
882
883 return isSecureConnEx (s, c, sc->sltable);
884}
885
886static int isSecureConnUpgradeable (const server_rec *s, const conn_rec *c)
887{
889
890 return isSecureConnEx (s, c, sc->slutable);
891}
892
893static int isSecure (const request_rec *r)
894{
895 return isSecureConn (r->server, r->connection);
896}
897
899{
901}
902
903static int isSecureUpgraded (const request_rec *r)
904{
906
907 return csd_data->is_secure;
908}
909
911{
912 if (!isSecure(r) && !isSecureUpgraded(r))
913 return DECLINED;
914
915 apr_table_setn(r->subprocess_env, "HTTPS", "on");
916
917 return DECLINED;
918}
919
920static const char *nwssl_hook_http_scheme(const request_rec *r)
921{
922 if (isSecure(r) && !isSecureUpgraded(r))
923 return "https";
924
925 return NULL;
926}
927
929{
930 if (isSecure(r))
931 return DEFAULT_HTTPS_PORT;
932
933 return 0;
934}
935
937{
938 apr_table_setn(c->notes, "nwconv-ssl", "Y");
939
940 return 1;
941}
942
944{
945 return 1;
946}
947
949{
950 secsocket_data *csd_data = (secsocket_data*)ap_get_module_config(c->conn_config, &nwssl_module);
951
952 return isSecureConn (c->base_server, c) || (csd_data && csd_data->is_secure);
953}
954
955/* This function must remain safe to use for a non-SSL connection. */
957{
959 const char *result;
960 BOOL resdup;
962
963 result = NULL;
964 resdup = TRUE;
965
966 /*
967 * When no pool is given try to find one
968 */
969 if (p == NULL) {
970 if (r != NULL)
971 p = r->pool;
972 else if (c != NULL)
973 p = c->pool;
974 else
975 p = mc->pPool;
976 }
977
978 /*
979 * Request dependent stuff
980 */
981 if (r != NULL) {
982 switch (var[0]) {
983 case 'H':
984 case 'h':
985 if (strcEQ(var, "HTTP_USER_AGENT"))
986 result = apr_table_get(r->headers_in, "User-Agent");
987 else if (strcEQ(var, "HTTP_REFERER"))
988 result = apr_table_get(r->headers_in, "Referer");
989 else if (strcEQ(var, "HTTP_COOKIE"))
990 result = apr_table_get(r->headers_in, "Cookie");
991 else if (strcEQ(var, "HTTP_FORWARDED"))
992 result = apr_table_get(r->headers_in, "Forwarded");
993 else if (strcEQ(var, "HTTP_HOST"))
994 result = apr_table_get(r->headers_in, "Host");
995 else if (strcEQ(var, "HTTP_PROXY_CONNECTION"))
996 result = apr_table_get(r->headers_in, "Proxy-Connection");
997 else if (strcEQ(var, "HTTP_ACCEPT"))
998 result = apr_table_get(r->headers_in, "Accept");
999 else if (strcEQ(var, "HTTPS")) {
1000 if (isSecure(r) || isSecureUpgraded(r))
1001 result = "on";
1002 else
1003 result = "off";
1004 }
1005 else if (strlen(var) > 5 && strcEQn(var, "HTTP:", 5))
1006 /* all other headers from which we are still not know about */
1008 break;
1009
1010 case 'R':
1011 case 'r':
1012 if (strcEQ(var, "REQUEST_METHOD"))
1013 result = r->method;
1014 else if (strcEQ(var, "REQUEST_SCHEME"))
1016 else if (strcEQ(var, "REQUEST_URI"))
1017 result = r->uri;
1018 else if (strcEQ(var, "REQUEST_FILENAME"))
1019 result = r->filename;
1020 else if (strcEQ(var, "REMOTE_ADDR"))
1022 else if (strcEQ(var, "REMOTE_HOST"))
1024 else if (strcEQ(var, "REMOTE_IDENT"))
1026 else if (strcEQ(var, "REMOTE_USER"))
1027 result = r->user;
1028 break;
1029
1030 case 'S':
1031 case 's':
1032 if (strcEQn(var, "SSL", 3)) break; /* shortcut common case */
1033
1034 if (strcEQ(var, "SERVER_ADMIN"))
1036 else if (strcEQ(var, "SERVER_NAME"))
1038 else if (strcEQ(var, "SERVER_PORT"))
1040 else if (strcEQ(var, "SERVER_PROTOCOL"))
1041 result = r->protocol;
1042 else if (strcEQ(var, "SCRIPT_FILENAME"))
1043 result = r->filename;
1044 break;
1045
1046 default:
1047 if (strcEQ(var, "PATH_INFO"))
1048 result = r->path_info;
1049 else if (strcEQ(var, "QUERY_STRING"))
1050 result = r->args;
1051 else if (strcEQ(var, "IS_SUBREQ"))
1052 result = (r->main != NULL ? "true" : "false");
1053 else if (strcEQ(var, "DOCUMENT_ROOT"))
1055 else if (strcEQ(var, "AUTH_TYPE"))
1057 else if (strcEQ(var, "THE_REQUEST"))
1058 result = r->the_request;
1059 break;
1060 }
1061 }
1062
1063 /*
1064 * Connection stuff
1065 */
1066 if (result == NULL && c != NULL) {
1067 /* XXX-Can't get specific SSL info from NetWare */
1068 /* SSLConnRec *sslconn = myConnConfig(c);
1069 if (strlen(var) > 4 && strcEQn(var, "SSL_", 4)
1070 && sslconn && sslconn->ssl)
1071 result = ssl_var_lookup_ssl(p, c, var+4);*/
1072
1073 if (strlen(var) > 4 && strcEQn(var, "SSL_", 4))
1074 result = NULL;
1075 }
1076
1077 /*
1078 * Totally independent stuff
1079 */
1080 if (result == NULL) {
1081 if (strlen(var) > 12 && strcEQn(var, "SSL_VERSION_", 12))
1082 result = NULL;
1083 /* XXX-Can't get specific SSL info from NetWare */
1084 /*result = ssl_var_lookup_ssl_version(p, var+12);*/
1085 else if (strcEQ(var, "SERVER_SOFTWARE"))
1087 else if (strcEQ(var, "API_VERSION")) {
1089 resdup = FALSE;
1090 }
1091 else if (strcEQ(var, "TIME_YEAR")) {
1093 result = apr_psprintf(p, "%02d%02d",
1094 (tm.tm_year / 100) + 19, tm.tm_year % 100);
1095 resdup = FALSE;
1096 }
1097#define MKTIMESTR(format, tmfield) \
1098 apr_time_exp_lt(&tm, apr_time_now()); \
1099 result = apr_psprintf(p, format, tm.tmfield); \
1100 resdup = FALSE;
1101 else if (strcEQ(var, "TIME_MON")) {
1102 MKTIMESTR("%02d", tm_mon+1)
1103 }
1104 else if (strcEQ(var, "TIME_DAY")) {
1105 MKTIMESTR("%02d", tm_mday)
1106 }
1107 else if (strcEQ(var, "TIME_HOUR")) {
1108 MKTIMESTR("%02d", tm_hour)
1109 }
1110 else if (strcEQ(var, "TIME_MIN")) {
1111 MKTIMESTR("%02d", tm_min)
1112 }
1113 else if (strcEQ(var, "TIME_SEC")) {
1114 MKTIMESTR("%02d", tm_sec)
1115 }
1116 else if (strcEQ(var, "TIME_WDAY")) {
1117 MKTIMESTR("%d", tm_wday)
1118 }
1119 else if (strcEQ(var, "TIME")) {
1122 "%02d%02d%02d%02d%02d%02d%02d", (tm.tm_year / 100) + 19,
1123 (tm.tm_year % 100), tm.tm_mon+1, tm.tm_mday,
1125 resdup = FALSE;
1126 }
1127 /* all other env-variables from the parent Apache process */
1128 else if (strlen(var) > 4 && strcEQn(var, "ENV:", 4)) {
1130 if (result == NULL)
1132 if (result == NULL)
1133 result = getenv(var+4);
1134 }
1135 }
1136
1137 if (result != NULL && resdup)
1139 if (result == NULL)
1140 result = "";
1141 return (char *)result;
1142}
1143
1144#define SWITCH_STATUS_LINE "HTTP/1.1 101 Switching Protocols"
1145#define UPGRADE_HEADER "Upgrade: TLS/1.0, HTTP/1.1"
1146#define CONNECTION_HEADER "Connection: Upgrade"
1147
1150
1151{
1152 const char *upgrade;
1154 request_rec *r = f->r;
1156 char *key;
1157 int ret;
1159 apr_bucket *b;
1160 apr_status_t rv;
1161
1162 /* Just remove the filter, if it doesn't work the first time, it won't
1163 * work at all for this request.
1164 */
1166
1167 if (!r) {
1168 /*
1169 ap_log_error(APLOG_MARK, APLOG_ERR, 0, r->server, APLOGNO(02131)
1170 "Unable to get upgradeable socket handle");
1171 */
1172 return ap_pass_brigade(f->next, bb);
1173 }
1174
1175 /* No need to ensure that this is a server with optional SSL, the filter
1176 * is only inserted if that is true.
1177 */
1178
1179 upgrade = apr_table_get(r->headers_in, "Upgrade");
1180 if (upgrade == NULL
1181 || strcmp(ap_getword(r->pool, &upgrade, ','), "TLS/1.0")) {
1182 /* "Upgrade: TLS/1.0, ..." header not found, don't do Upgrade */
1183 return ap_pass_brigade(f->next, bb);
1184 }
1185
1186 apr_table_unset(r->headers_out, "Upgrade");
1187
1189 csd = csd_data->csd;
1190
1191 /* Send the interim 101 response. */
1192 upgradebb = apr_brigade_create(r->pool, f->c->bucket_alloc);
1193
1196
1197 b = apr_bucket_flush_create(f->c->bucket_alloc);
1199
1200 rv = ap_pass_brigade(f->next, upgradebb);
1201 if (rv) {
1203 "could not send interim 101 Upgrade response");
1204 return AP_FILTER_ERROR;
1205 }
1206
1208
1209 if (csd && key) {
1210 int sockdes;
1212
1213
1215 if (!ret) {
1216 csd_data->is_secure = 1;
1217 }
1218 }
1219 else {
1221 "Upgradeable socket handle not found");
1222 return AP_FILTER_ERROR;
1223 }
1224
1226 "Awaiting re-negotiation handshake");
1227
1228 /* Now that we have initialized the ssl connection which added the ssl_io_filter,
1229 pass the brigade off to the connection based output filters so that the
1230 request can complete encrypted */
1231 return ap_pass_brigade(f->c->output_filters, bb);
1232}
1233
1235{
1237
1238 if (isSecureUpgradeable (r)) {
1239 ap_add_output_filter("UPGRADE_FILTER", NULL, r, r->connection);
1240 }
1241}
1242
1244{
1246 "specify an address and/or port with a key pair name.\n"
1247 "Optional third parameter of MUTUAL configures the port for mutual authentication."),
1249 "specify an address and/or port with a key pair name, that can be upgraded to an SSL connection.\n"
1250 "The address and/or port must have already be defined using a Listen directive."),
1251 AP_INIT_ITERATE("NWSSLTrustedCerts", set_trusted_certs, NULL, RSRC_CONF,
1252 "Adds trusted certificates that are used to create secure connections to proxied servers"),
1253 {NULL}
1254};
1255
1274
1276{
1278 NULL, /* dir config creater */
1279 NULL, /* dir merger --- default is to override */
1280 nwssl_config_server_create, /* server config */
1281 nwssl_config_server_merge, /* merge server config */
1282 nwssl_module_cmds, /* command apr_table_t */
1284};
1285
Apache Listeners Library.
#define TRUE
Definition abts.h:38
#define FALSE
Definition abts.h:35
APR-UTIL registration of functions exported by modules.
APR Portability Routines.
APR Strings library.
void ap_hook_pre_connection(ap_HOOK_pre_connection_t *pf, const char *const *aszPre, const char *const *aszSucc, int nOrder)
Definition connection.c:43
return found
Definition core.c:2840
static apr_pool_t * pconf
Definition event.c:441
#define ap_get_module_config(v, m)
void ap_hook_post_config(ap_HOOK_post_config_t *pf, const char *const *aszPre, const char *const *aszSucc, int nOrder)
Definition config.c:105
#define AP_DECLARE_MODULE(foo)
ap_conf_vector_t * base
#define AP_INIT_ITERATE(directive, func, mconfig, where, help)
#define ap_set_module_config(v, m, val)
void ap_hook_pre_config(ap_HOOK_pre_config_t *pf, const char *const *aszPre, const char *const *aszSucc, int nOrder)
Definition config.c:91
request_rec * r
#define AP_INIT_TAKE23(directive, func, mconfig, where, help)
#define AP_INIT_TAKE2(directive, func, mconfig, where, help)
void * csd
#define ap_http_scheme(r)
Definition httpd.h:297
#define AP_FILTER_ERROR
Definition httpd.h:473
#define DEFAULT_HTTPS_PORT
Definition httpd.h:280
#define DECLINED
Definition httpd.h:457
#define OK
Definition httpd.h:456
const char * ap_get_server_banner(void)
Definition core.c:3593
#define ap_fputs(f, bb, str)
apr_status_t ap_pass_brigade(ap_filter_t *filter, apr_bucket_brigade *bucket)
ap_filter_rec_t * ap_register_output_filter(const char *name, ap_out_filter_func filter_func, ap_init_filter_func filter_init, ap_filter_type ftype)
ap_filter_t * ap_add_output_filter(const char *name, void *ctx, request_rec *r, conn_rec *c)
void ap_remove_output_filter(ap_filter_t *f)
@ AP_FTYPE_PROTOCOL
apr_port_t ap_get_server_port(const request_rec *r)
Definition core.c:1199
const char * ap_document_root(request_rec *r)
Definition core.c:829
const char * ap_get_remote_logname(request_rec *r)
Definition core.c:1121
const char * ap_get_server_name_for_url(request_rec *r)
Definition core.c:1187
void ap_listen_pre_config(void)
Definition listen.c:804
ap_listen_rec * ap_listeners
Definition listen.c:42
#define APLOGNO(n)
Definition http_log.h:117
#define APLOG_INFO
Definition http_log.h:70
#define ap_log_rerror
Definition http_log.h:454
#define APLOG_ERR
Definition http_log.h:67
#define ap_log_error
Definition http_log.h:370
#define APLOG_MARK
Definition http_log.h:283
#define ap_log_perror
Definition http_log.h:412
#define APLOG_WARNING
Definition http_log.h:68
#define APLOG_CRIT
Definition http_log.h:66
#define MODULE_MAGIC_NUMBER_MAJOR
Definition ap_mmn.h:611
void ap_hook_http_scheme(ap_HOOK_http_scheme_t *pf, const char *const *aszPre, const char *const *aszSucc, int nOrder)
Definition protocol.c:2589
void ap_hook_default_port(ap_HOOK_default_port_t *pf, const char *const *aszPre, const char *const *aszSucc, int nOrder)
Definition protocol.c:2591
void ap_hook_fixups(ap_HOOK_fixups_t *pf, const char *const *aszPre, const char *const *aszSucc, int nOrder)
Definition request.c:87
void ap_hook_insert_filter(ap_HOOK_insert_filter_t *pf, const char *const *aszPre, const char *const *aszSucc, int nOrder)
Definition request.c:96
const char apr_port_t port
Definition http_vhost.h:125
void * dummy
Definition http_vhost.h:62
void const char * arg
Definition http_vhost.h:63
#define CRLF
Definition httpd.h:724
apr_file_t * f
#define APR_BRIGADE_INSERT_TAIL(b, e)
#define APR_HOOK_MIDDLE
Definition apr_hooks.h:303
apr_memcache_t * mc
apr_memcache_server_t * server
#define APR_REGISTER_OPTIONAL_FN(name)
#define APR_DECLARE_OPTIONAL_FN(ret, name, args)
#define RSRC_CONF
#define HTTP_INTERNAL_SERVER_ERROR
Definition httpd.h:535
char * ssl_var_lookup(apr_pool_t *p, server_rec *s, conn_rec *c, request_rec *r, char *var)
Definition mod_nw_ssl.c:956
#define BOOL
Definition ssl_private.h:81
#define STANDARD20_MODULE_STUFF
char * ap_getword(apr_pool_t *p, const char **line, char stop)
Definition util.c:723
#define GLOBAL_ONLY
const char * ap_check_cmd_context(cmd_parms *cmd, unsigned forbidden)
Definition core.c:1301
apr_size_t size
const char * value
Definition apr_env.h:51
#define APR_SUCCESS
Definition apr_errno.h:225
int apr_status_t
Definition apr_errno.h:44
const char * key
void * data
apr_array_header_t ** result
const char * opts
Definition apr_getopt.h:122
void * rec
Definition apr_hash.h:270
apr_vformatter_buff_t * c
Definition apr_lib.h:175
apr_sockaddr_t * addr
apr_sockaddr_t * sockaddr
apr_socket_t * sock
apr_sockaddr_t * sa
apr_interval_time_t t
apr_uint16_t apr_port_t
#define APR_UNSPEC
#define APR_INET
apr_pool_t * b
Definition apr_pools.h:529
#define apr_pcalloc(p, size)
Definition apr_pools.h:465
const char * s
Definition apr_strings.h:95
apr_int32_t apr_int32_t apr_int32_t err
apr_cmdtype_e cmd
int int status
apr_size_t apr_size_t const char apr_time_exp_t * tm
Definition apr_time.h:221
const char * ap_get_useragent_host(request_rec *req, int type, int *str_is_ip)
Definition core.c:1036
#define REMOTE_NAME
Definition http_core.h:106
Apache Configuration.
Apache connection library.
CORE HTTP Daemon.
Apache Logging library.
HTTP protocol handling.
Apache Request library.
HTTP Daemon routines.
apr_pool_t * p
Definition md_event.c:32
#define SO_TLS_UNCLEAN_SHUTDOWN
Definition mod_nw_ssl.c:68
static seclisten_rec * ap_seclisteners
Definition mod_nw_ssl.c:140
static unsigned long parse_addr(const char *w, unsigned short *ports)
Definition mod_nw_ssl.c:168
#define get_nwssl_cfg(srv)
Definition mod_nw_ssl.c:145
static int isSecureUpgraded(const request_rec *r)
Definition mod_nw_ssl.c:903
static seclistenup_rec * ap_seclistenersup
Definition mod_nw_ssl.c:141
static int compare_ipports(void *rec, const char *key, const char *value)
Definition mod_nw_ssl.c:855
static int isSecureConnEx(const server_rec *s, const conn_rec *c, const apr_table_t *t)
Definition mod_nw_ssl.c:867
static int ssl_is_https(conn_rec *c)
Definition mod_nw_ssl.c:948
static ap_listen_rec * nw_old_listeners
Definition mod_nw_ssl.c:143
static apr_array_header_t * certlist
Definition mod_nw_ssl.c:137
static int isSecureConn(const server_rec *s, const conn_rec *c)
Definition mod_nw_ssl.c:879
#define MAX_KEY
Definition mod_nw_ssl.c:50
static int isSecureUpgradeable(const request_rec *r)
Definition mod_nw_ssl.c:898
static int SSLize_Socket(SOCKET socketHnd, char *key, request_rec *r)
Definition mod_nw_ssl.c:393
static int nwssl_pre_config(apr_pool_t *pconf, apr_pool_t *plog, apr_pool_t *ptemp)
Definition mod_nw_ssl.c:642
static const char * set_secure_listener(cmd_parms *cmd, void *dummy, const char *ips, const char *key, const char *mutual)
Definition mod_nw_ssl.c:467
static const char * set_secure_upgradeable_listener(cmd_parms *cmd, void *dummy, const char *ips, const char *key)
Definition mod_nw_ssl.c:563
static unicode_t ** certarray
Definition mod_nw_ssl.c:138
#define MKTIMESTR(format, tmfield)
static char * get_port_key(conn_rec *c)
Definition mod_nw_ssl.c:232
static int numcerts
Definition mod_nw_ssl.c:139
static apr_status_t nwssl_socket_cleanup(void *data)
Definition mod_nw_ssl.c:613
#define SWITCH_STATUS_LINE
static void * nwssl_config_server_merge(apr_pool_t *p, void *basev, void *addv)
Definition mod_nw_ssl.c:847
static const char * set_trusted_certs(cmd_parms *cmd, void *dummy, char *arg)
Definition mod_nw_ssl.c:634
#define UPGRADE_HEADER
static apr_port_t nwssl_hook_default_port(const request_rec *r)
Definition mod_nw_ssl.c:928
static int nwssl_post_config(apr_pool_t *pconf, apr_pool_t *plog, apr_pool_t *ptemp, server_rec *s)
Definition mod_nw_ssl.c:730
static int find_secure_listener(seclisten_rec *lr)
Definition mod_nw_ssl.c:219
static int make_secure_socket(apr_pool_t *pconf, const struct sockaddr_in *server, char *key, int mutual, server_rec *sconf)
Definition mod_nw_ssl.c:246
#define strcEQ(s1, s2)
Definition mod_nw_ssl.c:93
static void register_hooks(apr_pool_t *p)
#define strcEQn(s1, s2, n)
Definition mod_nw_ssl.c:95
static int isSecure(const request_rec *r)
Definition mod_nw_ssl.c:893
int ssl_proxy_enable(conn_rec *c)
Definition mod_nw_ssl.c:936
static apr_status_t ssl_io_filter_Upgrade(ap_filter_t *f, apr_bucket_brigade *bb)
static int nwssl_pre_connection(conn_rec *c, void *csd)
Definition mod_nw_ssl.c:713
#define CONNECTION_HEADER
int ssl_engine_disable(conn_rec *c)
Definition mod_nw_ssl.c:943
static const command_rec nwssl_module_cmds[]
static const char * nwssl_hook_http_scheme(const request_rec *r)
Definition mod_nw_ssl.c:920
#define MAX_ADDRESS
Definition mod_nw_ssl.c:49
static void * nwssl_config_server_create(apr_pool_t *p, server_rec *s)
Definition mod_nw_ssl.c:839
static int convert_secure_socket(conn_rec *c, apr_socket_t *csd)
Definition mod_nw_ssl.c:329
static void ssl_hook_Insert_Filter(request_rec *r)
static void build_cert_list(apr_pool_t *p)
Definition mod_nw_ssl.c:148
static int isSecureConnUpgradeable(const server_rec *s, const conn_rec *c)
Definition mod_nw_ssl.c:886
static int nwssl_hook_Fixup(request_rec *r)
Definition mod_nw_ssl.c:910
return NULL
Definition mod_so.c:359
int i
Definition mod_so.c:347
sconf
Definition mod_so.c:349
apr_table_t * slutable
Definition mod_nw_ssl.c:128
apr_table_t * sltable
Definition mod_nw_ssl.c:127
apr_pool_t * pPool
Definition mod_nw_ssl.c:129
The representation of a filter chain.
Apache's listeners record.
Definition ap_listen.h:47
ap_listen_rec * next
Definition ap_listen.h:51
apr_sockaddr_t * bind_addr
Definition ap_listen.h:59
apr_socket_t * sd
Definition ap_listen.h:55
apr_os_sock_t * os_sock
apr_pool_t * pool
apr_int32_t tm_sec
Definition apr_time.h:101
apr_int32_t tm_hour
Definition apr_time.h:105
apr_int32_t tm_year
Definition apr_time.h:111
apr_int32_t tm_min
Definition apr_time.h:103
apr_int32_t tm_mday
Definition apr_time.h:107
apr_int32_t tm_mon
Definition apr_time.h:109
Structure to store things which are per connection.
Definition httpd.h:1152
struct ap_conf_vector_t * conn_config
Definition httpd.h:1190
A structure that represents the current request.
Definition httpd.h:845
char * user
Definition httpd.h:1005
char * uri
Definition httpd.h:1016
char * useragent_ip
Definition httpd.h:1101
apr_table_t * notes
Definition httpd.h:985
char * the_request
Definition httpd.h:866
apr_pool_t * pool
Definition httpd.h:847
char * filename
Definition httpd.h:1018
conn_rec * connection
Definition httpd.h:849
apr_table_t * headers_in
Definition httpd.h:976
char * protocol
Definition httpd.h:879
request_rec * main
Definition httpd.h:860
apr_table_t * subprocess_env
Definition httpd.h:983
server_rec * server
Definition httpd.h:851
const char * method
Definition httpd.h:900
char * path_info
Definition httpd.h:1024
char * args
Definition httpd.h:1026
char * ap_auth_type
Definition httpd.h:1007
apr_table_t * headers_out
Definition httpd.h:978
struct sockaddr_in local_addr
Definition mod_nw_ssl.c:110
seclisten_rec * next
Definition mod_nw_ssl.c:109
apr_port_t port
Definition mod_nw_ssl.c:116
char key[80]
Definition mod_nw_ssl.c:113
seclistenup_rec * next
Definition mod_nw_ssl.c:120
apr_port_t port
Definition mod_nw_ssl.c:123
apr_socket_t * csd
Definition mod_nw_ssl.c:133
A structure to store information for each virtual server.
Definition httpd.h:1322
char * server_admin
Definition httpd.h:1363
apr_status_t apr_os_sock_get(apr_os_sock_t *thesock, apr_socket_t *sock)
Definition sockets.c:506
apr_status_t apr_os_sock_make(apr_socket_t **apr_sock, apr_os_sock_info_t *os_sock_info, apr_pool_t *cont)
Definition sockets.c:512
apr_status_t apr_socket_close(apr_socket_t *thesocket)
Definition sockets.c:211
#define var