コード例 #1
0
ファイル: bin_interface.c プロジェクト: seanchann/opensips
/*
 * called in the OpenSIPS initialization phase by the main process.
 * forks the binary packet UDP receivers.
 *
 * @return: 0 on success
 */
int start_bin_receivers(void)
{
	pid_t pid;
	int i;

	if (udp_init_listener(bin, 0) != 0)
		return -1;

	for (i = 1; i <= bin_children; i++) {
		if ((pid = internal_fork("BIN receiver")) < 0) {
			LM_CRIT("Cannot fork binary packet receiver process!\n");
			return -1;
		}

		if (pid == 0) {
			LM_DBG("CHILD sock: %d\n", bin->socket);

			child_index = i;
			set_proc_attrs("BIN receiver %.*s ",
							bin->sock_str.len,
							bin->sock_str.s);
			bind_address = bin;

			if (init_child(PROC_BIN) < 0) {
				LM_ERR("init_child failed for BIN listener\n");
				report_failure_status();
				exit(-1);
			}

			bin_receive_loop();
			exit(-1);
		} else
			LM_DBG("PARENT sock: %d\n", bin->socket);
	}

	return 0;
}
コード例 #2
0
ファイル: main.c プロジェクト: yuantangliang/opensips
/**
 * Main loop, forks the children, bind to addresses,
 * handle signals.
 * \return don't return on sucess, -1 on error
 */
