2 * Copyright (C) 1995, 1997-1999 Jeffrey A. Uphoff
3 * Modified by Olaf Kirch, Oct. 1996.
4 * Modified by H.J. Lu, 1998.
5 * Modified by L. Hohberger of Mission Critical Linux, 2000.
17 #include <rpc/pmap_clnt.h>
22 /* Socket operations */
23 #include <sys/types.h>
24 #include <sys/socket.h>
27 short int restart = 0;
28 int run_mode = 0; /* foreground logging mode */
30 /* LH - I had these local to main, but it seemed silly to have
31 * two copies of each - one in main(), one static in log.c...
32 * It also eliminates the 256-char static in log.c */
34 char *version_p = NULL;
36 static struct option longopts[] =
38 { "foreground", 0, 0, 'F' },
39 { "no-syslog", 0, 0, 'd' },
40 { "help", 0, 0, 'h' },
41 { "version", 0, 0, 'v' },
42 { "outgoing-port", 1, 0, 'o' },
43 { "port", 1, 0, 'p' },
47 extern void sm_prog_1 (struct svc_req *, register SVCXPRT *);
48 extern int statd_get_socket(int port);
51 extern void simulator (int, char **);
55 #ifdef HAVE_TCP_WRAPPER
56 #include "tcpwrapper.h"
59 sm_prog_1_wrapper (struct svc_req *rqstp, register SVCXPRT *transp)
61 /* remote host authorization check */
62 if (!check_default("statd", svc_getcaller(transp),
63 rqstp->rq_proc, SM_PROG)) {
64 svcerr_auth (transp, AUTH_FAILED);
68 sm_prog_1 (rqstp, transp);
71 #define sm_prog_1 sm_prog_1_wrapper
80 log (L_FATAL, "Caught signal %d, un-registering and exiting.", sig);
81 pmap_unset (SM_PROG, SM_VERS);
86 * Startup information.
88 static void log_modes(void)
90 char buf[128]; /* watch stack size... */
92 /* No flags = no message */
93 if (!run_mode) return;
96 sprintf(buf,"Flags: ");
97 if (run_mode & MODE_NODAEMON)
98 strcat(buf,"No-Daemon ");
99 if (run_mode & MODE_LOG_STDERR)
100 strcat(buf,"Log-STDERR ");
101 /* future: IP aliasing
102 if (run_mode & MODE_NOTIFY_ONLY)
104 strcat(buf,"Notify-Only ");
107 /* future: IP aliasing
108 if (run_mode & MODE_NOTIFY_ONLY)
110 dprintf(L_DEBUG,"Notify IP: %s",svr_addr);
115 * Since we do more than standard statd stuff, we might need to
116 * help the occasional admin.
121 fprintf(stderr,"usage: %s [options]\n", name_p);
122 fprintf(stderr," -h, -?, --help Print this help screen.\n");
123 fprintf(stderr," -F, --foreground Foreground (no-daemon mode)\n");
124 fprintf(stderr," -d, --no-syslog Verbose logging to stderr. Foreground mode only.\n");
125 fprintf(stderr," -p, --port Port to listen on\n");
126 fprintf(stderr," -o, --outgoing-port Port for outgoing connections\n");
127 fprintf(stderr," -V, -v, --version Display version information and exit.\n");
131 * Entry routine/main loop.
133 int main (int argc, char **argv)
138 int port = 0, out_port = 0;
140 /* Default: daemon mode, no other options */
143 /* Set the basename */
144 if ((name_p = strrchr(argv[0],'/')) != NULL) {
150 /* Get the version */
151 if ((version_p = strrchr(VERSION,' ')) != NULL) {
157 /* Process command line switches */
158 while ((arg = getopt_long(argc, argv, "h?vVFdp:o:", longopts, NULL)) != EOF) {
160 case 'V': /* Version */
162 printf("%s version %s\n",name_p,version_p);
164 case 'F': /* Foreground/nodaemon mode */
165 run_mode |= MODE_NODAEMON;
167 case 'd': /* No daemon only - log to stderr */
168 run_mode |= MODE_LOG_STDERR;
171 out_port = atoi(optarg);
172 if (out_port < 1 || out_port > 65535) {
173 fprintf(stderr, "%s: bad port number: %s\n",
181 if (port < 1 || port > 65535) {
182 fprintf(stderr, "%s: bad port number: %s\n",
188 case '?': /* heeeeeelllllllpppp? heh */
192 default: /* oh dear ... heh */
198 if (port == out_port && port != 0) {
199 fprintf(stderr, "Listening and outgoing ports cannot be the same!\n");
203 if (!(run_mode & MODE_NODAEMON)) {
204 run_mode &= ~MODE_LOG_STDERR; /* Never log to console in
208 log_init (name_p,version_p);
214 /* LH - I _really_ need to update simulator... */
215 simulator (--argc, ++argv); /* simulator() does exit() */
218 if (!(run_mode & MODE_NODAEMON)) {
221 if ((pid = fork ()) < 0) {
222 perror ("Could not fork");
224 } else if (pid != 0) {
232 for (filedes = 0; filedes < sysconf (_SC_OPEN_MAX); filedes++) {
238 signal (SIGHUP, killer);
239 signal (SIGINT, killer);
240 signal (SIGTERM, killer);
241 /* WARNING: the following works on Linux and SysV, but not BSD! */
242 signal(SIGCHLD, SIG_IGN);
244 /* initialize out_port */
245 statd_get_socket(out_port);
248 pmap_unset (SM_PROG, SM_VERS);
250 shuffle_dirs (); /* Move directory names around */
251 notify_hosts (); /* Send out notify requests */
254 /* future: IP aliasing
255 if (!(run_mode & MODE_NOTIFY_ONLY)) {
256 rpc_init("statd", SM_PROG, SM_VERS, sm_prog_1, port);
258 /* this registers both UDP and TCP services */
259 rpc_init("statd", SM_PROG, SM_VERS, sm_prog_1, port);
262 * Handle incoming requests: SM_NOTIFY socket requests, as
263 * well as callbacks from lockd.
265 my_svc_run(); /* I rolled my own, Olaf made it better... */