Exemple #1
0
static apr_status_t piped_log_cleanup(void *data)
{
    piped_log *pl = data;

    if (pl->pid != NULL) {
        apr_proc_kill(pl->pid, SIGTERM);
    }
    return piped_log_cleanup_for_exec(data);
}
Exemple #2
0
static void piped_log_maintenance(int reason, void *data, apr_wait_t status)
{
    piped_log *pl = data;
    apr_status_t stats;
    int mpm_state;

    switch (reason) {
    case APR_OC_REASON_DEATH:
    case APR_OC_REASON_LOST:
        pl->pid = NULL; /* in case we don't get it going again, this
                         * tells other logic not to try to kill it
                         */
        apr_proc_other_child_unregister(pl);
        stats = ap_mpm_query(AP_MPMQ_MPM_STATE, &mpm_state);
        if (stats != APR_SUCCESS) {
            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, NULL,
                         "can't query MPM state; not restarting "
                         "piped log program '%s'",
                         pl->program);
        }
        else if (mpm_state != AP_MPMQ_STOPPING) {
            ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, NULL,
                         "piped log program '%s' failed unexpectedly",
                         pl->program);
            if ((stats = piped_log_spawn(pl)) != APR_SUCCESS) {
                /* what can we do?  This could be the error log we're having
                 * problems opening up... */
                char buf[120];
                ap_log_error(APLOG_MARK, APLOG_STARTUP, 0, NULL,
                             "piped_log_maintenance: unable to respawn '%s': %s",
                             pl->program, apr_strerror(stats, buf, sizeof(buf)));
            }
        }
        break;

    case APR_OC_REASON_UNWRITABLE:
        /* We should not kill off the pipe here, since it may only be full.
         * If it really is locked, we should kill it off manually. */
    break;

    case APR_OC_REASON_RESTART:
        if (pl->pid != NULL) {
            apr_proc_kill(pl->pid, SIGTERM);
            pl->pid = NULL;
        }
        break;

    case APR_OC_REASON_UNREGISTER:
        break;
    }
}
Exemple #3
0
static int proc_kill(lua_State *L)
{
  const char *options[] = {
    "never", "always", "timeout", "wait", "once", NULL,
  };

  const apr_kill_conditions_e values[] = {
    APR_KILL_NEVER, APR_KILL_ALWAYS, APR_KILL_AFTER_TIMEOUT,
    APR_JUST_WAIT, APR_KILL_ONLY_ONCE,
  };

  apr_status_t status;
  lua_apr_proc *process;
  int option;

  process = proc_check(L, 1);
  option = values[luaL_checkoption(L, 2, NULL, options)];
  status = apr_proc_kill(&process->handle, option);

  return push_status(L, status);
}
Exemple #4
0
/* It would be great if we could stress this stuff more, and make the test
 * more granular.
 */
static void test_child_kill(abts_case *tc, void *data)
{
    apr_file_t *std = NULL;
    apr_proc_t newproc;
    apr_procattr_t *procattr = NULL;
    const char *args[3];
    apr_status_t rv;

    args[0] = apr_pstrdup(p, "occhild" EXTENSION);
    args[1] = apr_pstrdup(p, "-X");
    args[2] = NULL;

    rv = apr_procattr_create(&procattr, p);
    ABTS_INT_EQUAL(tc, APR_SUCCESS, rv);

    rv = apr_procattr_io_set(procattr, APR_FULL_BLOCK, APR_NO_PIPE, 
                             APR_NO_PIPE);
    ABTS_INT_EQUAL(tc, APR_SUCCESS, rv);

    rv = apr_proc_create(&newproc, "./occhild" EXTENSION, args, NULL, procattr, p);
    ABTS_INT_EQUAL(tc, APR_SUCCESS, rv);
    ABTS_PTR_NOTNULL(tc, newproc.in);
    ABTS_PTR_EQUAL(tc, NULL, newproc.out);
    ABTS_PTR_EQUAL(tc, NULL, newproc.err);

    std = newproc.in;

    apr_proc_other_child_register(&newproc, ocmaint, NULL, std, p);

    apr_sleep(apr_time_from_sec(1));
    rv = apr_proc_kill(&newproc, SIGKILL);
    ABTS_INT_EQUAL(tc, APR_SUCCESS, rv);
    
    /* allow time for things to settle... */
    apr_sleep(apr_time_from_sec(3));
    
    apr_proc_other_child_refresh_all(APR_OC_REASON_RUNNING);
    ABTS_STR_EQUAL(tc, "APR_OC_REASON_DEATH", reasonstr);
}    
Exemple #5
0
apr_status_t proc_kill_force(fcgid_procnode *procnode,
                             server_rec *main_server)
{
    return apr_proc_kill(&(procnode->proc_id), SIGKILL);
}
Exemple #6
0
static void im_exec_stop(nx_module_t *module)
{
    nx_im_exec_conf_t *imconf;
    int i;
    boolean sigterm_sent = FALSE;
    apr_exit_why_e exitwhy;
    int exitval;
    int sig_num;
    apr_status_t rv;
    apr_status_t stopped = APR_SUCCESS;

    ASSERT(module != NULL);
    imconf = (nx_im_exec_conf_t *) module->config;
    ASSERT(imconf != NULL);

    log_debug("im_exec stopped");

    if ( module->input.desc.f != NULL )
    {
	apr_file_close(module->input.desc.f);
	apr_pool_clear(module->input.pool);
	module->input.desc.f = NULL;
    }

    if ( imconf->running == TRUE )
    {
	for ( i = 0; i < 50; i++ )
	{
	    if ( (rv = apr_proc_wait(&(imconf->proc), &exitval, &exitwhy, APR_NOWAIT)) != APR_SUCCESS )
	    {
		if ( APR_STATUS_IS_CHILD_DONE(rv) )
		{
		    rv = APR_SUCCESS;
		    break;
		}
		else if ( i >= 30 )
		{ // still running, kill it after 3 sec
		    if ( sigterm_sent == FALSE )
		    {
			sigterm_sent = TRUE;
#ifdef WIN32
			sig_num = 1;
#else
			sig_num = SIGTERM;
#endif
		    }
		    else
		    {
			if ( i <= 31 )
			{
			    log_warn("process %s did not exit, killing it.", imconf->cmd);
			}
#ifdef WIN32
			sig_num = 1;
#else
			sig_num = SIGKILL;
#endif
		    }
		    if ( (rv = apr_proc_kill(&(imconf->proc), sig_num)) != APR_SUCCESS )
		    {
			stopped = rv;
		    }
		}
	    }
	    apr_sleep(APR_USEC_PER_SEC / 10);
	}
	if ( !((stopped == APR_SUCCESS) || APR_STATUS_IS_ENOPROC(stopped)) )
	{
	    log_aprerror(stopped, "im_exec couldn't stop process");
	}
    }
    imconf->event = NULL;
}
Exemple #7
0
/** Kill a process with a given pid.
 *
 * Used to from the apache module thread to kill the trell master job, and 
 * we try to wait and determine if the process is dead.
 */