static int main_loop(void)
{
    static int chd_rank;
    int* startup_done = NULL;

    chd_rank=0;

    if (init_debug() != 0) {
        LM_ERR("failed to init logging levels\n");
        goto error;
    }

    if (dont_fork) {

        if (create_status_pipe() < 0) {
            LM_ERR("failed to create status pipe\n");
            goto error;
        }

        if (udp_init_nofork() < 0) {
            LM_ERR("failed to init UDP for no fork mode\n");
            goto error;
        }

        /* try to drop privileges */
        if (do_suid(uid, gid)==-1)
            goto error;

        if (start_module_procs()!=0) {
            LM_ERR("failed to fork module processes\n");
            goto error;
        }

        /* we need another process to act as the timer*/
        if (start_timer_processes()!=0) {
            LM_CRIT("cannot start timer process(es)\n");
            goto error;
        }

        is_main=1;

        udp_start_nofork();
        /* udp_start_nofork() returns only if error */

        /* in case of failed startup, behave as "attendant" to trigger
         * proper cleanup sequance (and proper signal handler !!!).
         * So, reset the dont_fork (as it will force inline signal handling)*/
        dont_fork = 0;
        return -1;

    } else {  /* don't fork */

        if (trans_init_all_listeners()<0) {
            LM_ERR("failed to init all SIP listeners, aborting\n");
            goto error;
        }

        /* all processes should have access to all the sockets (for sending)
         * so we open all first*/
        if (do_suid(uid, gid)==-1) goto error; /* try to drop privileges */

        if (start_module_procs()!=0) {
            LM_ERR("failed to fork module processes\n");
            goto error;
        }

        if(startup_rlist.a) {/* if a startup route was defined */
            startup_done = (int*)shm_malloc(sizeof(int));
            if(startup_done == NULL) {
                LM_ERR("No more shared memory\n");
                goto error;
            }
            *startup_done = 0;
        }

        if (fix_socket_list(&bin) != 0) {
            LM_ERR("failed to initialize binary interface socket list!\n");
            goto error;
        }

        /* OpenSIPS <--> OpenSIPS communication interface */
        if (bin && start_bin_receivers() != 0) {
            LM_CRIT("cannot start binary interface receiver processes!\n");
            goto error;
        }

        /* fork for the timer process*/
        if (start_timer_processes()!=0) {
            LM_CRIT("cannot start timer process(es)\n");
            goto error;
        }

        /* fork all processes required by UDP network layer */
        if (udp_start_processes( &chd_rank, startup_done)<0) {
            LM_CRIT("cannot start TCP processes\n");
            goto error;
        }

        /* fork all processes required by TCP network layer */
        if (tcp_start_processes( &chd_rank, startup_done)<0) {
            LM_CRIT("cannot start TCP processes\n");
            goto error;
        }
    }

    /* this is the main process -> it shouldn't send anything */
    bind_address=0;

    if (startup_done) {
        if (*startup_done==0)
            LM_CRIT("BUG: startup route defined, but not run :( \n");
        shm_free(startup_done);
    }

    /* main process left */
    is_main=1;
    set_proc_attrs("attendant");

    if (init_child(PROC_MAIN) < 0) {
        LM_ERR("error in init_child for PROC_MAIN\n");
        report_failure_status();
        goto error;
    }

    report_conditional_status( (!no_daemon_mode), 0);

    for(;;) {
        handle_sigs();
        pause();
    }

    /*return 0; */
error:
    is_main=1;  /* if we are here, we are the "main process",
				  any forked children should exit with exit(-1) and not
				  ever use return */
    report_conditional_status( (!dont_fork), -1);
    return -1;

}
コード例 #3
0
ファイル: sr_module.c プロジェクト: OpenSIPS/opensips
int start_module_procs(void)
{
	struct sr_module *m;
	unsigned int n;
	unsigned int l;
	int x;

	for( m=modules ; m ; m=m->next) {
		if (m->exports->procs==NULL)
			continue;
		for( n=0 ; m->exports->procs[n].name ; n++) {
			if ( !m->exports->procs[n].no || !m->exports->procs[n].function )
				continue;
			/* run pre-fork function */
			if (m->exports->procs[n].pre_fork_function)
				if (m->exports->procs[n].pre_fork_function()!=0) {
					LM_ERR("pre-fork function failed for process \"%s\" "
						"in module %s\n",
						m->exports->procs[n].name, m->exports->name);
					return -1;
				}
			/* fork the processes */
			for ( l=0; l<m->exports->procs[n].no ; l++) {
				LM_DBG("forking process \"%s\"/%d for module %s\n",
					m->exports->procs[n].name, l, m->exports->name);
				x = internal_fork( m->exports->procs[n].name,
						((m->exports->procs[n].flags&PROC_FLAG_HAS_IPC) ?
						0 : OSS_PROC_NO_IPC)|OSS_PROC_IS_EXTRA, TYPE_MODULE );
				if (x<0) {
					LM_ERR("failed to fork process \"%s\"/%d for module %s\n",
						m->exports->procs[n].name, l, m->exports->name);
					return -1;
				} else if (x==0) {
					/* new process */
					/* initialize the process for the rest of the modules */
					if ( m->exports->procs[n].flags&PROC_FLAG_INITCHILD ) {
						if (init_child(PROC_MODULE) < 0) {
							LM_ERR("error in init_child for PROC_MODULE\n");
							report_failure_status();
							exit(-1);
						}

						report_conditional_status( (!no_daemon_mode), 0);
					} else
						clean_write_pipeend();

					/* run the function */
					m->exports->procs[n].function(l);
					/* we shouldn't get here */
					exit(0);
				}
			}
			/* run post-fork function */
			if (m->exports->procs[n].post_fork_function)
				if (m->exports->procs[n].post_fork_function()!=0) {
					LM_ERR("post-fork function failed for process \"%s\" "
						"in module %s\n",
						m->exports->procs[n].name, m->exports->name);
					return -1;
				}
		}
	}

	return 0;
}
コード例 #4
0
ファイル: net_tcp.c プロジェクト: Danfx/opensips
int tcp_start_processes(int *chd_rank, int *startup_done)
{
	int r, n;
	int reader_fd[2]; /* for comm. with the tcp children read  */
	pid_t pid;
	struct socket_info *si;
	stat_var *load_p = NULL;

	if (tcp_disabled)
		return 0;

	/* estimate max fd. no:
	 * 1 tcp send unix socket/all_proc,
	 *  + 1 udp sock/udp proc + 1 tcp_child sock/tcp child*
	 *  + no_listen_tcp */
	for( r=0,n=PROTO_FIRST ; n<PROTO_LAST ; n++ )
		if ( is_tcp_based_proto(n) )
			for(si=protos[n].listeners; si ; si=si->next,r++ );

	if (register_tcp_load_stat( &load_p )!=0) {
		LM_ERR("failed to init tcp load statistic\n");
		goto error;
	}

	/* start the TCP workers & create the socket pairs */
	for(r=0; r<tcp_children_no; r++){
		/* create sock to communicate from TCP main to worker */
		if (socketpair(AF_UNIX, SOCK_STREAM, 0, reader_fd)<0){
			LM_ERR("socketpair failed: %s\n", strerror(errno));
			goto error;
		}

		(*chd_rank)++;
		pid=internal_fork("SIP receiver TCP");
		if (pid<0){
			LM_ERR("fork failed\n");
			goto error;
		}else if (pid>0){
			/* parent */
			close(reader_fd[1]);
			tcp_children[r].pid=pid;
			tcp_children[r].proc_no=process_no;
			tcp_children[r].busy=0;
			tcp_children[r].n_reqs=0;
			tcp_children[r].unix_sock=reader_fd[0];
		}else{
			/* child */
			set_proc_attrs("TCP receiver");
			pt[process_no].idx=r;
			pt[process_no].load = load_p;
			if (init_child(*chd_rank) < 0) {
				LM_ERR("init_children failed\n");
				report_failure_status();
				if (startup_done)
					*startup_done = -1;
				exit(-1);
			}

			/* was startup route executed so far ? */
			if (startup_done!=NULL && *startup_done==0 && r==0) {
				LM_DBG("runing startup for first TCP\n");
				if(run_startup_route()< 0) {
					LM_ERR("Startup route processing failed\n");
					report_failure_status();
					*startup_done = -1;
					exit(-1);
				}
				*startup_done = 1;
			}

			report_conditional_status( 1, 0);

			tcp_worker_proc( reader_fd[1] );
			exit(-1);
		}
	}

	/* wait for the startup route to be executed */
	if (startup_done)
		while (!(*startup_done)) {
			usleep(5);
			handle_sigs();
		}

	/* start the TCP manager process */
	if ( (pid=internal_fork( "TCP main"))<0 ) {
		LM_CRIT("cannot fork tcp main process\n");
		goto error;
	}else if (pid==0){
			/* child */
		/* close the TCP inter-process sockets */
		close(unix_tcp_sock);
		unix_tcp_sock = -1;
		close(pt[process_no].unix_sock);
		pt[process_no].unix_sock = -1;

		report_conditional_status( (!no_daemon_mode), 0);

		tcp_main_server();
		exit(-1);
	}

	return 0;
error:
	return -1;
}
コード例 #5
0
ファイル: main.c プロジェクト: Parantido/opensips
/**
 * Main loop, forks the children, bind to addresses,
 * handle signals.
 * \return don't return on sucess, -1 on error
 */
