33 RIBS is an infrastructure for building great SaaS applications (but not
44 limited to).
55
6- Copyright (C) 2012,2013 Adap.tv, Inc.
6+ Copyright (C) 2012,2013,2014 Adap.tv, Inc.
77
88 RIBS is free software: you can redistribute it and/or modify
99 it under the terms of the GNU Lesser General Public License as published by
2020#include "ribs.h"
2121#include <getopt.h>
2222#include <unistd.h>
23+
24+ /* do not allow files outside current working directory */
25+ char * current_dir_name = NULL ;
26+ size_t current_dir_name_size = 0 ;
27+
2328/*
2429 * file server
2530 */
@@ -35,6 +40,16 @@ void simple_file_server(void) {
3540 const char * file = ctx -> uri ;
3641 if (* file == '/' ) ++ file ;
3742
43+ if (* file ) {
44+ char * rp = ribs_malloc (PATH_MAX );
45+ if (NULL == realpath (file , rp ) ||
46+ 0 != strncmp (current_dir_name , rp , current_dir_name_size )) {
47+ http_server_response_sprintf (HTTP_STATUS_404 ,
48+ HTTP_CONTENT_TYPE_TEXT_PLAIN , "not found: %s" , file );
49+ return ;
50+ }
51+ }
52+
3853 int res = http_server_sendfile (file );
3954 if (0 > res ) {
4055 /* not found */
@@ -47,7 +62,7 @@ void simple_file_server(void) {
4762 }
4863 else if (0 < res ) {
4964 /* directory */
50- if (0 > http_server_generate_dir_list (ctx -> uri )) {
65+ if (0 > http_server_generate_dir_list (file )) {
5166 http_server_response_sprintf (HTTP_STATUS_404 ,
5267 HTTP_CONTENT_TYPE_TEXT_PLAIN , "dir not found: %s" , ctx -> uri );
5368 return ;
@@ -62,15 +77,25 @@ int main(int argc, char *argv[]) {
6277 {"port" , 1 , 0 , 'p' },
6378 {"daemonize" , 0 , 0 , 'd' },
6479 {"forks" , 1 , 0 , 'f' },
80+ {"ssl_port" , 1 , 0 ,'s' },
81+ {"key_file" , 1 , 0 , 'k' },
82+ {"chain_file" , 1 , 0 , 'c' },
83+ {"cipher_list" , 1 , 0 , 'l' },
6584 {0 , 0 , 0 , 0 }
6685 };
6786
6887 int port = 8080 ;
6988 int daemon_mode = 0 ;
7089 int forks = 0 ;
90+ #ifdef RIBS2_SSL
91+ int sport = 8443 ;
92+ char * key_file = NULL ;
93+ char * chain_file = NULL ;
94+ char * cipher_list = NULL ;
95+ #endif
7196 for (;;) {
7297 int option_index = 0 ;
73- int c = getopt_long (argc , argv , "p:f:d" , long_options , & option_index );
98+ int c = getopt_long (argc , argv , "p:f:s:c:k:l: d" , long_options , & option_index );
7499 if (c == -1 )
75100 break ;
76101 switch (c ) {
@@ -83,68 +108,115 @@ int main(int argc, char *argv[]) {
83108 case 'f' :
84109 forks = atoi (optarg );
85110 break ;
111+ #ifdef RIBS2_SSL
112+ case 'k' :
113+ key_file = optarg ;
114+ break ;
115+ case 'c' :
116+ chain_file = optarg ;
117+ break ;
118+ case 's' :
119+ sport = atoi (optarg );
120+ break ;
121+ case 'l' :
122+ cipher_list = optarg ;
123+ break ;
124+ #endif
86125 }
87126 }
88127
89- /* server config */
90- struct http_server server = {
91- /* port number */
92- .port = port ,
93-
94- /* call simple_file_server upon receiving http request */
95- .user_func = simple_file_server ,
96-
97- /* set idle connection timeout to 60 seconds */
98- .timeout_handler .timeout = 60000 ,
99-
100- /* set fiber's stack size to automatic (0) */
101- .stack_size = 0 ,
102-
103- /* start the server with 100 stacks */
104- /* more stacks will be created if necessary */
105- .num_stacks = 100 ,
106-
107- /* we expect most of our requests to be less than 8K */
108- .init_request_size = 8192 ,
109-
110- /* we expect most of our response headers to be less than
111- 8K */
112- .init_header_size = 8192 ,
113-
114- /* we expect most of our response payloads to be less than
115- 8K */
116- .init_payload_size = 8192 ,
117-
118- /* no limit on the request size, this should be set to
119- something reasonable if you want to protect your server
120- against denial of service attack */
121- .max_req_size = 0 ,
122-
123- /* no additional space is needed in the context to store app
124- specified data (fiber local storage) */
125- .context_size = 0
126- };
128+ char * cd = get_current_dir_name ();
129+ current_dir_name = malloc (PATH_MAX );
130+ if (NULL == realpath (cd , current_dir_name )) {
131+ LOGGER_PERROR ("realpath" );
132+ exit (EXIT_FAILURE );
133+ }
134+ free (cd );
135+ current_dir_name_size = strlen (current_dir_name );
136+
137+ /*
138+ * server config
139+ */
140+ struct http_server server = HTTP_SERVER_INITIALIZER ;
141+ /* port number */
142+ server .port = port ,
143+ /* call simple_file_server upon receiving http request */
144+ server .user_func = simple_file_server ,
145+ /* set idle connection timeout to 60 seconds */
146+ server .timeout_handler .timeout = 60000 ,
147+ /* set fiber's stack size to automatic (0) */
148+ server .stack_size = 0 ,
149+ /* start the server with 100 stacks */
150+ /* more stacks will be created if necessary */
151+ server .num_stacks = 100 ,
152+ /* we expect most of our requests to be less than 8K */
153+ server .init_request_size = 8192 ,
154+ /* we expect most of our response headers to be less than
155+ 8K */
156+ server .init_header_size = 8192 ,
157+ /* we expect most of our response payloads to be less than
158+ 8K */
159+ server .init_payload_size = 8192 ,
160+ /* no limit on the request size, this should be set to
161+ something reasonable if you want to protect your server
162+ against denial of service attack */
163+ server .max_req_size = 0 ,
164+ /* no additional space is needed in the context to store app
165+ specified data (fiber local storage) */
166+ server .context_size = 0 ,
167+ server .bind_addr = htonl (INADDR_ANY );
168+ #ifdef RIBS2_SSL
169+ server .use_ssl = 0 ;
170+
171+ /*
172+ * ssl server config
173+ */
174+ struct http_server server_ssl = HTTP_SERVER_INITIALIZER ;
175+ /* port number */
176+ server_ssl .port = sport ,
177+ /* call simple_file_server upon receiving http request */
178+ server_ssl .user_func = simple_file_server ,
179+ /* set idle connection timeout to 60 seconds */
180+ server_ssl .timeout_handler .timeout = 60000 ,
181+ /* set fiber's stack size to automatic (0) */
182+ server_ssl .stack_size = 0 ,
183+ /* start the server with 100 stacks */
184+ /* more stacks will be created if necessary */
185+ server_ssl .num_stacks = 100 ,
186+ /* we expect most of our requests to be less than 8K */
187+ server_ssl .init_request_size = 8192 ,
188+ /* we expect most of our response headers to be less than
189+ 8K */
190+ server_ssl .init_header_size = 8192 ,
191+ /* we expect most of our response payloads to be less than
192+ 8K */
193+ server_ssl .init_payload_size = 8192 ,
194+ /* no limit on the request size, this should be set to
195+ something reasonable if you want to protect your server
196+ against denial of service attack */
197+ server_ssl .max_req_size = 0 ,
198+ /* no additional space is needed in the context to store app
199+ specified data (fiber local storage) */
200+ server_ssl .context_size = 0 ,
201+ /* accept connections from any address */
202+ server_ssl .bind_addr = htonl (INADDR_ANY ),
203+ server_ssl .use_ssl = 1 ,
204+ server_ssl .privatekey_file = key_file ,
205+ server_ssl .certificate_chain_file = chain_file ;
206+
207+ if (cipher_list )
208+ server_ssl .cipher_list = cipher_list ;
209+
210+ if (key_file && 0 > http_server_init2 (& server_ssl ))
211+ exit (EXIT_FAILURE );
212+ #endif
127213
128214 /* initialize server, but don't accept connections yet */
129- if (0 > http_server_init (& server ))
215+ if (0 > http_server_init2 (& server ))
130216 exit (EXIT_FAILURE );
131217
132- /* run as daemon if specified */
133- if (daemon_mode )
134- daemonize (), daemon_finalize ();
135-
136- /* assume autoconfiguration if forks is not a positive value */
137- if (0 >= forks ) {
138- forks = sysconf (_SC_NPROCESSORS_CONF );
139- if (0 > forks )
140- exit (EXIT_FAILURE );
141- }
142-
143- for (; forks > 1 ; -- forks ){
144- if (0 >= fork ()) {
145- break ;
146- }
147- }
218+ if (0 > ribs_server_init (daemon_mode , "httpd.pid" , "httpd.log" , forks ))
219+ exit (EXIT_FAILURE );
148220
149221 /* initialize the event loop */
150222 if (0 > epoll_worker_init ())
@@ -154,7 +226,10 @@ int main(int argc, char *argv[]) {
154226 epoll worker */
155227 if (0 > http_server_init_acceptor (& server ))
156228 exit (EXIT_FAILURE );
157-
158- epoll_worker_loop ();
229+ #ifdef RIBS2_SSL
230+ if (key_file && 0 > http_server_init_acceptor (& server_ssl ))
231+ exit (EXIT_FAILURE );
232+ #endif
233+ ribs_server_start ();
159234 return 0 ;
160235}
0 commit comments