Merge branch 'tomato-RT' into tomato-1.28-Toastman-RT
[tomato.git] / release / src / router / rc / services.c
blobf92f1e933063d4f92fec82970a4b7c513bd4555b
1 /*
3 Copyright 2003, CyberTAN Inc. All Rights Reserved
5 This is UNPUBLISHED PROPRIETARY SOURCE CODE of CyberTAN Inc.
6 the contents of this file may not be disclosed to third parties,
7 copied or duplicated in any form without the prior written
8 permission of CyberTAN Inc.
10 This software should be used as a reference only, and it not
11 intended for production use!
13 THIS SOFTWARE IS OFFERED "AS IS", AND CYBERTAN GRANTS NO WARRANTIES OF ANY
14 KIND, EXPRESS OR IMPLIED, BY STATUTE, COMMUNICATION OR OTHERWISE. CYBERTAN
15 SPECIFICALLY DISCLAIMS ANY IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS
16 FOR A SPECIFIC PURPOSE OR NONINFRINGEMENT CONCERNING THIS SOFTWARE
21 Copyright 2005, Broadcom Corporation
22 All Rights Reserved.
24 THIS SOFTWARE IS OFFERED "AS IS", AND BROADCOM GRANTS NO WARRANTIES OF ANY
25 KIND, EXPRESS OR IMPLIED, BY STATUTE, COMMUNICATION OR OTHERWISE. BROADCOM
26 SPECIFICALLY DISCLAIMS ANY IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS
27 FOR A SPECIFIC PURPOSE OR NONINFRINGEMENT CONCERNING THIS SOFTWARE.
32 Modified for Tomato Firmware
33 Portions, Copyright (C) 2006-2009 Jonathan Zarate
36 #include "rc.h"
38 #include <arpa/inet.h>
39 #include <time.h>
40 #include <sys/time.h>
41 #include <errno.h>
43 // !!TB
44 #include <sys/mount.h>
45 #include <mntent.h>
46 #include <dirent.h>
48 #define IFUP (IFF_UP | IFF_RUNNING | IFF_BROADCAST | IFF_MULTICAST)
49 #define sin_addr(s) (((struct sockaddr_in *)(s))->sin_addr)
51 // Pop an alarm to recheck pids in 500 msec.
52 static const struct itimerval pop_tv = { {0,0}, {0, 500 * 1000} };
54 // Pop an alarm to reap zombies.
55 static const struct itimerval zombie_tv = { {0,0}, {307, 0} };
57 // -----------------------------------------------------------------------------
59 static const char dmhosts[] = "/etc/hosts.dnsmasq";
60 static const char dmresolv[] = "/etc/resolv.dnsmasq";
62 static pid_t pid_dnsmasq = -1;
64 static int is_wet(int idx, int unit, int subunit, void *param)
66 return nvram_match(wl_nvname("mode", unit, subunit), "wet");
69 void start_dnsmasq()
71 FILE *f;
72 const char *nv;
73 char buf[512];
74 char lan[24];
75 const char *router_ip;
76 const char *lan_ifname;
77 char sdhcp_lease[32];
78 char *e;
79 int n;
80 char *mac, *ip, *name;
81 char *p;
82 int ipn;
83 char ipbuf[32];
84 FILE *hf;
85 int dhcp_start;
86 int dhcp_count;
87 int dhcp_lease;
88 int do_dhcpd;
89 int do_dns;
91 TRACE_PT("begin\n");
93 if (getpid() != 1) {
94 start_service("dnsmasq");
95 return;
98 stop_dnsmasq();
100 if (foreach_wif(1, NULL, is_wet)) return;
102 if ((f = fopen("/etc/dnsmasq.conf", "w")) == NULL) return;
104 lan_ifname = nvram_safe_get("lan_ifname");
105 router_ip = nvram_safe_get("lan_ipaddr");
106 strlcpy(lan, router_ip, sizeof(lan));
107 if ((p = strrchr(lan, '.')) != NULL) *(p + 1) = 0;
109 fprintf(f,
110 "pid-file=/var/run/dnsmasq.pid\n"
111 "interface=%s\n",
112 lan_ifname);
113 if (((nv = nvram_get("wan_domain")) != NULL) || ((nv = nvram_get("wan_get_domain")) != NULL)) {
114 if (*nv) fprintf(f, "domain=%s\n", nv);
117 // dns
118 const dns_list_t *dns = get_dns(); // this always points to a static buffer
120 if (((nv = nvram_get("dns_minport")) != NULL) && (*nv)) n = atoi(nv);
121 else n = 4096;
122 fprintf(f,
123 "resolv-file=%s\n" // the real stuff is here
124 "addn-hosts=%s\n" // "
125 "expand-hosts\n" // expand hostnames in hosts file
126 "min-port=%u\n", // min port used for random src port
127 dmresolv, dmhosts, n);
128 do_dns = nvram_match("dhcpd_dmdns", "1");
130 // DNS rebinding protection, will discard upstream RFC1918 responses
131 if (nvram_get_int("dns_norebind")) {
132 fprintf(f,
133 "stop-dns-rebind\n"
134 "rebind-localhost-ok\n");
135 // allow RFC1918 responses for server domain
136 switch (get_wan_proto()) {
137 case WP_PPTP:
138 nv = nvram_get("pptp_server_ip");
139 break;
140 case WP_L2TP:
141 nv = nvram_get("l2tp_server_ip");
142 break;
143 default:
144 nv = NULL;
145 break;
147 if (nv && *nv) fprintf(f, "rebind-domain-ok=%s\n", nv);
150 for (n = 0 ; n < dns->count; ++n) {
151 if (dns->dns[n].port != 53) {
152 fprintf(f, "server=%s#%u\n", inet_ntoa(dns->dns[n].addr), dns->dns[n].port);
157 // dhcp
158 do_dhcpd = nvram_match("lan_proto", "dhcp");
159 if (do_dhcpd) {
160 dhcp_lease = nvram_get_int("dhcp_lease");
161 if (dhcp_lease <= 0) dhcp_lease = 1440;
163 if ((e = nvram_get("dhcpd_slt")) != NULL) n = atoi(e); else n = 0;
164 if (n < 0) strcpy(sdhcp_lease, "infinite");
165 else sprintf(sdhcp_lease, "%dm", (n > 0) ? n : dhcp_lease);
167 if (!do_dns) {
168 // if not using dnsmasq for dns
170 if ((dns->count == 0) && (nvram_get_int("dhcpd_llndns"))) {
171 // no DNS might be temporary. use a low lease time to force clients to update.
172 dhcp_lease = 2;
173 strcpy(sdhcp_lease, "2m");
174 do_dns = 1;
176 else {
177 // pass the dns directly
178 buf[0] = 0;
179 for (n = 0 ; n < dns->count; ++n) {
180 if (dns->dns[n].port == 53) { // check: option 6 doesn't seem to support other ports
181 sprintf(buf + strlen(buf), ",%s", inet_ntoa(dns->dns[n].addr));
184 fprintf(f, "dhcp-option=6%s\n", buf);
188 if ((p = nvram_get("dhcpd_startip")) && (*p) && (e = nvram_get("dhcpd_endip")) && (*e)) {
189 fprintf(f, "dhcp-range=%s,%s,%s,%dm\n", p, e, nvram_safe_get("lan_netmask"), dhcp_lease);
191 else {
192 // for compatibility
193 dhcp_start = nvram_get_int("dhcp_start");
194 dhcp_count = nvram_get_int("dhcp_num");
195 fprintf(f, "dhcp-range=%s%d,%s%d,%s,%dm\n",
196 lan, dhcp_start, lan, dhcp_start + dhcp_count - 1, nvram_safe_get("lan_netmask"), dhcp_lease);
199 nv = router_ip;
200 if ((nvram_get_int("dhcpd_gwmode") == 1) && (get_wan_proto() == WP_DISABLED)) {
201 p = nvram_safe_get("lan_gateway");
202 if ((*p) && (strcmp(p, "0.0.0.0") != 0)) nv = p;
205 n = nvram_get_int("dhcpd_lmax");
206 fprintf(f,
207 "dhcp-option=3,%s\n" // gateway
208 "dhcp-lease-max=%d\n",
210 (n > 0) ? n : 255);
212 if (nvram_get_int("dhcpd_auth") >= 0) {
213 fprintf(f, "dhcp-authoritative\n");
216 if (((nv = nvram_get("wan_wins")) != NULL) && (*nv) && (strcmp(nv, "0.0.0.0") != 0)) {
217 fprintf(f, "dhcp-option=44,%s\n", nv);
219 #ifdef TCONFIG_SAMBASRV
220 else if (nvram_get_int("smbd_enable") && nvram_invmatch("lan_hostname", "") && nvram_get_int("smbd_wins")) {
221 if ((nv == NULL) || (*nv == 0) || (strcmp(nv, "0.0.0.0") == 0)) {
222 // Samba will serve as a WINS server
223 fprintf(f, "dhcp-option=44,0.0.0.0\n");
226 #endif
228 else {
229 fprintf(f, "no-dhcp-interface=%s\n", lan_ifname);
232 // write static lease entries & create hosts file
234 if ((hf = fopen(dmhosts, "w")) != NULL) {
235 if (((nv = nvram_get("wan_hostname")) != NULL) && (*nv))
236 fprintf(hf, "%s %s\n", router_ip, nv);
237 #ifdef TCONFIG_SAMBASRV
238 else if (((nv = nvram_get("lan_hostname")) != NULL) && (*nv))
239 fprintf(hf, "%s %s\n", router_ip, nv);
240 #endif
243 // 00:aa:bb:cc:dd:ee<123<xxxxxxxxxxxxxxxxxxxxxxxxxx.xyz> = 53 w/ delim
244 // 00:aa:bb:cc:dd:ee<123.123.123.123<xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xyz> = 85 w/ delim
245 // 00:aa:bb:cc:dd:ee,00:aa:bb:cc:dd:ee<123.123.123.123<xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.xyz> = 106 w/ delim
246 p = nvram_safe_get("dhcpd_static");
247 while ((e = strchr(p, '>')) != NULL) {
248 n = (e - p);
249 if (n > 105) {
250 p = e + 1;
251 continue;
254 strncpy(buf, p, n);
255 buf[n] = 0;
256 p = e + 1;
258 if ((e = strchr(buf, '<')) == NULL) continue;
259 *e = 0;
260 mac = buf;
262 ip = e + 1;
263 if ((e = strchr(ip, '<')) == NULL) continue;
264 *e = 0;
265 if (strchr(ip, '.') == NULL) {
266 ipn = atoi(ip);
267 if ((ipn <= 0) || (ipn > 255)) continue;
268 sprintf(ipbuf, "%s%d", lan, ipn);
269 ip = ipbuf;
271 else {
272 if (inet_addr(ip) == INADDR_NONE) continue;
275 name = e + 1;
277 if ((hf) && (*name != 0)) {
278 fprintf(hf, "%s %s\n", ip, name);
281 if ((do_dhcpd) && (*mac != 0) && (strcmp(mac, "00:00:00:00:00:00") != 0)) {
282 fprintf(f, "dhcp-host=%s,%s,%s\n", mac, ip, sdhcp_lease);
286 if (hf) fclose(hf);
290 #ifdef TCONFIG_OPENVPN
291 write_vpn_dnsmasq_config(f);
292 #endif
294 fprintf(f, "%s\n\n", nvram_safe_get("dnsmasq_custom"));
296 fappend(f, "/etc/dnsmasq.custom");
300 fclose(f);
302 if (do_dns) {
303 unlink("/etc/resolv.conf");
304 symlink("/rom/etc/resolv.conf", "/etc/resolv.conf"); // nameserver 127.0.0.1
307 TRACE_PT("run dnsmasq\n");
309 eval("dnsmasq");
311 if (!nvram_contains_word("debug_norestart", "dnsmasq")) {
312 pid_dnsmasq = -2;
315 TRACE_PT("end\n");
318 void stop_dnsmasq(void)
320 TRACE_PT("begin\n");
322 if (getpid() != 1) {
323 stop_service("dnsmasq");
324 return;
327 pid_dnsmasq = -1;
329 unlink("/etc/resolv.conf");
330 symlink(dmresolv, "/etc/resolv.conf");
332 killall_tk("dnsmasq");
334 TRACE_PT("end\n");
337 void clear_resolv(void)
339 f_write(dmresolv, NULL, 0, 0, 0); // blank
342 void dns_to_resolv(void)
344 FILE *f;
345 const dns_list_t *dns;
346 int i;
347 mode_t m;
349 m = umask(022); // 077 from pppoecd
350 if ((f = fopen(dmresolv, "w")) != NULL) {
351 // Check for VPN DNS entries
352 if (!write_vpn_resolv(f)) {
353 dns = get_dns(); // static buffer
354 if (dns->count == 0) {
355 // Put a pseudo DNS IP to trigger Connect On Demand
356 if (nvram_match("ppp_demand", "1")) {
357 switch (get_wan_proto()) {
358 case WP_PPPOE:
359 case WP_PPTP:
360 case WP_L2TP:
361 fprintf(f, "nameserver 1.1.1.1\n");
362 break;
366 else {
367 for (i = 0; i < dns->count; i++) {
368 if (dns->dns[i].port == 53) { // resolv.conf doesn't allow for an alternate port
369 fprintf(f, "nameserver %s\n", inet_ntoa(dns->dns[i].addr));
374 fclose(f);
376 umask(m);
379 // -----------------------------------------------------------------------------
381 void start_httpd(void)
383 chdir("/www");
384 if (!nvram_match("http_enable", "0")) {
385 xstart("httpd");
387 if (!nvram_match("https_enable", "0")) {
388 xstart("httpd", "-s");
390 chdir("/");
393 void stop_httpd(void)
395 killall_tk("httpd");
398 // -----------------------------------------------------------------------------
400 void start_upnp(void)
402 if (get_wan_proto() == WP_DISABLED) return;
404 int enable;
405 FILE *f;
406 int upnp_port;
408 if (((enable = nvram_get_int("upnp_enable")) & 3) != 0) {
409 mkdir("/etc/upnp", 0777);
410 if (f_exists("/etc/upnp/config.alt")) {
411 xstart("miniupnpd", "-f", "/etc/upnp/config.alt");
413 else {
414 if ((f = fopen("/etc/upnp/config", "w")) != NULL) {
415 upnp_port = nvram_get_int("upnp_port");
416 if ((upnp_port < 0) || (upnp_port >= 0xFFFF)) upnp_port = 0;
418 char *lanip = nvram_safe_get("lan_ipaddr");
419 char *lanmask = nvram_safe_get("lan_netmask");
421 fprintf(f,
422 "ext_ifname=%s\n"
423 "listening_ip=%s/%s\n"
424 "port=%d\n"
425 "enable_upnp=%s\n"
426 "enable_natpmp=%s\n"
427 "secure_mode=%s\n"
428 "upnp_forward_chain=upnp\n"
429 "upnp_nat_chain=upnp\n"
430 "notify_interval=%d\n"
431 "system_uptime=yes\n"
432 "\n"
434 nvram_safe_get("wan_iface"),
435 lanip, lanmask,
436 upnp_port,
437 (enable & 1) ? "yes" : "no", // upnp enable
438 (enable & 2) ? "yes" : "no", // natpmp enable
439 nvram_get_int("upnp_secure") ? "yes" : "no", // secure_mode (only forward to self)
440 nvram_get_int("upnp_ssdp_interval")
443 if (nvram_get_int("upnp_clean")) {
444 int interval = nvram_get_int("upnp_clean_interval");
445 if (interval < 60) interval = 60;
446 fprintf(f,
447 "clean_ruleset_interval=%d\n"
448 "clean_ruleset_threshold=%d\n",
449 interval,
450 nvram_get_int("upnp_clean_threshold")
453 else
454 fprintf(f,"clean_ruleset_interval=0\n");
456 if (nvram_match("upnp_mnp", "1")) {
457 int https = nvram_get_int("https_enable");
458 fprintf(f, "presentation_url=http%s://%s:%s/forward-upnp.asp\n",
459 https ? "s" : "", lanip,
460 nvram_safe_get(https ? "https_lanport" : "http_lanport"));
462 else {
463 // Empty parameters are not included into XML service description
464 fprintf(f, "presentation_url=\n");
467 char uuid[45];
468 f_read_string("/proc/sys/kernel/random/uuid", uuid, sizeof(uuid));
469 fprintf(f, "uuid=%s\n", uuid);
471 int ports[4];
472 if ((ports[0] = nvram_get_int("upnp_min_port_int")) > 0 &&
473 (ports[1] = nvram_get_int("upnp_max_port_int")) > 0 &&
474 (ports[2] = nvram_get_int("upnp_min_port_ext")) > 0 &&
475 (ports[3] = nvram_get_int("upnp_max_port_ext")) > 0) {
476 fprintf(f,
477 "allow %d-%d %s/%s %d-%d\n",
478 ports[0], ports[1],
479 lanip, lanmask,
480 ports[2], ports[3]
483 else {
484 // by default allow only redirection of ports above 1024
485 fprintf(f, "allow 1024-65535 %s/%s 1024-65535\n", lanip, lanmask);
488 fappend(f, "/jffs/upnpconfig.custom");
489 fappend(f, "/etc/upnp/config.custom");
490 fprintf(f, "\ndeny 0-65535 0.0.0.0/0 0-65535\n");
491 fclose(f);
493 xstart("miniupnpd", "-f", "/etc/upnp/config");
499 void stop_upnp(void)
501 killall_tk("miniupnpd");
504 // -----------------------------------------------------------------------------
506 static pid_t pid_crond = -1;
508 void start_cron(void)
510 stop_cron();
512 eval("crond", nvram_contains_word("log_events", "crond") ? NULL : "-l", "9");
513 if (!nvram_contains_word("debug_norestart", "crond")) {
514 pid_crond = -2;
518 void stop_cron(void)
520 pid_crond = -1;
521 killall_tk("crond");
524 // -----------------------------------------------------------------------------
525 #ifdef LINUX26
527 static pid_t pid_hotplug2 = -1;
529 void start_hotplug2()
531 stop_hotplug2();
533 f_write_string("/proc/sys/kernel/hotplug", "", FW_NEWLINE, 0);
534 xstart("hotplug2", "--persistent", "--no-coldplug");
535 // FIXME: Don't remember exactly why I put "sleep" here -
536 // but it was not for a race with check_services()... - TB
537 sleep(1);
539 if (!nvram_contains_word("debug_norestart", "hotplug2")) {
540 pid_hotplug2 = -2;
544 void stop_hotplug2(void)
546 pid_hotplug2 = -1;
547 killall_tk("hotplug2");
550 #endif /* LINUX26 */
551 // -----------------------------------------------------------------------------
553 // Written by Sparq in 2002/07/16
554 void start_zebra(void)
556 #ifdef TCONFIG_ZEBRA
557 FILE *fp;
559 char *lan_tx = nvram_safe_get("dr_lan_tx");
560 char *lan_rx = nvram_safe_get("dr_lan_rx");
561 char *wan_tx = nvram_safe_get("dr_wan_tx");
562 char *wan_rx = nvram_safe_get("dr_wan_rx");
564 if ((*lan_tx == '0') && (*lan_rx == '0') && (*wan_tx == '0') && (*wan_rx == '0')) {
565 return;
568 // empty
569 if ((fp = fopen("/etc/zebra.conf", "w")) != NULL) {
570 fclose(fp);
574 if ((fp = fopen("/etc/ripd.conf", "w")) != NULL) {
575 char *lan_ifname = nvram_safe_get("lan_ifname");
576 char *wan_ifname = nvram_safe_get("wan_ifname");
578 fprintf(fp, "router rip\n");
579 fprintf(fp, "network %s\n", lan_ifname);
580 fprintf(fp, "network %s\n", wan_ifname);
581 fprintf(fp, "redistribute connected\n");
582 //fprintf(fp, "redistribute static\n");
584 // 43011: modify by zg 2006.10.18 for cdrouter3.3 item 173(cdrouter_rip_30) bug
585 // fprintf(fp, "redistribute kernel\n"); // 1.11: removed, redistributes indirect -- zzz
587 fprintf(fp, "interface %s\n", lan_ifname);
588 if (*lan_tx != '0') fprintf(fp, "ip rip send version %s\n", lan_tx);
589 if (*lan_rx != '0') fprintf(fp, "ip rip receive version %s\n", lan_rx);
591 fprintf(fp, "interface %s\n", wan_ifname);
592 if (*wan_tx != '0') fprintf(fp, "ip rip send version %s\n", wan_tx);
593 if (*wan_rx != '0') fprintf(fp, "ip rip receive version %s\n", wan_rx);
595 fprintf(fp, "router rip\n");
596 if (*lan_tx == '0') fprintf(fp, "distribute-list private out %s\n", lan_ifname);
597 if (*lan_rx == '0') fprintf(fp, "distribute-list private in %s\n", lan_ifname);
598 if (*wan_tx == '0') fprintf(fp, "distribute-list private out %s\n", wan_ifname);
599 if (*wan_rx == '0') fprintf(fp, "distribute-list private in %s\n", wan_ifname);
600 fprintf(fp, "access-list private deny any\n");
602 //fprintf(fp, "debug rip events\n");
603 //fprintf(fp, "log file /etc/ripd.log\n");
604 fclose(fp);
607 xstart("zebra", "-d");
608 xstart("ripd", "-d");
609 #endif
612 void stop_zebra(void)
614 #ifdef TCONFIG_ZEBRA
615 killall("zebra", SIGTERM);
616 killall("ripd", SIGTERM);
618 unlink("/etc/zebra.conf");
619 unlink("/etc/ripd.conf");
620 #endif
623 // -----------------------------------------------------------------------------
625 void start_syslog(void)
627 char *argv[16];
628 int argc;
629 char *nv;
630 char *b_opt = "";
631 char rem[256];
632 int n;
633 char s[64];
634 char cfg[256];
635 char *rot_siz = "50";
637 argv[0] = "syslogd";
638 argc = 1;
640 if (nvram_match("log_remote", "1")) {
641 nv = nvram_safe_get("log_remoteip");
642 if (*nv) {
643 snprintf(rem, sizeof(rem), "%s:%s", nv, nvram_safe_get("log_remoteport"));
644 argv[argc++] = "-R";
645 argv[argc++] = rem;
649 if (nvram_match("log_file", "1")) {
650 argv[argc++] = "-L";
652 /* Read options: rotate_size(kb) num_backups logfilename.
653 * Ignore these settings and use defaults if the logfile cannot be written to.
655 if (f_read_string("/etc/syslogd.cfg", cfg, sizeof(cfg)) > 0) {
656 if ((nv = strchr(cfg, '\n')))
657 *nv = 0;
659 if ((nv = strtok(cfg, " \t"))) {
660 if (isdigit(*nv))
661 rot_siz = nv;
664 if ((nv = strtok(NULL, " \t")))
665 b_opt = nv;
667 if ((nv = strtok(NULL, " \t")) && *nv == '/') {
668 if (f_write(nv, cfg, 0, FW_APPEND, 0) >= 0) {
669 argv[argc++] = "-O";
670 argv[argc++] = nv;
672 else {
673 rot_siz = "50";
674 b_opt = "";
679 argv[argc++] = "-s";
680 argv[argc++] = rot_siz;
682 if (isdigit(*b_opt)) {
683 argv[argc++] = "-b";
684 argv[argc++] = b_opt;
688 if (argc > 1) {
689 argv[argc] = NULL;
690 _eval(argv, NULL, 0, NULL);
692 argv[0] = "klogd";
693 argv[1] = NULL;
694 _eval(argv, NULL, 0, NULL);
696 // used to be available in syslogd -m
697 n = nvram_get_int("log_mark");
698 if (n > 0) {
699 // n is in minutes
700 if (n < 60)
701 sprintf(rem, "*/%d * * * *", n);
702 else if (n < 60 * 24)
703 sprintf(rem, "0 */%d * * *", n / 60);
704 else
705 sprintf(rem, "0 0 */%d * *", n / (60 * 24));
706 sprintf(s, "cru a syslogdmark \"%s logger -p syslog.info -- -- MARK --\"", rem);
707 system(s);
709 else {
710 system("cru d syslogdmark");
715 void stop_syslog(void)
717 killall("klogd", SIGTERM);
718 killall("syslogd", SIGTERM);
721 // -----------------------------------------------------------------------------
723 static pid_t pid_igmp = -1;
725 void start_igmp_proxy(void)
727 FILE *fp;
728 char *p;
730 pid_igmp = -1;
731 if (nvram_match("multicast_pass", "1")) {
732 switch (get_wan_proto()) {
733 case WP_DISABLED:
734 return;
735 case WP_PPPOE:
736 case WP_PPTP:
737 case WP_L2TP:
738 p = "wan_iface";
739 break;
740 default:
741 p = "wan_ifname";
742 break;
745 if (f_exists("/etc/igmp.alt")) {
746 eval("igmpproxy", "/etc/igmp.alt");
748 else if ((fp = fopen("/etc/igmp.conf", "w")) != NULL) {
749 fprintf(fp,
750 "quickleave\n"
751 "phyint %s upstream\n"
752 "\taltnet %s\n"
753 "phyint %s downstream ratelimit 0\n",
754 nvram_safe_get(p),
755 nvram_get("multicast_altnet") ? : "0.0.0.0/0",
756 nvram_safe_get("lan_ifname"));
757 fclose(fp);
758 eval("igmpproxy", "/etc/igmp.conf");
760 else {
761 return;
763 if (!nvram_contains_word("debug_norestart", "igmprt")) {
764 pid_igmp = -2;
769 void stop_igmp_proxy(void)
771 pid_igmp = -1;
772 killall_tk("igmpproxy");
776 // -----------------------------------------------------------------------------
778 void set_tz(void)
780 f_write_string("/etc/TZ", nvram_safe_get("tm_tz"), FW_CREATE|FW_NEWLINE, 0644);
783 void start_ntpc(void)
785 set_tz();
787 stop_ntpc();
789 if (nvram_get_int("ntp_updates") >= 0) {
790 xstart("ntpsync", "--init");
794 void stop_ntpc(void)
796 killall("ntpsync", SIGTERM);
799 // -----------------------------------------------------------------------------
801 static void stop_rstats(void)
803 int n;
804 int pid;
806 n = 60;
807 while ((n-- > 0) && ((pid = pidof("rstats")) > 0)) {
808 if (kill(pid, SIGTERM) != 0) break;
809 sleep(1);
813 static void start_rstats(int new)
815 if (nvram_match("rstats_enable", "1")) {
816 stop_rstats();
817 if (new) xstart("rstats", "--new");
818 else xstart("rstats");
822 // -----------------------------------------------------------------------------
824 // !!TB - FTP Server
826 #ifdef TCONFIG_FTP
827 static char *get_full_storage_path(char *val)
829 static char buf[128];
830 int len;
832 if (val[0] == '/')
833 len = sprintf(buf, "%s", val);
834 else
835 len = sprintf(buf, "%s/%s", MOUNT_ROOT, val);
837 if (len > 1 && buf[len - 1] == '/')
838 buf[len - 1] = 0;
840 return buf;
843 static char *nvram_storage_path(char *var)
845 char *val = nvram_safe_get(var);
846 return get_full_storage_path(val);
849 char vsftpd_conf[] = "/etc/vsftpd.conf";
850 char vsftpd_users[] = "/etc/vsftpd.users";
851 char vsftpd_passwd[] = "/etc/vsftpd.passwd";
853 /* VSFTPD code mostly stolen from Oleg's ASUS Custom Firmware GPL sources */
855 static void start_ftpd(void)
857 char tmp[256];
858 FILE *fp, *f;
859 char *buf;
860 char *p, *q;
861 char *user, *pass, *rights;
863 if (getpid() != 1) {
864 start_service("ftpd");
865 return;
868 if (!nvram_get_int("ftp_enable")) return;
870 mkdir_if_none(vsftpd_users);
871 mkdir_if_none("/var/run/vsftpd");
873 if ((fp = fopen(vsftpd_conf, "w")) == NULL)
874 return;
876 if (nvram_get_int("ftp_super"))
878 /* rights */
879 sprintf(tmp, "%s/%s", vsftpd_users, "admin");
880 if ((f = fopen(tmp, "w")))
882 fprintf(f,
883 "dirlist_enable=yes\n"
884 "write_enable=yes\n"
885 "download_enable=yes\n");
886 fclose(f);
890 #ifdef TCONFIG_SAMBASRV
891 if (nvram_match("smbd_cset", "utf8"))
892 fprintf(fp, "utf8=yes\n");
893 #endif
895 if (nvram_invmatch("ftp_anonymous", "0"))
897 fprintf(fp,
898 "anon_allow_writable_root=yes\n"
899 "anon_world_readable_only=no\n"
900 "anon_umask=022\n");
902 /* rights */
903 sprintf(tmp, "%s/ftp", vsftpd_users);
904 if ((f = fopen(tmp, "w")))
906 if (nvram_match("ftp_dirlist", "0"))
907 fprintf(f, "dirlist_enable=yes\n");
908 if (nvram_match("ftp_anonymous", "1") ||
909 nvram_match("ftp_anonymous", "3"))
910 fprintf(f, "write_enable=yes\n");
911 if (nvram_match("ftp_anonymous", "1") ||
912 nvram_match("ftp_anonymous", "2"))
913 fprintf(f, "download_enable=yes\n");
914 fclose(f);
916 if (nvram_match("ftp_anonymous", "1") ||
917 nvram_match("ftp_anonymous", "3"))
918 fprintf(fp,
919 "anon_upload_enable=yes\n"
920 "anon_mkdir_write_enable=yes\n"
921 "anon_other_write_enable=yes\n");
922 } else {
923 fprintf(fp, "anonymous_enable=no\n");
926 fprintf(fp,
927 "dirmessage_enable=yes\n"
928 "download_enable=no\n"
929 "dirlist_enable=no\n"
930 "hide_ids=yes\n"
931 "syslog_enable=yes\n"
932 "local_enable=yes\n"
933 "local_umask=022\n"
934 "chmod_enable=no\n"
935 "chroot_local_user=yes\n"
936 "check_shell=no\n"
937 "log_ftp_protocol=%s\n"
938 "user_config_dir=%s\n"
939 "passwd_file=%s\n"
940 "listen=yes\n"
941 "listen_port=%s\n"
942 "background=yes\n"
943 "isolate=no\n"
944 "max_clients=%d\n"
945 "max_per_ip=%d\n"
946 "idle_session_timeout=%s\n"
947 "use_sendfile=no\n"
948 "anon_max_rate=%d\n"
949 "local_max_rate=%d\n"
950 "%s\n",
951 nvram_get_int("log_ftp") ? "yes" : "no",
952 vsftpd_users, vsftpd_passwd,
953 nvram_get("ftp_port") ? : "21",
954 nvram_get_int("ftp_max"),
955 nvram_get_int("ftp_ipmax"),
956 nvram_get("ftp_staytimeout") ? : "300",
957 nvram_get_int("ftp_anonrate") * 1024,
958 nvram_get_int("ftp_rate") * 1024,
959 nvram_safe_get("ftp_custom"));
961 fclose(fp);
963 /* prepare passwd file and default users */
964 if ((fp = fopen(vsftpd_passwd, "w")) == NULL)
965 return;
967 if (((user = nvram_get("http_username")) == NULL) || (*user == 0)) user = "admin";
968 if (((pass = nvram_get("http_passwd")) == NULL) || (*pass == 0)) pass = "admin";
970 fprintf(fp, /* anonymous, admin, nobody */
971 "ftp:x:0:0:ftp:%s:/sbin/nologin\n"
972 "%s:%s:0:0:root:/:/sbin/nologin\n"
973 "nobody:x:65534:65534:nobody:%s/:/sbin/nologin\n",
974 nvram_storage_path("ftp_anonroot"), user,
975 nvram_get_int("ftp_super") ? crypt(pass, "$1$") : "x",
976 MOUNT_ROOT);
978 if ((buf = strdup(nvram_safe_get("ftp_users"))) != NULL)
981 username<password<rights
982 rights:
983 Read/Write
984 Read Only
985 View Only
986 Private
988 p = buf;
989 while ((q = strsep(&p, ">")) != NULL) {
990 if (vstrsep(q, "<", &user, &pass, &rights) != 3) continue;
991 if (!user || !pass) continue;
993 /* directory */
994 if (strncmp(rights, "Private", 7) == 0)
996 sprintf(tmp, "%s/%s", nvram_storage_path("ftp_pvtroot"), user);
997 mkdir_if_none(tmp);
999 else
1000 sprintf(tmp, "%s", nvram_storage_path("ftp_pubroot"));
1002 fprintf(fp, "%s:%s:0:0:%s:%s:/sbin/nologin\n",
1003 user, crypt(pass, "$1$"), user, tmp);
1005 /* rights */
1006 sprintf(tmp, "%s/%s", vsftpd_users, user);
1007 if ((f = fopen(tmp, "w")))
1009 tmp[0] = 0;
1010 if (nvram_invmatch("ftp_dirlist", "1"))
1011 strcat(tmp, "dirlist_enable=yes\n");
1012 if (strstr(rights, "Read") || !strcmp(rights, "Private"))
1013 strcat(tmp, "download_enable=yes\n");
1014 if (strstr(rights, "Write") || !strncmp(rights, "Private", 7))
1015 strcat(tmp, "write_enable=yes\n");
1017 fputs(tmp, f);
1018 fclose(f);
1021 free(buf);
1024 fclose(fp);
1025 killall("vsftpd", SIGHUP);
1027 /* start vsftpd if it's not already running */
1028 if (pidof("vsftpd") <= 0)
1029 xstart("vsftpd");
1032 static void stop_ftpd(void)
1034 if (getpid() != 1) {
1035 stop_service("ftpd");
1036 return;
1039 killall_tk("vsftpd");
1040 unlink(vsftpd_passwd);
1041 unlink(vsftpd_conf);
1042 eval("rm", "-rf", vsftpd_users);
1044 #endif // TCONFIG_FTP
1046 // -----------------------------------------------------------------------------
1048 // !!TB - Samba
1050 #ifdef TCONFIG_SAMBASRV
1051 static void kill_samba(int sig)
1053 if (sig == SIGTERM) {
1054 killall_tk("smbd");
1055 killall_tk("nmbd");
1057 else {
1058 killall("smbd", sig);
1059 killall("nmbd", sig);
1063 static void start_samba(void)
1065 FILE *fp;
1066 DIR *dir = NULL;
1067 struct dirent *dp;
1068 char nlsmod[15];
1069 int mode;
1070 char *nv;
1072 if (getpid() != 1) {
1073 start_service("smbd");
1074 return;
1077 mode = nvram_get_int("smbd_enable");
1078 if (!mode || !nvram_invmatch("lan_hostname", ""))
1079 return;
1081 if ((fp = fopen("/etc/smb.conf", "w")) == NULL)
1082 return;
1084 fprintf(fp, "[global]\n"
1085 " interfaces = %s\n"
1086 " bind interfaces only = yes\n"
1087 " workgroup = %s\n"
1088 " netbios name = %s\n"
1089 " server string = %s\n"
1090 " guest account = nobody\n"
1091 " security = user\n"
1092 " %s\n"
1093 " guest ok = %s\n"
1094 " guest only = no\n"
1095 " browseable = yes\n"
1096 " syslog only = yes\n"
1097 " timestamp logs = no\n"
1098 " syslog = 1\n"
1099 " encrypt passwords = yes\n"
1100 #if defined(LINUX26) && defined(TCONFIG_SAMBA3)
1101 " use sendfile = yes\n"
1102 #endif
1103 " preserve case = yes\n"
1104 " short preserve case = yes\n",
1105 nvram_safe_get("lan_ifname"),
1106 nvram_get("smbd_wgroup") ? : "WORKGROUP",
1107 nvram_safe_get("lan_hostname"),
1108 nvram_get("router_name") ? : "Tomato",
1109 mode == 2 ? "" : "map to guest = Bad User",
1110 mode == 2 ? "no" : "yes" // guest ok
1113 if (nvram_get_int("smbd_wins")) {
1114 nv = nvram_safe_get("wan_wins");
1115 if ((*nv == 0) || (strcmp(nv, "0.0.0.0") == 0)) {
1116 fprintf(fp, " wins support = yes\n");
1120 if (nvram_get_int("smbd_master")) {
1121 fprintf(fp,
1122 " domain master = yes\n"
1123 " local master = yes\n"
1124 " preferred master = yes\n"
1125 " os level = 65\n");
1128 nv = nvram_safe_get("smbd_cpage");
1129 if (*nv) {
1130 #ifndef TCONFIG_SAMBA3
1131 fprintf(fp, " client code page = %s\n", nv);
1132 #endif
1133 sprintf(nlsmod, "nls_cp%s", nv);
1135 nv = nvram_safe_get("smbd_nlsmod");
1136 if ((*nv) && (strcmp(nv, nlsmod) != 0))
1137 modprobe_r(nv);
1139 modprobe(nlsmod);
1140 nvram_set("smbd_nlsmod", nlsmod);
1143 #ifndef TCONFIG_SAMBA3
1144 if (nvram_match("smbd_cset", "utf8"))
1145 fprintf(fp, " coding system = utf8\n");
1146 else if (nvram_invmatch("smbd_cset", ""))
1147 fprintf(fp, " character set = %s\n", nvram_safe_get("smbd_cset"));
1148 #endif
1150 nv = nvram_safe_get("smbd_custom");
1151 /* add socket options unless overriden by the user */
1152 if (strstr(nv, "socket options") == NULL) {
1153 fprintf(fp, " socket options = TCP_NODELAY SO_KEEPALIVE IPTOS_LOWDELAY SO_RCVBUF=16384 SO_SNDBUF=16384\n");
1155 fprintf(fp, "%s\n\n", nv);
1157 /* configure shares */
1159 char *buf;
1160 char *p, *q;
1161 char *name, *path, *comment, *writeable, *hidden;
1162 int cnt = 0;
1164 if ((buf = strdup(nvram_safe_get("smbd_shares"))) != NULL)
1166 /* sharename<path<comment<writeable[0|1]<hidden[0|1] */
1168 p = buf;
1169 while ((q = strsep(&p, ">")) != NULL) {
1170 if (vstrsep(q, "<", &name, &path, &comment, &writeable, &hidden) != 5) continue;
1171 if (!path || !name) continue;
1173 /* share name */
1174 fprintf(fp, "\n[%s]\n", name);
1176 /* path */
1177 fprintf(fp, " path = %s\n", path);
1179 /* access level */
1180 if (!strcmp(writeable, "1"))
1181 fprintf(fp, " writable = yes\n delete readonly = yes\n force user = root\n");
1182 if (!strcmp(hidden, "1"))
1183 fprintf(fp, " browseable = no\n");
1185 /* comment */
1186 if (comment)
1187 fprintf(fp, " comment = %s\n", comment);
1189 cnt++;
1191 free(buf);
1194 /* Share every mountpoint below MOUNT_ROOT */
1195 if (nvram_get_int("smbd_autoshare") && (dir = opendir(MOUNT_ROOT))) {
1196 while ((dp = readdir(dir))) {
1197 if (strcmp(dp->d_name, ".") && strcmp(dp->d_name, "..")) {
1199 char path[256];
1200 struct stat sb;
1201 int thisdev;
1203 /* Only if is a directory and is mounted */
1204 sprintf(path, "%s/%s", MOUNT_ROOT, dp->d_name);
1205 sb.st_mode = S_IFDIR; /* failsafe */
1206 stat(path, &sb);
1207 if (!S_ISDIR(sb.st_mode))
1208 continue;
1210 /* If this dir & its parent dir are on the same device, it is not a mountpoint */
1211 strcat(path, "/.");
1212 stat(path, &sb);
1213 thisdev = sb.st_dev;
1214 strcat(path, ".");
1215 ++sb.st_dev; /* failsafe */
1216 stat(path, &sb);
1217 if (thisdev == sb.st_dev)
1218 continue;
1220 /* smbd_autoshare: 0 - disable, 1 - read-only, 2 - writable, 3 - hidden writable */
1221 fprintf(fp, "\n[%s]\n path = %s/%s\n comment = %s\n",
1222 dp->d_name, MOUNT_ROOT, dp->d_name, dp->d_name);
1223 if (nvram_match("smbd_autoshare", "3")) // Hidden
1224 fprintf(fp, "\n[%s$]\n path = %s/%s\n browseable = no\n",
1225 dp->d_name, MOUNT_ROOT, dp->d_name);
1226 if (nvram_match("smbd_autoshare", "2") || nvram_match("smbd_autoshare", "3")) // RW
1227 fprintf(fp, " writable = yes\n delete readonly = yes\n force user = root\n");
1229 cnt++;
1233 if (dir) closedir(dir);
1235 if (cnt == 0) {
1236 /* by default share MOUNT_ROOT as read-only */
1237 fprintf(fp, "\n[share]\n"
1238 " path = %s\n"
1239 " writable = no\n",
1240 MOUNT_ROOT);
1243 fclose(fp);
1245 mkdir_if_none("/var/run/samba");
1246 mkdir_if_none("/etc/samba");
1248 /* write smbpasswd */
1249 #ifdef TCONFIG_SAMBA3
1250 eval("smbpasswd", "nobody", "\"\"");
1251 #else
1252 eval("smbpasswd", "-a", "nobody", "\"\"");
1253 #endif
1254 if (mode == 2) {
1255 char *smbd_user;
1256 if (((smbd_user = nvram_get("smbd_user")) == NULL) || (*smbd_user == 0) || !strcmp(smbd_user, "root"))
1257 smbd_user = "nas";
1258 #ifdef TCONFIG_SAMBA3
1259 eval("smbpasswd", smbd_user, nvram_safe_get("smbd_passwd"));
1260 #else
1261 eval("smbpasswd", "-a", smbd_user, nvram_safe_get("smbd_passwd"));
1262 #endif
1265 kill_samba(SIGHUP);
1266 int ret1 = 0, ret2 = 0;
1267 /* start samba if it's not already running */
1268 if (pidof("nmbd") <= 0)
1269 ret1 = xstart("nmbd", "-D");
1270 if (pidof("smbd") <= 0)
1271 ret2 = xstart("smbd", "-D");
1273 if (ret1 || ret2) kill_samba(SIGTERM);
1276 static void stop_samba(void)
1278 if (getpid() != 1) {
1279 stop_service("smbd");
1280 return;
1283 kill_samba(SIGTERM);
1284 /* clean up */
1285 unlink("/var/log/smb");
1286 unlink("/var/log/nmb");
1287 eval("rm", "-rf", "/var/run/samba");
1289 #endif // TCONFIG_SAMBASRV
1291 #ifdef TCONFIG_MEDIA_SERVER
1292 #define MEDIA_SERVER_APP "minidlna"
1294 static void start_media_server(void)
1296 FILE *f;
1297 int port, pid, https;
1298 char *dbdir;
1299 char *argv[] = { MEDIA_SERVER_APP, "-f", "/etc/"MEDIA_SERVER_APP".conf", "-R", NULL };
1300 static int once = 1;
1302 if (getpid() != 1) {
1303 start_service("media");
1304 return;
1307 if (nvram_get_int("ms_sas") == 0)
1308 once = 0;
1310 if (nvram_get_int("ms_enable") != 0) {
1311 if ((!once) && (nvram_get_int("ms_rescan") == 0)) {
1312 // no forced rescan
1313 argv[3] = NULL;
1315 nvram_unset("ms_rescan");
1317 if (f_exists("/etc/"MEDIA_SERVER_APP".alt")) {
1318 argv[2] = "/etc/"MEDIA_SERVER_APP".alt";
1320 else {
1321 if ((f = fopen(argv[2], "w")) != NULL) {
1322 port = nvram_get_int("ms_port");
1323 https = nvram_get_int("https_enable");
1324 dbdir = nvram_safe_get("ms_dbdir");
1325 if (!(*dbdir)) dbdir = NULL;
1326 mkdir_if_none(dbdir ? : "/var/run/"MEDIA_SERVER_APP);
1328 fprintf(f,
1329 "network_interface=%s\n"
1330 "port=%d\n"
1331 "friendly_name=%s\n"
1332 "db_dir=%s/.db\n"
1333 "enable_tivo=%s\n"
1334 "strict_dlna=%s\n"
1335 "presentation_url=http%s://%s:%s/nas-media.asp\n"
1336 "inotify=yes\n"
1337 "notify_interval=600\n"
1338 "album_art_names=Cover.jpg/cover.jpg/Thumb.jpg/thumb.jpg\n"
1339 "\n",
1340 nvram_safe_get("lan_ifname"),
1341 (port < 0) || (port >= 0xffff) ? 0 : port,
1342 nvram_get("router_name") ? : "Tomato",
1343 dbdir ? : "/var/run/"MEDIA_SERVER_APP,
1344 nvram_get_int("ms_tivo") ? "yes" : "no",
1345 nvram_get_int("ms_stdlna") ? "yes" : "no",
1346 https ? "s" : "", nvram_safe_get("lan_ipaddr"), nvram_safe_get(https ? "https_lanport" : "http_lanport")
1349 // media directories
1350 char *buf, *p, *q;
1351 char *path, *restrict;
1353 if ((buf = strdup(nvram_safe_get("ms_dirs"))) != NULL) {
1354 /* path<restrict[A|V|P|] */
1356 p = buf;
1357 while ((q = strsep(&p, ">")) != NULL) {
1358 if (vstrsep(q, "<", &path, &restrict) < 1 || !path || !(*path))
1359 continue;
1360 fprintf(f, "media_dir=%s%s%s\n",
1361 restrict ? : "", (restrict && *restrict) ? "," : "", path);
1363 free(buf);
1366 fclose(f);
1370 /* start media server if it's not already running */
1371 if (pidof(MEDIA_SERVER_APP) <= 0) {
1372 if ((_eval(argv, NULL, 0, &pid) == 0) && (once)) {
1373 /* If we started the media server successfully, wait 1 sec
1374 * to let it die if it can't open the database file.
1375 * If it's still alive after that, assume it's running and
1376 * disable forced once-after-reboot rescan.
1378 sleep(1);
1379 if (pidof(MEDIA_SERVER_APP) > 0)
1380 once = 0;
1386 static void stop_media_server(void)
1388 if (getpid() != 1) {
1389 stop_service("media");
1390 return;
1393 killall_tk(MEDIA_SERVER_APP);
1395 #endif // TCONFIG_MEDIA_SERVER
1397 #ifdef TCONFIG_USB
1398 static void start_nas_services(void)
1400 if (getpid() != 1) {
1401 start_service("usbapps");
1402 return;
1405 #ifdef TCONFIG_SAMBASRV
1406 start_samba();
1407 #endif
1408 #ifdef TCONFIG_FTP
1409 start_ftpd();
1410 #endif
1411 #ifdef TCONFIG_MEDIA_SERVER
1412 start_media_server();
1413 #endif
1416 static void stop_nas_services(void)
1418 if (getpid() != 1) {
1419 stop_service("usbapps");
1420 return;
1423 #ifdef TCONFIG_MEDIA_SERVER
1424 stop_media_server();
1425 #endif
1426 #ifdef TCONFIG_FTP
1427 stop_ftpd();
1428 #endif
1429 #ifdef TCONFIG_SAMBASRV
1430 stop_samba();
1431 #endif
1434 void restart_nas_services(int stop, int start)
1436 int fd = file_lock("usb");
1437 /* restart all NAS applications */
1438 if (stop)
1439 stop_nas_services();
1440 if (start)
1441 start_nas_services();
1442 file_unlock(fd);
1444 #endif // TCONFIG_USB
1446 // -----------------------------------------------------------------------------
1448 /* -1 = Don't check for this program, it is not expected to be running.
1449 * Other = This program has been started and should be kept running. If no
1450 * process with the name is running, call func to restart it.
1451 * Note: At startup, dnsmasq forks a short-lived child which forks a
1452 * long-lived (grand)child. The parents terminate.
1453 * Many daemons use this technique.
1455 static void _check(pid_t pid, const char *name, void (*func)(void))
1457 if (pid == -1) return;
1459 if (pidof(name) > 0) return;
1461 syslog(LOG_DEBUG, "%s terminated unexpectedly, restarting.\n", name);
1462 func();
1464 // Force recheck in 500 msec
1465 setitimer(ITIMER_REAL, &pop_tv, NULL);
1468 void check_services(void)
1470 TRACE_PT("keep alive\n");
1472 // Periodically reap any zombies
1473 setitimer(ITIMER_REAL, &zombie_tv, NULL);
1475 #ifdef LINUX26
1476 _check(pid_hotplug2, "hotplug2", start_hotplug2);
1477 #endif
1478 _check(pid_dnsmasq, "dnsmasq", start_dnsmasq);
1479 _check(pid_crond, "crond", start_cron);
1480 _check(pid_igmp, "igmpproxy", start_igmp_proxy);
1483 // -----------------------------------------------------------------------------
1485 void start_services(void)
1487 static int once = 1;
1489 if (once) {
1490 once = 0;
1492 if (nvram_get_int("telnetd_eas")) start_telnetd();
1493 if (nvram_get_int("sshd_eas")) start_sshd();
1496 // start_syslog();
1497 start_nas();
1498 start_zebra();
1499 start_dnsmasq();
1500 start_cifs();
1501 start_httpd();
1502 start_cron();
1503 // start_upnp();
1504 start_rstats(0);
1505 start_sched();
1506 restart_nas_services(1, 1); // !!TB - Samba, FTP and Media Server
1509 void stop_services(void)
1511 clear_resolv();
1513 restart_nas_services(1, 0); // stop Samba, FTP and Media Server
1514 stop_sched();
1515 stop_rstats();
1516 // stop_upnp();
1517 stop_cron();
1518 stop_httpd();
1519 stop_cifs();
1520 stop_dnsmasq();
1521 stop_zebra();
1522 stop_nas();
1523 // stop_syslog();
1526 // -----------------------------------------------------------------------------
1528 /* nvram "action_service" is: "service-action[-modifier]"
1529 * action is something like "stop" or "start" or "restart"
1530 * optional modifier is "c" for the "service" command-line command
1532 void exec_service(void)
1534 const int A_START = 1;
1535 const int A_STOP = 2;
1536 const int A_RESTART = 1|2;
1537 char buffer[128];
1538 char *service;
1539 char *act;
1540 char *next;
1541 char *modifier;
1542 int action, user;
1543 int i;
1545 strlcpy(buffer, nvram_safe_get("action_service"), sizeof(buffer));
1546 next = buffer;
1548 TOP:
1549 act = strsep(&next, ",");
1550 service = strsep(&act, "-");
1551 if (act == NULL) {
1552 next = NULL;
1553 goto CLEAR;
1555 modifier = act;
1556 strsep(&modifier, "-");
1558 TRACE_PT("service=%s action=%s modifier=%s\n", service, act, modifier ? : "");
1560 if (strcmp(act, "start") == 0) action = A_START;
1561 else if (strcmp(act, "stop") == 0) action = A_STOP;
1562 else if (strcmp(act, "restart") == 0) action = A_RESTART;
1563 else action = 0;
1564 user = (modifier != NULL && *modifier == 'c');
1566 if (strcmp(service, "dhcpc") == 0) {
1567 if (action & A_STOP) stop_dhcpc();
1568 if (action & A_START) start_dhcpc();
1569 goto CLEAR;
1572 if ((strcmp(service, "dhcpd") == 0) || (strcmp(service, "dns") == 0) || (strcmp(service, "dnsmasq") == 0)) {
1573 if (action & A_STOP) stop_dnsmasq();
1574 if (action & A_START) {
1575 dns_to_resolv();
1576 start_dnsmasq();
1578 goto CLEAR;
1581 if (strcmp(service, "firewall") == 0) {
1582 if (action & A_STOP) {
1583 stop_firewall();
1584 stop_igmp_proxy();
1586 if (action & A_START) {
1587 start_firewall();
1588 start_igmp_proxy();
1590 goto CLEAR;
1593 if (strcmp(service, "restrict") == 0) {
1594 if (action & A_STOP) {
1595 stop_firewall();
1597 if (action & A_START) {
1598 i = nvram_get_int("rrules_radio"); // -1 = not used, 0 = enabled by rule, 1 = disabled by rule
1600 start_firewall();
1602 // if radio was disabled by access restriction, but no rule is handling it now, enable it
1603 if (i == 1) {
1604 if (nvram_get_int("rrules_radio") < 0) {
1605 eval("radio", "on");
1609 goto CLEAR;
1612 if (strcmp(service, "qos") == 0) {
1613 if (action & A_STOP) {
1614 stop_qos();
1616 stop_firewall(); start_firewall(); // always restarted
1617 if (action & A_START) {
1618 start_qos();
1619 if (nvram_match("qos_reset", "1")) f_write_string("/proc/net/clear_marks", "1", 0, 0);
1621 goto CLEAR;
1625 if (strcmp(service, "qoslimit") == 0) {
1626 if (action & A_STOP) {
1627 new_qoslimit_stop();
1629 stop_firewall(); start_firewall(); // always restarted
1630 if (action & A_START) {
1631 new_qoslimit_start();
1633 goto CLEAR;
1636 if (strcmp(service, "arpbind") == 0) {
1637 if (action & A_STOP) new_arpbind_stop();
1638 if (action & A_START) new_arpbind_start();
1639 goto CLEAR;
1643 if (strcmp(service, "upnp") == 0) {
1644 if (action & A_STOP) {
1645 stop_upnp();
1647 stop_firewall(); start_firewall(); // always restarted
1648 if (action & A_START) {
1649 start_upnp();
1651 goto CLEAR;
1654 if (strcmp(service, "telnetd") == 0) {
1655 if (action & A_STOP) stop_telnetd();
1656 if (action & A_START) start_telnetd();
1657 goto CLEAR;
1660 if (strcmp(service, "sshd") == 0) {
1661 if (action & A_STOP) stop_sshd();
1662 if (action & A_START) start_sshd();
1663 goto CLEAR;
1666 if (strcmp(service, "httpd") == 0) {
1667 if (action & A_STOP) stop_httpd();
1668 if (action & A_START) start_httpd();
1669 goto CLEAR;
1672 if (strcmp(service, "admin") == 0) {
1673 if (action & A_STOP) {
1674 stop_sshd();
1675 stop_telnetd();
1676 stop_httpd();
1678 stop_firewall(); start_firewall(); // always restarted
1679 if (action & A_START) {
1680 start_httpd();
1681 create_passwd();
1682 if (nvram_match("telnetd_eas", "1")) start_telnetd();
1683 if (nvram_match("sshd_eas", "1")) start_sshd();
1685 goto CLEAR;
1688 if (strcmp(service, "ddns") == 0) {
1689 if (action & A_STOP) stop_ddns();
1690 if (action & A_START) start_ddns();
1691 goto CLEAR;
1694 if (strcmp(service, "ntpc") == 0) {
1695 if (action & A_STOP) stop_ntpc();
1696 if (action & A_START) start_ntpc();
1697 goto CLEAR;
1700 if (strcmp(service, "logging") == 0) {
1701 if (action & A_STOP) {
1702 stop_syslog();
1704 if (!user) {
1705 // always restarted except from "service" command
1706 stop_cron(); start_cron();
1707 stop_firewall(); start_firewall();
1709 if (action & A_START) {
1710 start_syslog();
1712 goto CLEAR;
1715 if (strcmp(service, "crond") == 0) {
1716 if (action & A_STOP) {
1717 stop_cron();
1719 if (action & A_START) {
1720 start_cron();
1722 goto CLEAR;
1725 #ifdef LINUX26
1726 if (strncmp(service, "hotplug", 7) == 0) {
1727 if (action & A_STOP) {
1728 stop_hotplug2();
1730 if (action & A_START) {
1731 start_hotplug2(1);
1733 goto CLEAR;
1735 #endif
1737 if (strcmp(service, "upgrade") == 0) {
1738 if (action & A_START) {
1739 #if TOMATO_SL
1740 stop_usbevent();
1741 stop_smbd();
1742 #endif
1743 restart_nas_services(1, 0); // stop Samba, FTP and Media Server
1744 stop_jffs2();
1745 // stop_cifs();
1746 stop_zebra();
1747 stop_cron();
1748 stop_ntpc();
1749 stop_upnp();
1750 // stop_dhcpc();
1751 killall("rstats", SIGTERM);
1752 killall("buttons", SIGTERM);
1753 stop_syslog();
1754 remove_storage_main(1); // !!TB - USB Support
1755 stop_usb(); // !!TB - USB Support
1757 goto CLEAR;
1760 #ifdef TCONFIG_CIFS
1761 if (strcmp(service, "cifs") == 0) {
1762 if (action & A_STOP) stop_cifs();
1763 if (action & A_START) start_cifs();
1764 goto CLEAR;
1766 #endif
1768 #ifdef TCONFIG_JFFS2
1769 if (strncmp(service, "jffs", 4) == 0) {
1770 if (action & A_STOP) stop_jffs2();
1771 if (action & A_START) start_jffs2();
1772 goto CLEAR;
1774 #endif
1776 if (strcmp(service, "routing") == 0) {
1777 if (action & A_STOP) {
1778 stop_zebra();
1779 do_static_routes(0); // remove old '_saved'
1780 eval("brctl", "stp", nvram_safe_get("lan_ifname"), "0");
1782 stop_firewall();
1783 start_firewall();
1784 if (action & A_START) {
1785 do_static_routes(1); // add new
1786 start_zebra();
1787 eval("brctl", "stp", nvram_safe_get("lan_ifname"), nvram_safe_get("lan_stp"));
1789 goto CLEAR;
1792 if (strcmp(service, "ctnf") == 0) {
1793 if (action & A_START) {
1794 setup_conntrack();
1795 stop_firewall();
1796 start_firewall();
1798 goto CLEAR;
1801 if (strcmp(service, "wan") == 0) {
1802 if (action & A_STOP) {
1803 if (get_wan_proto() == WP_PPPOE) {
1804 stop_dnsmasq();
1805 stop_redial();
1806 stop_singe_pppoe(PPPOE0);
1807 if (((action & A_START) == 0) && (nvram_match("ppp_demand", "1"))) {
1808 sleep(1);
1809 start_pppoe(PPPOE0);
1811 start_dnsmasq();
1813 else {
1814 stop_wan();
1818 if (action & A_START) {
1819 rename("/tmp/ppp/log", "/tmp/ppp/log.~");
1821 if (get_wan_proto() == WP_PPPOE) {
1822 stop_singe_pppoe(PPPOE0);
1823 start_pppoe(PPPOE0);
1824 if (nvram_invmatch("ppp_demand", "1")) {
1825 start_redial();
1828 else {
1829 start_wan(BOOT);
1831 sleep(2);
1832 force_to_dial();
1834 goto CLEAR;
1837 if (strcmp(service, "net") == 0) {
1838 if (action & A_STOP) {
1839 stop_dnsmasq();
1840 stop_nas();
1841 stop_wan();
1842 stop_lan();
1843 stop_vlan();
1845 if (action & A_START) {
1846 start_vlan();
1847 start_lan();
1848 start_wan(BOOT);
1849 start_nas();
1850 start_dnsmasq();
1851 start_wl();
1853 goto CLEAR;
1856 if (strcmp(service, "nas") == 0) {
1857 if (action & A_STOP) {
1858 stop_nas();
1860 if (action & A_START) {
1861 start_nas();
1862 start_wl();
1864 goto CLEAR;
1867 if (strcmp(service, "rstats") == 0) {
1868 if (action & A_STOP) stop_rstats();
1869 if (action & A_START) start_rstats(0);
1870 goto CLEAR;
1873 if (strcmp(service, "rstatsnew") == 0) {
1874 if (action & A_STOP) stop_rstats();
1875 if (action & A_START) start_rstats(1);
1876 goto CLEAR;
1879 if (strcmp(service, "sched") == 0) {
1880 if (action & A_STOP) stop_sched();
1881 if (action & A_START) start_sched();
1882 goto CLEAR;
1885 #ifdef TCONFIG_USB
1886 // !!TB - USB Support
1887 if (strcmp(service, "usb") == 0) {
1888 if (action & A_STOP) stop_usb();
1889 if (action & A_START) {
1890 start_usb();
1891 // restart Samba and ftp since they may be killed by stop_usb()
1892 restart_nas_services(0, 1);
1893 // remount all partitions by simulating hotplug event
1894 add_remove_usbhost("-1", 1);
1896 goto CLEAR;
1899 if (strcmp(service, "usbapps") == 0) {
1900 if (action & A_STOP) stop_nas_services();
1901 if (action & A_START) start_nas_services();
1902 goto CLEAR;
1904 #endif
1906 #ifdef TCONFIG_FTP
1907 // !!TB - FTP Server
1908 if (strcmp(service, "ftpd") == 0) {
1909 if (action & A_STOP) stop_ftpd();
1910 setup_conntrack();
1911 stop_firewall();
1912 start_firewall();
1913 if (action & A_START) start_ftpd();
1914 goto CLEAR;
1916 #endif
1918 #ifdef TCONFIG_MEDIA_SERVER
1919 if (strcmp(service, "media") == 0 || strcmp(service, "dlna") == 0) {
1920 if (action & A_STOP) stop_media_server();
1921 if (action & A_START) start_media_server();
1922 goto CLEAR;
1924 #endif
1926 #ifdef TCONFIG_SAMBASRV
1927 // !!TB - Samba
1928 if (strcmp(service, "samba") == 0 || strcmp(service, "smbd") == 0) {
1929 if (action & A_STOP) stop_samba();
1930 if (action & A_START) {
1931 create_passwd();
1932 stop_dnsmasq();
1933 start_dnsmasq();
1934 start_samba();
1936 goto CLEAR;
1938 #endif
1940 #ifdef TCONFIG_OPENVPN
1941 if (strncmp(service, "vpnclient", 9) == 0) {
1942 if (action & A_STOP) stop_vpnclient(atoi(&service[9]));
1943 if (action & A_START) start_vpnclient(atoi(&service[9]));
1944 goto CLEAR;
1947 if (strncmp(service, "vpnserver", 9) == 0) {
1948 if (action & A_STOP) stop_vpnserver(atoi(&service[9]));
1949 if (action & A_START) start_vpnserver(atoi(&service[9]));
1950 goto CLEAR;
1952 #endif
1954 CLEAR:
1955 if (next) goto TOP;
1957 // some functions check action_service and must be cleared at end -- zzz
1958 nvram_set("action_service", "");
1960 // Force recheck in 500 msec
1961 setitimer(ITIMER_REAL, &pop_tv, NULL);
1964 static void do_service(const char *name, const char *action, int user)
1966 int n;
1967 char s[64];
1969 n = 150;
1970 while (!nvram_match("action_service", "")) {
1971 if (user) {
1972 putchar('*');
1973 fflush(stdout);
1975 else if (--n < 0) break;
1976 usleep(100 * 1000);
1979 snprintf(s, sizeof(s), "%s-%s%s", name, action, (user ? "-c" : ""));
1980 nvram_set("action_service", s);
1981 kill(1, SIGUSR1);
1983 n = 150;
1984 while (nvram_match("action_service", s)) {
1985 if (user) {
1986 putchar('.');
1987 fflush(stdout);
1989 else if (--n < 0) {
1990 break;
1992 usleep(100 * 1000);
1996 int service_main(int argc, char *argv[])
1998 if (argc != 3) usage_exit(argv[0], "<service> <action>");
1999 do_service(argv[1], argv[2], 1);
2000 printf("\nDone.\n");
2001 return 0;
2004 void start_service(const char *name)
2006 do_service(name, "start", 0);
2009 void stop_service(const char *name)
2011 do_service(name, "stop", 0);
2015 void restart_service(const char *name)
2017 do_service(name, "restart", 0);