示例#1
0
文件: loghelpers.c 项目: raorn/wdm
void WDMRedirectStderr(int level)
{
    int errpipe[2];
    int exitstatus;

    if (pipe(errpipe) == -1)
        WDMError("cannot create pipe. " "all stderr messages will go to stderr\n");

    childpid = fork();
    if (childpid == -1) {
        WDMError("fork failed. " "all stderr messages will go to stderr\n");
        close(errpipe[0]);
        close(errpipe[1]);
    } else if (childpid != 0) {
        /* parent, will read all messages from stderr and
         * redirect it to log */
        Signal(SIGTERM, WDMRedirectSignals);
        Signal(SIGINT, WDMRedirectSignals);
        Signal(SIGHUP, WDMRedirectSignals);
        close(errpipe[1]);
        exitstatus = WDMRedirectFileToLog(WDM_LEVEL_ERROR, childpid, errpipe[0]);
        close(errpipe[0]);
        exit(exitstatus);
    }

    /* child, will close read end of pipe and dup2
     * write end of pipe to stderr */
    close(errpipe[0]);
    RegisterCloseOnFork(errpipe[1]);
    dup2(errpipe[1], 2);
}
示例#2
0
文件: dm.c 项目: bbidulock/wdm
static int StorePid(void)
{
	int oldpid;

	if (pidFile[0] != '\0') {
		pidFd = open(pidFile, O_RDWR);
		if (pidFd == -1 && errno == ENOENT)
			pidFd = open(pidFile, O_RDWR | O_CREAT, 0666);
		if (pidFd == -1 || !(pidFilePtr = fdopen(pidFd, "r+"))) {
			WDMError("process-id file %s cannot be opened\n", pidFile);
			return -1;
		}
		if (fscanf(pidFilePtr, "%d\n", &oldpid) != 1)
			oldpid = -1;
		fseek(pidFilePtr, 0l, 0);
		if (lockPidFile.i) {
#ifdef F_SETLK
#ifndef SEEK_SET
#define SEEK_SET 0
#endif
			struct flock lock_data;
			lock_data.l_type = F_WRLCK;
			lock_data.l_whence = SEEK_SET;
			lock_data.l_start = lock_data.l_len = 0;
			if (fcntl(pidFd, F_SETLK, &lock_data) == -1) {
				if (errno == EAGAIN)
					return oldpid;
				else
					return -1;
			}
#else
#ifdef LOCK_EX
			if (flock(pidFd, LOCK_EX | LOCK_NB) == -1) {
				if (errno == EWOULDBLOCK)
					return oldpid;
				else
					return -1;
			}
#else
			if (lockf(pidFd, F_TLOCK, 0) == -1) {
				if (errno == EACCES)
					return oldpid;
				else
					return -1;
			}
#endif
#endif
		}
		fprintf(pidFilePtr, "%5ld\n", (long)getpid());
		(void)fflush(pidFilePtr);
		RegisterCloseOnFork(pidFd);
	}
	return 0;
}
示例#3
0
文件: server.c 项目: cz172638/wdm
int
WaitForServer (struct display *d)
{
    static int i;

    for (i = 0; i < (d->openRepeat > 0 ? d->openRepeat : 1); i++) {
    	(void) Signal (SIGALRM, abortOpen);
    	(void) alarm ((unsigned) d->openTimeout);
    	if (!Setjmp (openAbort)) {
	    Debug ("Before XOpenDisplay(%s)\n", d->name);
	    errno = 0;
	    (void) XSetIOErrorHandler (openErrorHandler);
	    dpy = XOpenDisplay (d->name);
#ifdef STREAMSCONN
	    {
		/* For some reason, the next XOpenDisplay we do is
		   going to fail, so we might as well get that out
		   of the way.  There is something broken here. */
		Display *bogusDpy = XOpenDisplay (d->name);
		Debug ("bogus XOpenDisplay %s\n",
		       bogusDpy ? "succeeded" : "failed");
		if (bogusDpy) XCloseDisplay(bogusDpy); /* just in case */
	    }
#endif
	    (void) alarm ((unsigned) 0);
	    (void) Signal (SIGALRM, SIG_DFL);
	    (void) XSetIOErrorHandler ((int (*)(Display *)) 0);
	    Debug ("After XOpenDisplay(%s)\n", d->name);
	    if (dpy) {
#ifdef XDMCP
	    	if (d->displayType.location == Foreign)
		    GetRemoteAddress (d, ConnectionNumber (dpy));
#endif
	    	RegisterCloseOnFork (ConnectionNumber (dpy));
		(void) fcntl (ConnectionNumber (dpy), F_SETFD, 0);
	    	return 1;
	    } else {
	    	Debug ("OpenDisplay failed %d (%s) on \"%s\"\n",
		       errno, strerror (errno), d->name);
	    }
	    Debug ("waiting for server to start %d\n", i);
	    sleep ((unsigned) d->openDelay);
    	} else {
	    Debug ("hung in open, aborting\n");
	    LogError ("Hung in XOpenDisplay(%s), aborting\n", d->name);
	    (void) Signal (SIGALRM, SIG_DFL);
	    break;
    	}
    }
    Debug ("giving up on server\n");
    LogError ("server open failed for %s, giving up\n", d->name);
    return 0;
}
示例#4
0
文件: socket.c 项目: Fat-Zer/tdebase
static int
CreateListeningSocket( struct sockaddr *sock_addr, int salen )
{
	int fd;
#if defined(IPv6) && defined(IPPROTO_IPV6) && defined(IPV6_V6ONLY)
	int on = 0;
#endif
	const char *addrstring = "unknown";
#if defined(IPv6) && defined(AF_INET6)
	char addrbuf[INET6_ADDRSTRLEN];
#endif

	if (!request_port)
		return -1;

	if (debugLevel & DEBUG_CORE) {
#if defined(IPv6) && defined(AF_INET6)
		void *ipaddr;
		if (sock_addr->sa_family == AF_INET6)
			ipaddr = & ((struct sockaddr_in6 *)sock_addr)->sin6_addr;
		else
			ipaddr = & ((struct sockaddr_in *)sock_addr)->sin_addr;
		addrstring =
			inet_ntop( sock_addr->sa_family, ipaddr, addrbuf, sizeof(addrbuf) );

#else
		addrstring = inet_ntoa( ((struct sockaddr_in *)sock_addr)->sin_addr );
#endif

		Debug( "creating socket to listen on port %d of address %s\n",
		       request_port, addrstring );
	}

	if ((fd = socket( sock_addr->sa_family, SOCK_DGRAM, 0 )) == -1) {
		LogError( "XDMCP socket creation failed, errno %d\n", errno );
		return -1;
	}
#if defined(IPv6) && defined(IPPROTO_IPV6) && defined(IPV6_V6ONLY)
	setsockopt( fd, IPPROTO_IPV6, IPV6_V6ONLY, &on, sizeof(on) );
#endif

	if (bind( fd, sock_addr, salen ) == -1) {
		LogError( "error %d binding socket address %d\n", errno, request_port );
		close( fd );
		return -1;
	}

	RegisterCloseOnFork( fd );
	RegisterInput( fd );
	return fd;
}
示例#5
0
CreateWellKnownSockets ()
{
    struct sockaddr_in	sock_addr;
    char		*name, *localHostname();

    if (request_port == 0)
	    return;
    Debug ("creating socket %d\n", request_port);
    xdmcpFd = socket (AF_INET, SOCK_DGRAM, 0);
    if (xdmcpFd == -1) {
	LogError (ReadCatalog(MC_LOG_SET,MC_LOG_FAIL_SOCK,MC_DEF_LOG_FAIL_SOCK),
		  request_port);
	return;
    }
    name = localHostname ();
    registerHostname (name, strlen (name));
    RegisterCloseOnFork (xdmcpFd);
    /* zero out the entire structure; this avoids 4.4 incompatibilities */
    bzero ((char *) &sock_addr, sizeof (sock_addr));
#ifdef BSD44SOCKETS
    sock_addr.sin_len = sizeof(sock_addr);
#endif
    sock_addr.sin_family = AF_INET;
    sock_addr.sin_port = htons ((short) request_port);
    sock_addr.sin_addr.s_addr = htonl (INADDR_ANY);
    if (bind (xdmcpFd, (struct sockaddr *)&sock_addr, sizeof (sock_addr)) == -1)
    {
	LogError (ReadCatalog(MC_LOG_SET,MC_LOG_ERR_BIND,MC_DEF_LOG_ERR_BIND),
		  request_port, errno);
	close (xdmcpFd);
	xdmcpFd = -1;
	return;
    }
    WellKnownSocketsMax = xdmcpFd;
    FD_SET (xdmcpFd, &WellKnownSocketsMask);

    chooserFd = socket (AF_INET, SOCK_STREAM, 0);
    Debug ("Created chooser socket %d\n", chooserFd);
    if (chooserFd == -1)
    {
	LogError ((unsigned char *)"chooser socket creation failed, errno %d\n", errno);
	return;
    }
    listen (chooserFd, 5);
    if (chooserFd > WellKnownSocketsMax)
	WellKnownSocketsMax = chooserFd;
    FD_SET (chooserFd, &WellKnownSocketsMask);
}
示例#6
0
CreateWellKnownSockets ()
{
    struct sockaddr_in	sock_addr;
    char		*name, *localHostname();

    if (request_port == 0)
	    return;
    Debug ("creating socket %d\n", request_port);
    xdmcpFd = socket (AF_INET, SOCK_DGRAM, 0);
    if (xdmcpFd == -1) {
	LogError ("socket creation failed\n");
	return;
    }
    name = localHostname ();
    registerHostname (name, strlen (name));
    RegisterCloseOnFork (xdmcpFd);
    /* zero out the entire structure; this avoids 4.4 incompatibilities */
    bzero ((char *) &sock_addr, sizeof (sock_addr));
    sock_addr.sin_family = AF_INET;
    sock_addr.sin_port = htons ((short) request_port);
    sock_addr.sin_addr.s_addr = htonl (INADDR_ANY);
    if (bind (xdmcpFd, &sock_addr, sizeof (sock_addr)) == -1)
    {
	LogError ("error binding socket address %d\n", request_port);
	close (xdmcpFd);
	xdmcpFd = -1;
	return;
    }
    WellKnownSocketsMax = xdmcpFd;
    FD_SET (xdmcpFd, &WellKnownSocketsMask);

    chooserFd = socket (AF_INET, SOCK_STREAM, 0);
    Debug ("Created chooser socket %d\n", chooserFd);
    if (chooserFd == -1)
    {
	LogError ("chooser socket creation failed\n");
	return;
    }
    listen (chooserFd, 5);
    if (chooserFd > WellKnownSocketsMax)
	WellKnownSocketsMax = chooserFd;
    FD_SET (chooserFd, &WellKnownSocketsMask);
}
示例#7
0
文件: server.c 项目: bbidulock/xdm
int
WaitForServer (struct display *d)
{
    static int i;

    for (i = 0; i < (d->openRepeat > 0 ? d->openRepeat : 1); i++) {
	(void) Signal (SIGALRM, abortOpen);
	(void) alarm ((unsigned) d->openTimeout);
	if (!Setjmp (openAbort)) {
	    Debug ("Before XOpenDisplay(%s)\n", d->name);
	    errno = 0;
	    (void) XSetIOErrorHandler (openErrorHandler);
	    d->dpy = XOpenDisplay (d->name);
	    (void) alarm ((unsigned) 0);
	    (void) Signal (SIGALRM, SIG_DFL);
	    (void) XSetIOErrorHandler ((int (*)(Display *)) 0);
	    Debug ("After XOpenDisplay(%s)\n", d->name);
	    if (d->dpy) {
#ifdef XDMCP
		if (d->displayType.location == Foreign)
		    GetRemoteAddress (d, ConnectionNumber (d->dpy));
#endif
		RegisterCloseOnFork (ConnectionNumber (d->dpy));
		(void) fcntl (ConnectionNumber (d->dpy), F_SETFD, 0);
		return 1;
	    } else {
		Debug ("OpenDisplay failed %d (%s) on \"%s\"\n",
		       errno, strerror (errno), d->name);
	    }
	    Debug ("waiting for server to start %d\n", i);
	    sleep ((unsigned) d->openDelay);
	} else {
	    Debug ("hung in open, aborting\n");
	    LogError ("Hung in XOpenDisplay(%s), aborting\n", d->name);
	    (void) Signal (SIGALRM, SIG_DFL);
	    break;
	}
    }
    Debug ("giving up on server\n");
    LogError ("server open failed for %s, giving up\n", d->name);
    return 0;
}
示例#8
0
int
main( int argc, char **argv )
{
	int oldpid, oldumask, fd, noDaemonMode;
	char *pt, *errorLogFile, **opts;

	/* make sure at least world write access is disabled */
	if (((oldumask = umask( 022 )) & 002) == 002)
		(void)umask( oldumask );

	/* give /dev/null as stdin */
	if ((fd = open( "/dev/null", O_RDONLY )) > 0) {
		dup2( fd, 0 );
		close( fd );
	}
	if (fcntl( 1, F_GETFD ) < 0)
		dup2( 0, 1 );
	if (fcntl( 2, F_GETFD ) < 0)
		dup2( 0, 2 );

	if (argv[0][0] == '/') {
		if (!StrDup( &progpath, argv[0] ))
			Panic( "Out of memory" );
	} else
#ifdef __linux__
	{
		/* note that this will resolve symlinks ... */
		int len;
		char fullpath[PATH_MAX];
		if ((len = readlink( "/proc/self/exe", fullpath, sizeof(fullpath) )) < 0)
			Panic( "Invoke with full path specification or mount /proc" );
		if (!StrNDup( &progpath, fullpath, len ))
			Panic( "Out of memory" );
	}
#else
# if 0
		Panic( "Must be invoked with full path specification" );
# else
	{
		char directory[PATH_MAX+1];
		if (!getcwd( directory, sizeof(directory) ))
			Panic( "Can't find myself (getcwd failed)" );
		if (strchr( argv[0], '/' ))
			StrApp( &progpath, directory, "/", argv[0], (char *)0 );
		else {
			int len;
			char *path, *pathe, *name, *thenam, nambuf[PATH_MAX+1];

			if (!(path = getenv( "PATH" )))
				Panic( "Can't find myself (no PATH)" );
			len = strlen( argv[0] );
			name = nambuf + PATH_MAX - len;
			memcpy( name, argv[0], len + 1 );
			*--name = '/';
			do {
				if (!(pathe = strchr( path, ':' )))
					pathe = path + strlen( path );
				len = pathe - path;
				if (!len || (len == 1 && *path == '.')) {
					len = strlen( directory );
					path = directory;
				}
				thenam = name - len;
				if (thenam >= nambuf) {
					memcpy( thenam, path, len );
					if (!access( thenam, X_OK ))
						goto found;
				}
				path = pathe;
			} while (*path++ != '\0');
			Panic( "Can't find myself (not in PATH)" );
		  found:
			if (!StrDup( &progpath, thenam ))
				Panic( "Out of memory" );
		}
	}
# endif
#endif
	prog = strrchr( progpath, '/' ) + 1;

#if !defined(HAVE_SETPROCTITLE) && !defined(NOXDMTITLE)
	Title = argv[0];
	TitleLen = (argv[argc - 1] + strlen( argv[argc - 1] )) - Title;
#endif

	/*
	 * Parse command line options
	 */
	noDaemonMode = getppid();
	errorLogFile = 0;
	if (!(opts = Malloc( 2 * sizeof(char *) )))
		return 1;
	opts[0] = (char *)"";
	opts[1] = 0;
	while (*++argv) {
		if (**argv != '-')
			break;
		pt = *argv + 1;
		if (*pt == '-')
			pt++;
		if (!strcmp( pt, "help" ) || !strcmp( pt, "h" )) {
			printf( "Usage: %s [options] [tty]\n"
"  -daemon\t  - Daemonize even when started by init\n"
"  -nodaemon\t  - Don't daemonize even when started from command line\n"
"  -config <file>  - Use alternative master configuration file\n"
"  -xrm <res>\t  - Override frontend-specific resource\n"
"  -error <file>\t  - Use alternative log file\n"
"  -debug <num>\t  - Debug option bitfield:\n"
"\t\t\t0x1 - core log\n"
"\t\t\t0x2 - config reader log\n"
"\t\t\t0x4 - greeter log\n"
"\t\t\t0x8 - IPC log\n"
"\t\t\t0x10 - session sub-daemon post-fork delay\n"
"\t\t\t0x20 - config reader post-start delay\n"
"\t\t\t0x40 - greeter post-start delay\n"
"\t\t\t0x80 - don't use syslog\n"
"\t\t\t0x100 - core Xauth log\n"
"\t\t\t0x400 - valgrind config reader and greeter\n"
"\t\t\t0x800 - strace config reader and greeter\n"
			        , prog );
			exit( 0 );
		} else if (!strcmp( pt, "daemon" ))
			noDaemonMode = 0;
		else if (!strcmp( pt, "nodaemon" ))
			noDaemonMode = 1;
		else if (argv[1] && !strcmp( pt, "config" ))
			StrDup( opts, *++argv );
		else if (argv[1] && !strcmp( pt, "xrm" ))
			opts = addStrArr( opts, *++argv, -1 );
		else if (argv[1] && !strcmp( pt, "debug" ))
			sscanf( *++argv, "%i", &debugLevel );
		else if (argv[1] && (!strcmp( pt, "error" ) || !strcmp( pt, "logfile" )))
			errorLogFile = *++argv;
		else {
			fprintf( stderr, "\"%s\" is an unknown option or is missing a parameter\n", *argv );
			exit( 1 );
		}
	}

	/*
	 * Only allow root to run in non-debug mode to avoid problems
	 */
	if (!debugLevel && getuid()) {
		fprintf( stderr, "Only root wants to run %s\n", prog );
		exit( 1 );
	}

	InitErrorLog( errorLogFile );

	if (noDaemonMode != 1)
		BecomeDaemon();

	/*
	 * Step 1 - load configuration parameters
	 */
	if (!InitResources( opts ) || ScanConfigs( FALSE ) < 0)
		LogPanic( "Config reader failed. Aborting ...\n" );

	/* SUPPRESS 560 */
	if ((oldpid = StorePid())) {
		if (oldpid == -1)
			LogError( "Can't create/lock pid file %s\n", pidFile );
		else
			LogError( "Can't lock pid file %s, another xdm is running (pid %d)\n",
			          pidFile, oldpid );
		exit( 1 );
	}

#ifdef NEED_ENTROPY
	AddOtherEntropy();
#endif

	/*
	 * We used to clean up old authorization files here. As authDir is
	 * supposed to be /var/run/xauth or /tmp, we needn't to care for it.
	 */

#ifdef XDMCP
	init_session_id();
#else
	Debug( "not compiled for XDMCP\n" );
#endif
	if (pipe( signalFds ))
		LogPanic( "Unable to create signal notification pipe.\n" );
	RegisterInput( signalFds[0] );
	RegisterCloseOnFork( signalFds[0] );
	RegisterCloseOnFork( signalFds[1] );
	(void)Signal( SIGTERM, SigHandler );
	(void)Signal( SIGINT, SigHandler );
	(void)Signal( SIGHUP, SigHandler );
	(void)Signal( SIGCHLD, SigHandler );
	(void)Signal( SIGUSR1, SigHandler );

	/*
	 * Step 2 - run a sub-daemon for each entry
	 */
#ifdef XDMCP
	UpdateListenSockets();
#endif
	openCtrl( 0 );
	MainLoop();
	closeCtrl( 0 );
	if (sdRec.how) {
		commitBootOption();
		if (Fork() <= 0) {
			char *cmd = sdRec.how == SHUT_HALT ? cmdHalt : cmdReboot;
			execute( parseArgs( (char **)0, cmd ), (char **)0 );
			LogError( "Failed to execute shutdown command %\"s\n", cmd );
			exit( 1 );
		} else {
			sigset_t mask;
			sigemptyset( &mask );
			sigaddset( &mask, SIGCHLD );
			sigaddset( &mask, SIGHUP );
			sigsuspend( &mask );
		}
	}
	Debug( "nothing left to do, exiting\n" );
	return 0;
}
示例#9
0
CreateWellKnownSockets ()
{
    struct t_bind bind_addr;
    struct netconfig *nconf;
    struct nd_hostserv service;
    struct nd_addrlist *servaddrs;
    char *name, *localHostname();
    char bindbuf[15];
    int it;

    if (request_port == 0)
	return;
    Debug ("creating UDP stream %d\n", request_port);

    nconf = getnetconfigent("udp");
    if (!nconf) {
	t_error("getnetconfigent udp");
	return;
    }

    xdmcpFd = t_open(nconf->nc_device, O_RDWR, NULL);
    if (xdmcpFd == -1) {
	LogError ("XDMCP stream creation failed\n");
	t_error ("t_open");
	return;
    }
    name = localHostname ();
    registerHostname (name, strlen (name));
    RegisterCloseOnFork (xdmcpFd);

    service.h_host = HOST_SELF;
    sprintf(bindbuf, "%d", request_port);
    service.h_serv = bindbuf;
    netdir_getbyname(nconf, &service, &servaddrs);
    freenetconfigent(nconf);

    bind_addr.qlen = 5;
    bind_addr.addr.buf = servaddrs->n_addrs[0].buf;
    bind_addr.addr.len = servaddrs->n_addrs[0].len;
    it = t_bind(xdmcpFd, &bind_addr, &bind_addr);
    netdir_free(servaddrs, ND_ADDRLIST);
    if (it < 0)
    {
	LogError ("error binding STREAMS address %d\n", request_port);
	t_error("t_bind");	/* also goes to log file */
	t_close (xdmcpFd);
	xdmcpFd = -1;
	return;
    }
    WellKnownSocketsMax = xdmcpFd;
    FD_SET (xdmcpFd, &WellKnownSocketsMask);

    chooserFd = t_open ("/dev/tcp", O_RDWR, NULL);
    Debug ("Created chooser fd %d\n", chooserFd);
    if (chooserFd == -1)
    {
	LogError ("chooser stream creation failed\n");
	t_error("t_open chooser");
	return;
    }
    if (chooserFd > WellKnownSocketsMax)
	WellKnownSocketsMax = chooserFd;
    FD_SET (chooserFd, &WellKnownSocketsMask);
}
示例#10
0
文件: Greet.c 项目: bbidulock/wdm
static int InitGreet(struct display *d)
{
	int pid;

	WDMDebug("Greet display=%s\n", d->name);

	pipe(pipe_filedes);

	pid = fork();

	if (pid == -1) {			/* error */
		WDMError("Greet cannot fork\n");
		exit(RESERVER_DISPLAY);
	}
	if (pid == 0) {				/* child */
		char **env = NULL;
		char *argv[20];
		int argc = 1;			/* argc = 0 is for command itself */

		close(pipe_filedes[0]);
		fcntl(pipe_filedes[1], F_SETFD, 0);	/* Reset close-on-exec (just in case) */

		env = (char **)systemEnv(d, (char *)NULL, FAKEHOME);

		if (*wdmLocale)
			env = WDMSetEnv(env, "LANG", wdmLocale);

		if (*wdmCursorTheme)
			env = WDMSetEnv(env, "XCURSOR_THEME", wdmCursorTheme);

		if ((argv[0] = strrchr(wdmLogin, '/')) == NULL)
			argv[0] = wdmLogin;
		else
			argv[0]++;

		argv[argc++] = wstrconcat("-d", d->name);
		if (*wdmWm)
			argv[argc++] = wstrconcat("-w", wdmWm);
		if (*wdmLogo)
			argv[argc++] = wstrconcat("-l", wdmLogo);
		if (*wdmHelpFile)
			argv[argc++] = wstrconcat("-h", wdmHelpFile);
		if (*wdmDefaultUser)
			argv[argc++] = "-u";
		if (*wdmBg)
			argv[argc++] = wstrconcat("-b", wdmBg);
		if (*wdmLoginConfig)
			argv[argc++] = wstrconcat("-c", wdmLoginConfig);
		if (wdmAnimations)
			argv[argc++] = "-a";
		if (wdmXineramaHead) {
			argv[argc] = wmalloc(25);	/* much more than length of 64bit integer 
										   converted to string, but it still a hack */
			sprintf(argv[argc++], "-x%i", wdmXineramaHead);
		}
		argv[argc] = wmalloc(25);
		sprintf(argv[argc++], "-f%i", pipe_filedes[1]);

		argv[argc++] = NULL;
		execve(wdmLogin, argv, env);

		WDMError("Greet cannot exec %s\n", wdmLogin);
		exit(RESERVER_DISPLAY);
	}

	close(pipe_filedes[1]);
	RegisterCloseOnFork(pipe_filedes[0]);
	return pid;
}