Exemple #1
0
void na_env_init(na_env_t *env)
{
    env->current_conn      = 0;
    env->is_refused_active = false;
    env->is_refused_accept = false;
    env->is_worker_busy    = calloc(sizeof(bool), env->worker_max);
    for (int j=0;j<env->worker_max;++j) {
        env->is_worker_busy[j] = false;
    }
    env->current_conn_max = 0;
    pthread_mutex_init(&env->lock_connpool,     NULL);
    pthread_mutex_init(&env->lock_current_conn, NULL);
    pthread_mutex_init(&env->lock_tid,          NULL);
    pthread_mutex_init(&env->lock_loop,         NULL);
    pthread_rwlock_init(&env->lock_refused, NULL);
    env->lock_worker_busy = calloc(sizeof(pthread_rwlock_t), env->worker_max);
    for (int j=0;j<env->worker_max;++j) {
        pthread_rwlock_init(&env->lock_worker_busy[j], NULL);
    }
    na_connpool_create(&env->connpool_active, env->connpool_max);
    if (env->is_use_backup) {
        na_connpool_create(&env->connpool_backup, env->connpool_max);
    }
}
Exemple #2
0
int main (int argc, char *argv[])
{
    pthread_t           th[NA_ENV_MAX];
    na_env_t           *env[NA_ENV_MAX];
    mpool_t            *env_pool;
    int                 c;
    int                 env_cnt          = 0;
    bool                is_daemon        = false;
    struct json_object *conf_obj         = NULL;
    struct json_object *environments_obj = NULL;

    while (-1 != (c = getopt(argc, argv,
           "f:" /* configuration file with JSON */
           "t:" /* check configuration file */
           "d"  /* go to background */
           "v"  /* show version and information */
           "h"  /* show help */
    )))
    {
        switch (c) {
        case 'd':
            is_daemon = true;
            break;
        case 'f':
            ConfFile         = optarg;
            conf_obj         = na_get_conf(optarg);
            environments_obj = na_get_environments(conf_obj, &env_cnt);
            break;
        case 't':
            conf_obj         = na_get_conf(optarg);
            environments_obj = na_get_environments(conf_obj, &env_cnt);
            printf("JSON configuration is OK\n");
            return 0;
            break;
        case 'v':
            na_version();
            return 0;
            break;
        case 'h':
            na_usage();
            return 0;
            break;
        default:
            break;
        }
    }

    if (is_daemon && daemon(0, 0) == -1) {
        NA_DIE_WITH_ERROR(NA_ERROR_FAILED_DAEMONIZE);
    }

    if (env_cnt > NA_ENV_MAX) {
        NA_DIE_WITH_ERROR(NA_ERROR_TOO_MANY_ENVIRONMENTS);
    }

    StartTimestamp = time(NULL);
    na_setup_signals();
    na_memproto_bm_skip_init();

    env_pool = mpool_create(0);
    if (env_cnt == 0) {
        env_cnt = 1;
        env[0]  = na_env_add(&env_pool);
        na_env_setup_default(env[0], 0);
    } else {
        for (int i=0;i<env_cnt;++i) {
            env[i] = na_env_add(&env_pool);
            na_env_setup_default(env[i], i);
            na_conf_env_init(environments_obj, env[i], i, false);
        }
    }

    json_object_put(conf_obj);

    for (int i=0;i<env_cnt;++i) {
        env[i]->current_conn      = 0;
        env[i]->is_refused_active = false;
        env[i]->is_refused_accept = false;
        env[i]->is_worker_busy    = calloc(sizeof(bool), env[i]->worker_max);
        for (int j=0;j<env[i]->worker_max;++j) {
            env[i]->is_worker_busy[j] = false;
        }
        env[i]->error_count      = 0;
        env[i]->current_conn_max = 0;
        pthread_mutex_init(&env[i]->lock_connpool, NULL);
        pthread_mutex_init(&env[i]->lock_current_conn, NULL);
        pthread_mutex_init(&env[i]->lock_tid, NULL);
        pthread_mutex_init(&env[i]->lock_loop, NULL);
        pthread_mutex_init(&env[i]->lock_error_count, NULL);
        pthread_rwlock_init(&env[i]->lock_refused, NULL);
        pthread_rwlock_init(&env[i]->lock_request_bufsize_max, NULL);
        pthread_rwlock_init(&env[i]->lock_response_bufsize_max, NULL);
        pthread_rwlock_init(&LockReconf, NULL);
        env[i]->lock_worker_busy = calloc(sizeof(pthread_rwlock_t), env[i]->worker_max);
        for (int j=0;j<env[i]->worker_max;++j) {
            pthread_rwlock_init(&env[i]->lock_worker_busy[j], NULL);
        }
        na_connpool_create(&env[i]->connpool_active, env[i]->connpool_max);
        if (env[i]->is_use_backup) {
            na_connpool_create(&env[i]->connpool_backup, env[i]->connpool_max);
        }
    }

    for (int i=0;i<env_cnt;++i) {
        pthread_create(&th[i], NULL, na_event_loop, env[i]);
    }

    // monitoring signal
    while (true) {

        if (SigExit == 1) {
            break;
        }

        if (SigReconf == 1) {
            conf_obj         = na_get_conf(ConfFile);
            environments_obj = na_get_environments(conf_obj, &env_cnt);

            pthread_rwlock_wrlock(&LockReconf);
            for (int i=0;i<env_cnt;++i) {
                na_conf_env_init(environments_obj, env[i], i, true);
            }
            pthread_rwlock_unlock(&LockReconf);

            json_object_put(conf_obj);
            SigReconf = 0;
        }

        // XXX we should sleep forever and only wake upon a signal
        sleep(1);
    }

    for (int i=0;i<env_cnt;++i) {
        na_connpool_destroy(&env[i]->connpool_active);
        if (env[i]->is_use_backup) {
            na_connpool_destroy(&env[i]->connpool_backup);
        }
        pthread_mutex_destroy(&env[i]->lock_connpool);
        pthread_mutex_destroy(&env[i]->lock_current_conn);
        pthread_mutex_destroy(&env[i]->lock_tid);
        pthread_mutex_destroy(&env[i]->lock_error_count);
        pthread_rwlock_destroy(&env[i]->lock_refused);
        pthread_rwlock_destroy(&env[i]->lock_request_bufsize_max);
        pthread_rwlock_destroy(&env[i]->lock_response_bufsize_max);
        pthread_rwlock_destroy(&LockReconf);
        for (int j=0;j<env[i]->worker_max;++j) {
            pthread_rwlock_destroy(&env[i]->lock_worker_busy[j]);
        }
        NA_FREE(env[i]->is_worker_busy);
        NA_FREE(env[i]->lock_worker_busy);
        pthread_detach(th[i]);
    }

    mpool_destroy(env_pool);

    return 0;
}