static int main_loop(void)
{
	static int chd_rank;
	int* startup_done = NULL;

	chd_rank=0;

	if (start_module_procs()!=0) {
		LM_ERR("failed to fork module processes\n");
		goto error;
	}

	if(startup_rlist.a) {/* if a startup route was defined */
		startup_done = (int*)shm_malloc(sizeof(int));
		if(startup_done == NULL) {
			LM_ERR("No more shared memory\n");
			goto error;
		}
		*startup_done = 0;
	}

	/* fork for the timer process*/
	if (start_timer_processes()!=0) {
		LM_CRIT("cannot start timer process(es)\n");
		goto error;
	}

	/* fork all processes required by UDP network layer */
	if (udp_start_processes( &chd_rank, startup_done)<0) {
		LM_CRIT("cannot start TCP processes\n");
		goto error;
	}

	/* fork all processes required by TCP network layer */
	if (tcp_start_processes( &chd_rank, startup_done)<0) {
		LM_CRIT("cannot start TCP processes\n");
		goto error;
	}

	/* this is the main process -> it shouldn't send anything */
	bind_address=0;

	if (startup_done) {
		if (*startup_done==0)
			LM_CRIT("BUG: startup route defined, but not run :( \n");
		shm_free(startup_done);
	}

	/* main process left */
	is_main=1;
	set_proc_attrs("attendant");

	if (init_child(PROC_MAIN) < 0) {
		LM_ERR("error in init_child for PROC_MAIN\n");
		report_failure_status();
		goto error;
	}

	report_conditional_status( (!no_daemon_mode), 0);

	for(;;){
			handle_sigs();
			pause();
	}

	/*return 0; */
error:
	is_main=1;  /* if we are here, we are the "main process",
				  any forked children should exit with exit(-1) and not
				  ever use return */
	report_failure_status();
	return -1;

}