Busybox: Upgrade to 1.21.1 (stable). lsof active.
[tomato.git] / release / src / router / rc / nginx.c
blob93e5337eba2c8ea198599408231a4b591876dd08
1 /*
2 * nginx.c
4 * Copyright (C) 2013 NGinX for Tomato RAF
5 * ***** Ofer Chen, roadkill AT tomatoraf DOT com
6 * ***** Vicente Soriano, victek AT tomatoraf DOT com
8 * No part of this program can be used out of Tomato Firmware without owners permission.
9 * This code generates the configurations files for NGINX. You can see these files in /etc/nginx/
12 #include <stdlib.h>
13 #include <rc.h>
14 #include <shutils.h>
15 #include <utils.h>
16 #include <syslog.h>
17 #include <sys/stat.h>
18 #include <stdarg.h>
20 #define nginxbin "nginx" // process name
21 #define nginxname "tomato.local" // server name
22 #define nginxdocrootdir "/www" // document root
23 #define nginxconf "/tmp/etc/nginx/nginx.conf" // config file
24 #define nginxcustom "#" // additional window for custom parameter.
25 #define fastcgiconf "/tmp/etc/nginx/fastcgi.conf" // fastcgi config file
26 #define mimetypes "/tmp/etc/nginx/mime.types" // mime.types config
27 #define nginxdir "/tmp/etc/nginx/" // directory to write config files
28 #define client_body_temp_path "/tmp/var/lib/nginx/client" // temp path needed to execute nginx
29 #define fastcgi_temp_path "/tmp/var/lib/nginx/fastcgi" // temp path needed to execute nginx fastcgi
30 #define uwsgi_temp_path "/tmp/var/lib/nginx/uwsgi" // temp path needed to execute nginx
31 #define scgi_temp_path "/tmp/var/lib/nginx/scgi" // temp path needed to execute nginx
32 #define nginxuser "root" // user. Beta test, root can't be exposed.
33 #define nginx_worker_proc "1" // worker processes. CPU, cores.
34 #define nginx_cpu_affinity "0101" // Can bind the worker process to a CPU, it calls sched_setaffinity().
35 //define nginx_worker_priority "5" // priority ((-20)=High Priority (19)=Lowest Priority) Info: kernel have -5.
36 #define nginx_multi_accept "on" // specifies multiple connections for one core CPU
37 #define nginx_limitrate "50k" // specifies a limit rate of 50Kbps (multiply it by limit_conn_zone) per IP.
38 #define nginx_limitzone "one" // specifies the server zone to apply the restriction (limit_rate+n).
39 #define nginx_globrate "5m" // defines max global speed.
40 #define nginx_master_process "off" // set to "on" in developpment mode only.
41 #define nginx_limitsimconn "10" // defines max number of simulta. Connections in the server zone (limitzone).
42 #define nginxerrorlog "/tmp/var/log/nginx/error.log" // error log
43 #define nginxpid "/tmp/var/run/nginx.pid" // pid
44 #define nginx_worker_rlimit_profile "8192" // worker rlimit profile
45 #define nginx_keepalive_timeout "60" // the server will close connections after this time
46 #define nginx_worker_connections "512" // worker_proc*512/keepalive_timeout*60 = 512 users per minute.
47 #define nginxaccesslog "/tmp/var/log/nginx/access.log" // access log
48 #define nginssendfile "on" // sendfile
49 #define nginxtcp_nopush "on" // tcp_nopush
50 #define nginxserver_names_hash_bucket_size "128" // server names hash bucket size
52 FILE * nginx_conf_file;
53 FILE * fastcgi_conf_file;
54 FILE * mimetypes_file;
55 unsigned int fastpath=0;
57 void nginx_write(const char *format, ...) {
58 va_list args;
59 va_start(args, format);
60 vfprintf(nginx_conf_file, format, args);
61 va_end(args);
64 void fastcgi_write(const char *format, ...) {
65 va_list args;
66 va_start(args, format);
67 vfprintf(fastcgi_conf_file, format, args);
68 va_end(args);
72 void mimetypes_write(const char *format, ...) {
73 va_list args;
74 va_start(args, format);
75 vfprintf(mimetypes_file, format, args);
76 va_end(args);
79 int build_fastcgi_conf(void) {
80 // Starting a fastcgi configuration file
81 // syslog(LOG_INFO,"FastCGI - config file generation started\n");
83 if(mkdir_if_none(nginxdir));
84 // syslog(LOG_INFO,"FastCGI - directory created %s\n", nginxdir);
85 if((fastcgi_conf_file = fopen(fastcgiconf, "w")) == NULL) {
86 // notice_set("FastCGI","config file %s has been created\n", fastcgiconf);
87 simple_unlock(fastcgiconf);
88 return 0;
91 fastcgi_write("# FastCGI generated config file\n");
92 fastcgi_write("fastcgi_param SCRIPT_FILENAME\t\t$document_root$fastcgi_script_name;\n");
93 fastcgi_write("fastcgi_param QUERY_STRING\t\t$query_string;\n");
94 fastcgi_write("fastcgi_param REQUEST_METHOD\t\t$request_method;\n");
95 fastcgi_write("fastcgi_param CONTENT_TYPE\t\t$content_type;\n");
96 fastcgi_write("fastcgi_param CONTENT_LENGTH\t\t$content_length;\n");
97 fastcgi_write("fastcgi_param SCRIPT_NAME\t\t$fastcgi_script_name;\n");
98 fastcgi_write("fastcgi_param REQUEST_URI\t\t$request_uri;\n");
99 fastcgi_write("fastcgi_param DOCUMENT_URI\t\t$document_uri;\n");
100 fastcgi_write("fastcgi_param DOCUMENT_ROOT\t\t$document_root;\n");
101 fastcgi_write("fastcgi_param SERVER_PROTOCOL\t\t$server_protocol;\n");
102 fastcgi_write("fastcgi_param GATEWAY_INTERFACE\t\tCGI/1.1;\n");
103 fastcgi_write("fastcgi_param SERVER_SOFTWARE\t\tnginx/$nginx_version;\n");
104 fastcgi_write("fastcgi_param REMOTE_ADDR\t\t$remote_addr;\n");
105 fastcgi_write("fastcgi_param REMOTE_PORT\t\t$remote_port;\n");
106 fastcgi_write("fastcgi_param SERVER_ADDR\t\t$server_addr;\n");
107 fastcgi_write("fastcgi_param SERVER_PORT\t\t$server_port;\n");
108 fastcgi_write("fastcgi_param SERVER_NAME\t\t$server_name;\n");
110 fastcgi_write("fastcgi_index index.php;\n");
111 fastcgi_write("fastcgi_param REDIRECT_STATUS 200;\n");
113 fclose(fastcgi_conf_file);
114 // syslog(LOG_INFO,"FastCGI - config file finished succesfully!!\n");
115 fprintf(stderr, "Wrote: %s\n", fastcgiconf);
117 return 0;
120 int build_mime_types(void) {
121 unsigned int i; //integer cast
123 static const char *nginxdmimetypes[] = {
124 "text/html\t\t\t\thtml htm shtml",
125 "text/css\t\t\t\tcss",
126 "text/xml\t\t\t\txml rss",
127 "image/gif\t\t\t\tgif",
128 "image/jpeg\t\t\t\tjpeg jpg",
129 "application/x-javascript\t\t\t\tjs",
130 "text/plain\t\t\t\ttxt",
131 "text/x-component\t\t\t\thtc",
132 "text/mathml\t\t\t\tmml",
133 "image/png\t\t\t\tpng",
134 "image/x-icon\t\t\t\tico",
135 "image/x-jng\t\t\t\tjng",
136 "image/vnd.wap.wbmp\t\t\t\twbmp",
137 "application/java-archive\t\t\t\tjar war ear",
138 "application/mac-binhex40\t\t\t\thqx",
139 "application/pdf\t\t\t\tpdf",
140 "application/x-cocoa\t\t\t\tcco",
141 "application/x-java-archive-diff\t\t\t\tjardiff",
142 "application/x-java-jnlp-file\t\t\t\tjnlp",
143 "application/x-makeself\t\t\t\trun",
144 "application/x-perl\t\t\t\tpl pm",
145 "application/x-pilot\t\t\t\tprc pdb",
146 "application/x-rar-compressed\t\t\t\trar",
147 "application/x-redhat-package-manager\t\t\t\trpm",
148 "application/x-sea\t\t\t\tsea",
149 "application/x-shockwave-flash\t\t\t\tswf",
150 "application/x-stuffit\t\t\t\tsit",
151 "application/x-tcl\t\t\t\ttcl tk",
152 "application/x-x509-ca-cert\t\t\t\tder pem crt",
153 "application/x-xpinstall\t\t\t\txpi",
154 "application/zip\t\t\t\tzip",
155 "application/octet-stream\t\t\t\tdeb",
156 "application/octet-stream\t\t\t\tbin exe dll",
157 "application/octet-stream\t\t\t\tdmg",
158 "application/octet-stream\t\t\t\teot",
159 "application/octet-stream\t\t\t\tiso img",
160 "application/octet-stream\t\t\t\tmsi msp msm",
161 "audio/mpeg\t\t\t\tmp3",
162 "audio/x-realaudio\t\t\t\tra",
163 "video/mpeg\t\t\t\tmpeg mpg",
164 "video/quicktime\t\t\t\tmov",
165 "video/x-flv\t\t\t\tflv",
166 "video/x-msvideo\t\t\t\tavi",
167 "video/x-ms-wmv\t\t\t\twmv",
168 "video/x-ms-asf\t\t\t\tasx asf",
169 "video/x-mng\t\t\t\tmng",
170 NULL };
173 // Starting the mime.types configuration file
174 // syslog(LOG_INFO,"MimeTypes - File generation started\n");
176 if(mkdir_if_none(nginxdir));
177 // syslog(LOG_INFO,"MimeTypes - directory created %s\n", nginxdir);
178 if((mimetypes_file = fopen(mimetypes, "w")) == NULL) {
179 // notice_set("MimeTypes","file %s has been created\n", mimetypes);
180 simple_unlock(mimetypes);
181 return 0;
183 mimetypes_write("# Mime.Types generated file\n");
184 mimetypes_write("types {\n");
185 for(i=0; nginxdmimetypes[i]; i++) { mimetypes_write("\t%s;\n", nginxdmimetypes[i]); }
186 mimetypes_write("}\n");
187 fclose(mimetypes_file);
188 // syslog(LOG_INFO,"MimeTypes - file built succesfully!!\n");
189 fprintf(stderr, "Wrote: %s\n", mimetypes);
190 return 0;
193 int build_nginx_conf(void) {
194 char *buf; //default param buffer
195 unsigned int i; //integer cast
197 // Starting the nginx configuration file
198 syslog(LOG_INFO,"NGinX - started generating nginx config file\n");
200 if(mkdir_if_none(nginxdir));
201 // syslog(LOG_INFO,"NGinX - directory created %s\n", nginxdir);
202 if((nginx_conf_file = fopen(nginxconf, "w")) == NULL) {
203 // notice_set("NGinX","config file %s has been created\n", nginxconf);
204 simple_unlock(nginxconf);
205 return 0;
207 nginx_write("# NGinX generated config file\n");
208 // syslog(LOG_INFO,"NGinX","started writing config file %s\n", nginxconf);
210 //Global process
211 nginx_write("user\t%s;\n", nginxuser);
212 nginx_write("worker_processes\t%s;\n", nginx_worker_proc);
213 nginx_write("worker_cpu_affinity\t%s;\n", nginx_cpu_affinity);
214 nginx_write("master_process\t%s;\n", nginx_master_process);
215 i = nvram_get_int("nginx_priority");
216 if ((i <= -20) || (i >= 19)) i = 10; // min = Max Performance and max= Min Performance value for worker_priority
217 nginx_write("worker_priority\t%d;\n", i);
218 nginx_write("error_log\t%s;\n", nginxerrorlog);
219 nginx_write("pid\t%s;\n", nginxpid);
220 nginx_write("worker_rlimit_nofile\t%s;\n", nginx_worker_rlimit_profile);
222 //Events
223 nginx_write("events {\n");
224 nginx_write("\tworker_connections\t%s;\n", nginx_worker_connections);
225 // nginx_write("\tmulti_accept\t%s;\n", nginx_multi_accept);
226 nginx_write("\t}\n");
228 //http
229 nginx_write("http {\n");
230 nginx_write("include\t%s;\n", mimetypes);
231 nginx_write("include\t%s;\n", fastcgiconf);
232 nginx_write("default_type\tapplication/octet-stream;\n");
233 nginx_write("log_format main '$remote_addr - $remote_user [$time_local] $status '\n");
234 nginx_write("'\"$request\" $body_bytes_sent \"$http_referer\" '\n");
235 nginx_write("'\"$http_user_agent\" \"$http_x_forwarded_for\"';\n");
236 nginx_write("sendfile\t%s;\n", nginssendfile);
238 // nginx_write("keepalive_timeout\t%s;\n", nginx_keepalive_timeout);
239 // nginx_write("tcp_nopush\t%s;\n", nginxtcp_nopush);
240 // nginx_write("server_names_hash_bucket_size\t%s;\n", nginxserver_names_hash_bucket_size);
241 // nginx_write("limit_req_zone $binary_remote_addr zone=one:10m rate=1r/s;\n");
243 //Basic Server Parameters.
244 nginx_write("server {\n");
245 i = nvram_get_int("nginx_port");
246 if ((i <= 0) || (i >= 0xFFFF)) i = 85; // 0xFFFF 65535
247 nginx_write("listen\t%d;\n", i);
248 if ((buf = nvram_safe_get("nginx_fqdn")) == NULL) buf = nginxname;
249 nginx_write("server_name\t%s;\n", buf);
250 nginx_write("access_log\t%s\tmain;\n", nginxaccesslog);
251 nginx_write("location\t/\t{\n");
252 if ((buf = nvram_safe_get("nginx_docroot")) == NULL) buf = nginxdocrootdir;
253 nginx_write("root\t%s;\n", buf);
254 nginx_write("index\tindex.html\tindex.htm\tindex.php;\n");
255 // Error pages section
256 nginx_write("error_page 404\t/404.html;\n");
257 nginx_write("error_page 500\t502\t503\t504\t/50x.html;\n");
258 nginx_write("location\t/50x.html\t{\n");
259 if ((buf = nvram_safe_get("nginx_docroot")) == NULL) buf = nginxdocrootdir;
260 nginx_write("root\t%s;\n", buf);
261 nginx_write("}\n");
263 // PHP to FastCGI Server
264 nginx_write("location ~ \\.php$ {\n");
265 nginx_write("root\t%s;\n", buf);
266 nginx_write("fastcgi_pass\t127.0.0.1:9000;\n");
267 nginx_write("fastcgi_index\tindex.php;\n");
268 nginx_write("\t}\n");
269 // Server for static files
270 nginx_write("location ~ ^/(images|javascript|js|css|flash|media|static)/ {\n");
271 nginx_write("root\t%s;\n", buf);
272 nginx_write("expires 10d;\n");
273 nginx_write("\t\t\t}\n");
274 nginx_write("\t\t}\n");
275 nginx_write("\t}\n");
276 nginx_write("}\n");
277 // Process to close and write config file
278 nginx_write("\n");
279 if ((buf = nvram_safe_get("nginx_custom")) == NULL) buf = nginxcustom;
280 nginx_write(buf);
281 fclose(nginx_conf_file);
282 syslog(LOG_INFO,"NGinX - config file built succesfully\n");
283 fprintf(stderr, "Wrote: %s\n", nginxconf);
284 return 0;
287 // Start the NGINX module according environment directives.
288 void start_nginx(void)
290 if (fastpath != 1) {
291 if(!nvram_match("nginx_enable", "1")){
292 syslog(LOG_INFO,"NGinX - daemon not enabled cancelled generation of config file\n");
293 return;
295 }else{
296 syslog(LOG_INFO,"NGinX - fastpath forced generation of config file\n");
299 if (fastpath != 1) {
300 stop_nginx();
301 }else{
302 stop_nginxfp();
305 if (!f_exists(fastcgiconf)) build_fastcgi_conf();
306 if (!f_exists(mimetypes)) build_mime_types();
308 if (fastpath != 1) {
309 build_nginx_conf();
310 }else{
311 if (!f_exists(nginxconf)) build_nginx_conf();
314 if(mkdir_if_none(client_body_temp_path));
315 // syslog(LOG_INFO,"NGinX - directory created %s\n", client_body_temp_path);
316 if(mkdir_if_none(fastcgi_temp_path));
317 // syslog(LOG_INFO,"NGinX - directory created %s\n", fastcgi_temp_path);
318 if(mkdir_if_none(uwsgi_temp_path));
319 // syslog(LOG_INFO,"NGinX - directory created %s\n", uwsgi_temp_path);
320 if(mkdir_if_none(scgi_temp_path));
321 // syslog(LOG_INFO,"NGinX - directory created %s\n", scgi_temp_path);
322 syslog(LOG_INFO,"NGinX - running daemon\n");
323 xstart(nginxbin, "-c", nginxconf);
325 // Start NGinx using fastpath method no checks
326 void start_nginxfp(void)
328 fastpath = 1;
329 start_nginx();
330 fastpath = 0;
332 // Stopping NGINX and remove traces of the process.
333 void stop_nginx(void)
335 unsigned int i;
337 i = 0;
338 syslog(LOG_INFO,"NGinX - killing daemon\n");
339 if ((i = pidof (nginxbin)) > 0) {
340 killall_tk(nginxbin);
341 if (f_exists(nginxpid)) {
342 unlink(nginxpid);
343 // syslog(LOG_INFO,"NGinX - removed pid file %s\n", nginxpid);
345 if (f_exists(fastcgiconf)) {
346 if (fastpath != 1) {
347 unlink(fastcgiconf);
348 // syslog(LOG_INFO,"NGinX - removed fastcgi config file %s\n", fastcgiconf);
350 // syslog(LOG_INFO,"NGinX - skip removal of fastcgi config file %s due to fastpath method\n", fastcgiconf);
352 if (f_exists(mimetypes)) {
353 if (fastpath != 1) {
354 unlink(mimetypes);
355 // syslog(LOG_INFO,"NGinX - remove mime types file %s\n", mimetypes);
357 // syslog(LOG_INFO,"NGinX - skip removal of mime types config file %s due to fastpath method\n", mimetypes);
359 if (f_exists(nginxconf)) {
360 if (fastpath != 1) {
361 unlink(nginxconf);
362 // syslog(LOG_INFO,"NGinX - removed nginx config file %s\n", nginxconf);
364 // syslog(LOG_INFO,"NGinX - skip removal of nginx config file %s due to fastpath method\n", nginxconf);
368 // Stop NGinx using fastpath method no checks
369 void stop_nginxfp(void)
371 fastpath = 1;
372 stop_nginx();
373 fastpath = 0;