server.c

来自「samba-3.0.22.tar.gz 编译smb服务器的源码」· C语言 代码 · 共 671 行 · 第 1/2 页

C
671
字号
	p->next = packet;	packet->next = NULL;	packet->prev = p;}/****************************************************************************  Listens for NMB or DGRAM packets, and queues them.  return True if the socket is dead***************************************************************************/static BOOL listen_for_wins_packets(void){	int num_interfaces = iface_count();	fd_set fds;	int i, num, s, new_s;	static int maxfd = 0;	struct timeval timeout;	if(listen_set == NULL) {		if(!create_listen_fdset( &maxfd)) {			DEBUG(0,("listen_for_packets: Fatal error. unable to create listen set. Exiting.\n"));			return True;		}	}	memcpy((char *)&fds, (char *)listen_set, sizeof(fd_set));	timeout.tv_sec = NMBD_SELECT_LOOP;	timeout.tv_usec = 0;	/* Prepare for the select - allow certain signals. */	BlockSignals(False, SIGTERM);	num = sys_select(maxfd+1, &fds, NULL, NULL, &timeout);	/* We can only take signals when we are in the select - block them again here. */	BlockSignals(True, SIGTERM);	if(num == -1)		return False;	for (; num > 0; num--) {		s = -1;		/* check the sockets we are only listening on, waiting to accept */				for (i=0; i<num_interfaces; i++) {			struct sockaddr addr;			socklen_t in_addrlen = sizeof(addr);					if(FD_ISSET(sock_array[i], &fds)) {				s = sock_array[i];				/* Clear this so we don't look at it again. */				FD_CLR(sock_array[i], &fds);				/* accept and add the new socket to the listen set */				new_s=accept(s, &addr, &in_addrlen);				if (new_s < 0)					continue;					DEBUG(5,("listen_for_wins_packets: new connection, old: %d, new : %d\n", s, new_s));								set_socket_options(new_s, "SO_KEEPALIVE");				set_socket_options(new_s, user_socket_options);				FD_SET(new_s, listen_set);				add_fd_to_sock_array(new_s);				maxfd = MAX( maxfd, new_s);			}		}		/*		 * check for the sockets we are waiting data from		 * either client sending datas		 * or reply to our requests		 */		for (i=num_interfaces; i<listen_number; i++) {			if(FD_ISSET(sock_array[i], &fds)) {				struct wins_packet_struct *packet = read_wins_packet(sock_array[i], timeout.tv_sec);				if (packet) {					packet->fd = sock_array[i];					queue_packet(packet);				}				DEBUG(2,("listen_for_wins_packets: some data on fd %d\n", sock_array[i]));				FD_CLR(sock_array[i], &fds);				break;			}			}	}	return False;}/*******************************************************************  Run elements off the packet queue till its empty******************************************************************/static void run_wins_packet_queue(void){	struct wins_packet_struct *p;	while ((p = packet_queue)) {		packet_queue = p->next;		if (packet_queue)			packet_queue->prev = NULL;		p->next = p->prev = NULL;		construct_reply(p);		/* if it was a stop assoc, close the connection */		if (p->stop_packet) {			FD_CLR(p->fd, listen_set);			remove_fd_from_sock_array(p->fd);			close(p->fd);		}	}} /**************************************************************************** ** The main select loop. **************************************************************************** */static void process(void){	while( True ) {		time_t t = time(NULL);		/* check for internal messages */		message_dispatch();		if(listen_for_wins_packets())			return;		run_wins_packet_queue();		run_pull_replication(t);				run_push_replication(t);				/*		 * Reload the services file if we got a sighup.		 */		if(reload_after_sighup) {			reload_services( True );			reopen_logs();			reload_after_sighup = False;		}		/* free temp memory */		talloc_free_children(mem_ctx);		/* free up temp memory */		lp_talloc_free();	}} /* process *//****************************************************************************  main program****************************************************************************/ int main(int argc,char *argv[]){	/* shall I run as a daemon */	static BOOL is_daemon = False;	static BOOL interactive = False;	static BOOL Fork = True;	static BOOL log_stdout = False;	struct poptOption long_options[] = {		POPT_AUTOHELP		{ "daemon", 'D', POPT_ARG_VAL, &is_daemon, True, "Become a daemon (default)" },		{ "foreground", 'F', POPT_ARG_VAL, &Fork, False, "Run daemon in foreground (for daemontools, etc)" },		{ "stdout", 'S', POPT_ARG_VAL, &log_stdout, True, "Log to stdout" },		{ "interactive", 'i', POPT_ARG_NONE, NULL, 'i', "Run interactive (not a daemon)" },		{ "port", 'p', POPT_ARG_INT, &wins_port, 'p', "Listen on the specified port" },		POPT_COMMON_SAMBA		POPT_TABLEEND	};	int opt;	poptContext pc;#ifdef HAVE_SET_AUTH_PARAMETERS	set_auth_parameters(argc,argv);#endif	pc = poptGetContext("wrepld", argc, (const char **)argv, long_options, 						POPT_CONTEXT_KEEP_FIRST);	while ((opt = poptGetNextOpt(pc)) != -1) {		switch (opt)  {		case 'i':			interactive = True;			Fork = False;			log_stdout = True;			break;		}	}	if (log_stdout && Fork) {		d_printf("Can't log to stdout (-S) unless daemon is in foreground (-F) or interactive (-i)\n");		poptPrintUsage(pc, stderr, 0);		exit(1);	}#ifdef HAVE_SETLUID	/* needed for SecureWare on SCO */	setluid(0);#endif	sec_init();	load_case_tables();	set_remote_machine_name("wrepld", False);	setup_logging(argv[0],log_stdout);	/* we want to re-seed early to prevent time delays causing           client problems at a later date. (tridge) */	generate_random_buffer(NULL, 0);	/* make absolutely sure we run as root - to handle cases where people	   are crazy enough to have it setuid */	gain_root_privilege();	gain_root_group_privilege();	fault_setup((void (*)(void *))exit_server);	CatchSignal(SIGTERM , SIGNAL_CAST dflt_sig);	/* we are never interested in SIGPIPE */	BlockSignals(True,SIGPIPE);#if defined(SIGFPE)	/* we are never interested in SIGFPE */	BlockSignals(True,SIGFPE);#endif#if defined(SIGUSR2)	/* We are no longer interested in USR2 */	BlockSignals(True,SIGUSR2);#endif	/* POSIX demands that signals are inherited. If the invoking process has	 * these signals masked, we will have problems, as we won't recieve them. */	BlockSignals(False, SIGHUP);	BlockSignals(False, SIGUSR1);	/* we want total control over the permissions on created files,	   so set our umask to 0 */	umask(0);	reopen_logs();	DEBUG(0,( "wrepld version %s started.\n", SAMBA_VERSION_STRING));	DEBUGADD( 0, ( "%s\n", COPYRIGHT_STARTUP_MESSAGE ) );	DEBUG(2,("uid=%d gid=%d euid=%d egid=%d\n",		 (int)getuid(),(int)getgid(),(int)geteuid(),(int)getegid()));	if (sizeof(uint16) < 2 || sizeof(uint32) < 4) {		DEBUG(0,("ERROR: Samba is not configured correctly for the word size on your machine\n"));		exit(1);	}	/*	 * Do this before reload_services.	 */	if (!reload_services(False))		return(-1);		if (!init_names())		return -1;	#ifdef WITH_PROFILE	if (!profile_setup(False)) {		DEBUG(0,("ERROR: failed to setup profiling\n"));		return -1;	}#endif	CatchSignal(SIGHUP,SIGNAL_CAST sig_hup);		DEBUG(3,( "loaded services\n"));	if (!is_daemon && !is_a_socket(0)) {		DEBUG(0,("standard input is not a socket, assuming -D option\n"));		is_daemon = True;	}	if (is_daemon && !interactive) {		DEBUG( 3, ( "Becoming a daemon.\n" ) );		become_daemon(Fork);	}#if HAVE_SETPGID	/*	 * If we're interactive we want to set our own process group for	 * signal management.	 */	if (interactive)		setpgid( (pid_t)0, (pid_t)0);#endif	if (!directory_exist(lp_lockdir(), NULL)) {		mkdir(lp_lockdir(), 0755);	}	if (is_daemon) {		pidfile_create("wrepld");	}	if (!message_init()) {		exit(1);	}	/* Initialise the memory context */	mem_ctx=talloc_init("wins repl talloc ctx");	/* initialise the global partners table */	partner_count=init_wins_partner_table();	/* We can only take signals in the select. */	BlockSignals( True, SIGTERM );	process();	poptFreeContext(pc);	exit_server("normal exit");	return(0);}

⌨️ 快捷键说明

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