static int
trell_kill_process( trell_sconf_t* svr_conf,  request_rec* r, pid_t pid )
{
    int i;
    apr_status_t rv;

    // Shaky..?
    apr_proc_t proc;
    
    proc.pid = pid;
    proc.in = NULL;
    proc.out = NULL;
    proc.err = NULL;
    
    
    // This is slightly shaky as well, since we're not necessarily the parent
    // process, and if the child isn't waited upon, we have a defunct/zombie.
    
    rv = apr_proc_kill( &proc, SIGTERM );
    if( rv != APR_SUCCESS ) {
        ap_log_rerror( APLOG_MARK, APLOG_NOTICE, rv, r, "mod_trell: %s@%d", __FILE__, __LINE__ );
        return rv;
    }
    ap_log_rerror( APLOG_MARK, APLOG_NOTICE, OK, r, "mod_trell: Sent pid=%d SIGTERM", proc.pid );
    apr_sleep( 1000 ); // Slight wait to let process hopefully terminate.
    for(i=0; i<3; i++ ) {
        // Check if child is dead. However, it is not safe to assume that the
        // master is child of current process.
        int exitcode;
        apr_exit_why_e why=0;
        rv = apr_proc_wait( &proc, &exitcode, &why, APR_NOWAIT );
        if( rv == APR_CHILD_DONE ) {
            ap_log_rerror( APLOG_MARK, APLOG_NOTICE, OK, r, "mod_trell: SIGTERM why=%d", why );
            return APR_SUCCESS;
        }
        
        // Wait failed, check to see if the messenger still lives... If not,
        // we assume it's dead.
        struct messenger msgr;
        messenger_status_t status = messenger_init( &msgr, svr_conf->m_master_id );
        if( status != MESSENGER_OK ) {
            ap_log_rerror( APLOG_MARK, APLOG_NOTICE, OK, r, "mod_trell: failed to get master messenger, assuming master is dead." );
            return APR_SUCCESS;
        }
        messenger_free( &msgr );
        
        ap_log_rerror( APLOG_MARK, APLOG_NOTICE, OK, r, "mod_trell: Child not done, sleeping it=%d", i );
        apr_sleep( 1000000 );
    }
    

    rv = apr_proc_kill( &proc, SIGKILL );
    apr_sleep( 1000 ); // Slight wait to let process hopefully terminate.
    if( rv != APR_SUCCESS ) {
        ap_log_rerror( APLOG_MARK, APLOG_NOTICE, rv, r, "mod_trell: %s@%d", __FILE__, __LINE__ );
        return rv;
    }
    ap_log_rerror( APLOG_MARK, APLOG_NOTICE, OK, r, "mod_trell: Sent pid=%d SIGKILL", proc.pid );
    for(i=0; i<3; i++ ) {
        int exitcode;
        apr_exit_why_e why=0;
        rv = apr_proc_wait( &proc, &exitcode, &why, APR_NOWAIT );
        if( rv == APR_CHILD_DONE ) {
            ap_log_rerror( APLOG_MARK, APLOG_NOTICE, OK, r, "mod_trell: SIGKILL why=%d", why );
            return APR_SUCCESS;
        }

        struct messenger msgr;
        messenger_status_t status = messenger_init( &msgr, svr_conf->m_master_id );
        if( status != MESSENGER_OK ) {
            ap_log_rerror( APLOG_MARK, APLOG_NOTICE, OK, r, "mod_trell: failed to get master messenger, assuming master is dead." );
            return APR_SUCCESS;
        }
        messenger_free( &msgr );
 
        ap_log_rerror( APLOG_MARK, APLOG_NOTICE, OK, r, "mod_trell: Child not done, sleeping it=%d", i );
        apr_sleep( 1000000 );
    }
    ap_log_rerror( APLOG_MARK, APLOG_CRIT, OK, r, "mod_trell: Failed to kill master job." );
}