⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 syslogd.c

📁 linux下记录系统日志代码以及记录内核日志代码
💻 C
📖 第 1 页 / 共 5 页
字号:
	 * Convert to lower case to recognize the correct domain laterly	 */	for (p = (char *)LocalDomain; *p ; p++)		if (isupper(*p))			*p = tolower(*p);	(void) signal(SIGTERM, die);	(void) signal(SIGINT, Debug ? die : SIG_IGN);	(void) signal(SIGQUIT, Debug ? die : SIG_IGN);	(void) signal(SIGCHLD, reapchild);	(void) signal(SIGALRM, domark);	(void) signal(SIGUSR1, Debug ? debug_switch : SIG_IGN);	(void) alarm(TIMERINTVL);	/* Create a partial message table for all file descriptors. */	num_fds = getdtablesize();	dprintf("Allocated parts table for %d file descriptors.\n", num_fds);	if ( (parts = (char **) malloc(num_fds * sizeof(char *))) == \	    (char **) 0 )	{		logerror("Cannot allocate memory for message parts table.");		die(0);	}	for(i= 0; i < num_fds; ++i)	    parts[i] = (char *) 0;	dprintf("Starting.\n");	init();#ifndef TESTING	if ( Debug )	{		dprintf("Debugging disabled, SIGUSR1 to turn on debugging.\n");		debugging_on = 0;	}	/*	 * Send a signal to the parent to it can terminate.	 */	if (getpid() != ppid)		kill (ppid, SIGTERM);#endif	/* Main loop begins here. */	for (;;) {		int nfds;		errno = 0;		FD_ZERO(&readfds);		maxfds = 0;#ifdef SYSLOG_UNIXAF#ifndef TESTING		/*		 * Add the Unix Domain Sockets to the list of read		 * descriptors.		 */		/* Copy master connections */		for (i = 0; i < nfunix; i++) {			if (funix[i] != -1) {				FD_SET(funix[i], &readfds);				if (funix[i]>maxfds) maxfds=funix[i];			}		}#endif#endif#ifdef SYSLOG_INET#ifndef TESTING		/*		 * Add the Internet Domain Socket to the list of read		 * descriptors.		 */		if ( InetInuse && AcceptRemote ) {			FD_SET(inetm, &readfds);			if (inetm>maxfds) maxfds=inetm;			dprintf("Listening on syslog UDP port.\n");		}#endif#endif#ifdef TESTING		FD_SET(fileno(stdin), &readfds);		if (fileno(stdin) > maxfds) maxfds = fileno(stdin);		dprintf("Listening on stdin.  Press Ctrl-C to interrupt.\n");#endif		if ( debugging_on )		{			dprintf("Calling select, active file descriptors (max %d): ", maxfds);			for (nfds= 0; nfds <= maxfds; ++nfds)				if ( FD_ISSET(nfds, &readfds) )					dprintf("%d ", nfds);			dprintf("\n");		}		nfds = select(maxfds+1, (fd_set *) &readfds, (fd_set *) NULL,				  (fd_set *) NULL, (struct timeval *) NULL);		if ( restart )		{			dprintf("\nReceived SIGHUP, reloading syslogd.\n");			init();			restart = 0;			continue;		}		if (nfds == 0) {			dprintf("No select activity.\n");			continue;		}		if (nfds < 0) {			if (errno != EINTR)				logerror("select");			dprintf("Select interrupted.\n");			continue;		}		if ( debugging_on )		{			dprintf("\nSuccessful select, descriptor count = %d, " \				"Activity on: ", nfds);			for (nfds= 0; nfds <= maxfds; ++nfds)				if ( FD_ISSET(nfds, &readfds) )					dprintf("%d ", nfds);			dprintf(("\n"));		}#ifndef TESTING#ifdef SYSLOG_UNIXAF		for (i = 0; i < nfunix; i++) {		    if ((fd = funix[i]) != -1 && FD_ISSET(fd, &readfds)) {			memset(line, '\0', sizeof(line));			i = recv(fd, line, MAXLINE - 2, 0);			dprintf("Message from UNIX socket: #%d\n", fd);			if (i > 0) {				line[i] = line[i+1] = '\0';				printchopped(LocalHostName, line, i + 2,  fd);			} else if (i < 0 && errno != EINTR) {				dprintf("UNIX socket error: %d = %s.\n", \					errno, strerror(errno));				logerror("recvfrom UNIX");	      	}				}			}#endif#ifdef SYSLOG_INET		if (InetInuse && AcceptRemote && FD_ISSET(inetm, &readfds)) {			len = sizeof(frominet);			memset(line, '\0', sizeof(line));			i = recvfrom(finet, line, MAXLINE - 2, 0, \				     (struct sockaddr *) &frominet, &len);			dprintf("Message from inetd socket: #%d, host: %s\n",				inetm, inet_ntoa(frominet.sin_addr));			if (i > 0) {				line[i] = line[i+1] = '\0';				from = (char *)cvthname(&frominet);				/*				 * Here we could check if the host is permitted				 * to send us syslog messages. We just have to				 * catch the result of cvthname, look for a dot				 * and if that doesn't exist, replace the first				 * '\0' with '.' and we have the fqdn in lowercase				 * letters so we could match them against whatever.				 *  -Joey				 */				printchopped(from, line, \ 					     i + 2,  finet);			} else if (i < 0 && errno != EINTR) {				dprintf("INET socket error: %d = %s.\n", \					errno, strerror(errno));				logerror("recvfrom inet");				/* should be harmless now that we set				 * BSDCOMPAT on the socket */				sleep(10);			}		}#endif#else		if ( FD_ISSET(fileno(stdin), &readfds) ) {			dprintf("Message from stdin.\n");			memset(line, '\0', sizeof(line));			line[0] = '.';			parts[fileno(stdin)] = (char *) 0;			i = read(fileno(stdin), line, MAXLINE);			if (i > 0) {				printchopped(LocalHostName, line, i+1, fileno(stdin));		  	} else if (i < 0) {		    		if (errno != EINTR) {		      			logerror("stdin");				}		  	}			FD_CLR(fileno(stdin), &readfds);		  }#endif	}}int usage(){	fprintf(stderr, "usage: syslogd [-drvh] [-l hostlist] [-m markinterval] [-n] [-p path]\n" \		" [-s domainlist] [-f conffile]\n");	exit(1);}#ifdef SYSLOG_UNIXAFstatic int create_unix_socket(const char *path){	struct sockaddr_un sunx;	int fd;	char line[MAXLINE +1];	if (path[0] == '\0')		return -1;	(void) unlink(path);	memset(&sunx, 0, sizeof(sunx));	sunx.sun_family = AF_UNIX;	(void) strncpy(sunx.sun_path, path, sizeof(sunx.sun_path));	fd = socket(AF_UNIX, SOCK_DGRAM, 0);	if (fd < 0 || bind(fd, (struct sockaddr *) &sunx,			   sizeof(sunx.sun_family)+strlen(sunx.sun_path)) < 0 ||	    chmod(path, 0666) < 0) {		(void) snprintf(line, sizeof(line), "cannot create %s", path);		logerror(line);		dprintf("cannot create %s (%d).\n", path, errno);		close(fd);#ifndef SYSV		die(0);#endif		return -1;	}	return fd;}#endif#ifdef SYSLOG_INETstatic int create_inet_socket(){	int fd, on = 1;	struct sockaddr_in sin;	fd = socket(AF_INET, SOCK_DGRAM, 0);	if (fd < 0) {		logerror("syslog: Unknown protocol, suspending inet service.");		return fd;	}	memset(&sin, 0, sizeof(sin));	sin.sin_family = AF_INET;	sin.sin_port = LogPort;	if (setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, \		       (char *) &on, sizeof(on)) < 0 ) {		logerror("setsockopt(REUSEADDR), suspending inet");		close(fd);		return -1;	}	/* We need to enable BSD compatibility. Otherwise an attacker	 * could flood our log files by sending us tons of ICMP errors.	 */	if (setsockopt(fd, SOL_SOCKET, SO_BSDCOMPAT, \			(char *) &on, sizeof(on)) < 0) {		logerror("setsockopt(BSDCOMPAT), suspending inet");		close(fd);		return -1;	}	if (bind(fd, (struct sockaddr *) &sin, sizeof(sin)) < 0) {		logerror("bind, suspending inet");		close(fd);		return -1;	}	return fd;}#endifchar **crunch_list(list)	char *list;{	int count, i;	char *p, *q;	char **result = NULL;	p = list;		/* strip off trailing delimiters */	while (p[strlen(p)-1] == LIST_DELIMITER) {		count--;		p[strlen(p)-1] = '\0';	}	/* cut off leading delimiters */	while (p[0] == LIST_DELIMITER) {		count--;		p++; 	}		/* count delimiters to calculate elements */	for (count=i=0; p[i]; i++)		if (p[i] == LIST_DELIMITER) count++;		if ((result = (char **)malloc(sizeof(char *) * count+2)) == NULL) {		printf ("Sorry, can't get enough memory, exiting.\n");		exit(0);	}		/*	 * We now can assume that the first and last	 * characters are different from any delimiters,	 * so we don't have to care about this.	 */	count = 0;	while ((q=strchr(p, LIST_DELIMITER))) {		result[count] = (char *) malloc((q - p + 1) * sizeof(char));		if (result[count] == NULL) {			printf ("Sorry, can't get enough memory, exiting.\n");			exit(0);		}		strncpy(result[count], p, q - p);		result[count][q - p] = '\0';		p = q; p++;		count++;	}	if ((result[count] = \	     (char *)malloc(sizeof(char) * strlen(p) + 1)) == NULL) {		printf ("Sorry, can't get enough memory, exiting.\n");		exit(0);	}	strcpy(result[count],p);	result[++count] = NULL;#if 0	count=0;	while (result[count])		dprintf ("#%d: %s\n", count, StripDomains[count++]);#endif	return result;}void untty()#ifdef SYSV{	if ( !Debug ) {		setsid();	}	return;}#else{	int i;	if ( !Debug ) {		i = open(_PATH_TTY, O_RDWR);		if (i >= 0) {			(void) ioctl(i, (int) TIOCNOTTY, (char *)0);			(void) close(i);		}	}}#endif/* * Parse the line to make sure that the msg is not a composite of more * than one message. */void printchopped(hname, msg, len, fd)	const char *hname;	char *msg;	int len;	int fd;{	auto int ptlngth;	auto char *start = msg,		  *p,	          *end,		  tmpline[MAXLINE + 1];	dprintf("Message length: %d, File descriptor: %d.\n", len, fd);	tmpline[0] = '\0';	if ( parts[fd] != (char *) 0 )	{		dprintf("Including part from messages.\n");		strcpy(tmpline, parts[fd]);		free(parts[fd]);		parts[fd] = (char *) 0;		if ( (strlen(msg) + strlen(tmpline)) > MAXLINE )		{			logerror("Cannot glue message parts together");			printline(hname, tmpline);			start = msg;		}		else		{			dprintf("Previous: %s\n", tmpline);			dprintf("Next: %s\n", msg);			strcat(tmpline, msg);	/* length checked above */			printline(hname, tmpline);			if ( (strlen(msg) + 1) == len )				return;			else				start = strchr(msg, '\0') + 1;		}	}	if ( msg[len-1] != '\0' )	{		msg[len] = '\0';		for(p= msg+len-1; *p != '\0' && p > msg; )			--p;		if(*p == '\0') p++;		ptlngth = strlen(p);		if ( (parts[fd] = malloc(ptlngth + 1)) == (char *) 0 )			logerror("Cannot allocate memory for message part.");		else		{			strcpy(parts[fd], p);			dprintf("Saving partial msg: %s\n", parts[fd]);			memset(p, '\0', ptlngth);		}	}	do {		end = strchr(start + 1, '\0');		printline(hname, start);		start = end + 1;	} while ( *start != '\0' );	return;}/* * Take a raw input line, decode the message, and print the message * on the appropriate log files. */void printline(hname, msg)	const char *hname;	char *msg;{	register char *p, *q;	register unsigned char c;	char line[MAXLINE + 1];	int pri;	/* test for special codes */	pri = DEFUPRI;	p = msg;	if (*p == '<') {		pri = 0;		while (isdigit(*++p))		{		   pri = 10 * pri + (*p - '0');		}		if (*p == '>')			++p;	}	if (pri &~ (LOG_FACMASK|LOG_PRIMASK))		pri = DEFUPRI;	memset (line, 0, sizeof(line));	q = line;	while ((c = *p++) && q < &line[sizeof(line) - 4]) {		if (c == '\n')			*q++ = ' ';		else if (c < 040) {			*q++ = '^';			*q++ = c ^ 0100;		} else if (c == 0177 || (c & 0177) < 040) {			*q++ = '\\';			*q++ = '0' + ((c & 0300) >> 6);			*q++ = '0' + ((c & 0070) >> 3);			*q++ = '0' + (c & 0007);		} else			*q++ = c;	}	*q = '\0';	logmsg(pri, line, hname, SYNC_FILE);	return;}/* * Take a raw input line from /dev/klog, split and format similar to syslog(). */void printsys(msg)	char *msg;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -