int
main(int argc, char ** argv) {
    evbase_t         * evbase      = event_base_new();
    evhtp_t          * htp         = evhtp_new(evbase, NULL);
    evhtp_callback_t * cb_plurals  = NULL;
    evhtp_callback_t * cb_score    = NULL;
    int                num_threads = 6;

    cb_plurals = evhtp_set_cb(htp, "/blahblah/plurals", receive_plurals, "plurals");
    cb_score = evhtp_set_cb(htp, "/blahblah/score", provide_score, "score");
#ifndef EVHTP_DISABLE_EVTHR
    evhtp_use_threads(htp, NULL, num_threads, NULL);
#else
    if (num_threads != 1) {
        printf("Error: multithreading is not supported\n");
        exit(1);
    }
#endif
    evhtp_bind_socket(htp, "0.0.0.0", 8081, 1024);

    event_base_loop(evbase, 0);

    evhtp_unbind_socket(htp);
    evhtp_callback_free(cb_score);
    evhtp_callback_free(cb_plurals);
    evhtp_free(htp);
    event_base_free(evbase);

    return 0;
}
Esempio n. 2
0
void HttpStack::start(evhtp_thread_init_cb init_cb)
{
  initialize();

  int rc = evhtp_use_threads(_evhtp, init_cb, _num_threads, this);
  if (rc != 0)
  {
    throw Exception("evhtp_use_threads", rc); // LCOV_EXCL_LINE
  }

  // If the bind address is IPv6 evhtp needs to be told by prepending ipv6 to
  // the  parameter.  Use getaddrinfo() to analyse the bind_address.
  addrinfo hints;
  memset(&hints, 0, sizeof(hints));
  hints.ai_family = AF_UNSPEC;    // To allow both IPv4 and IPv6 addresses.
  hints.ai_socktype = SOCK_STREAM;
  addrinfo* servinfo = NULL;

  std::string full_bind_address = _bind_address;
  std::string local_bind_address = "127.0.0.1";
  const int error_num = getaddrinfo(_bind_address.c_str(), NULL, &hints, &servinfo);

  if ((error_num == 0) &&
      (servinfo->ai_family == AF_INET6))
  {
    full_bind_address = "ipv6:" + full_bind_address;
    local_bind_address = "ipv6:::1";
  }

  freeaddrinfo(servinfo);

  rc = evhtp_bind_socket(_evhtp, full_bind_address.c_str(), _bind_port, 1024);
  if (rc != 0)
  {
    LOG_ERROR("evhtp_bind_socket failed with address %s and port %d", full_bind_address.c_str(), _bind_port);
    throw Exception("evhtp_bind_socket", rc); // LCOV_EXCL_LINE
  }

  if (local_bind_address != full_bind_address) {
    rc = evhtp_bind_socket(_evhtp, local_bind_address.c_str(), _bind_port, 1024);
    if (rc != 0)
    {
      LOG_ERROR("evhtp_bind_socket failed with address %s and port %d", local_bind_address.c_str(), _bind_port);
      throw Exception("evhtp_bind_socket - localhost", rc); // LCOV_EXCL_LINE
    }
  }

  rc = pthread_create(&_event_base_thread, NULL, event_base_thread_fn, this);
  if (rc != 0)
  {
    throw Exception("pthread_create", rc); // LCOV_EXCL_LINE
  }
}
Esempio n. 3
0
int main() {
    evbase_t *evbase = event_base_new();
    evhtp_t *htp = evhtp_new(evbase, NULL);

    fprintf(stdout, "Welcome to CAvatar.\n");

    // A place for our images
    mkdir(imgfolder, 0700);

    // A few static routes
    evhtp_set_cb(htp, "/", route_index, NULL);
    evhtp_set_cb(htp, "/favicon.ico", route_favicon, NULL);

    // Metas
    evhtp_set_regex_cb(htp, "[\\/](meta)[\\/]([0-9a-fA-F]{32})", route_meta, NULL);

    // Images
    evhtp_set_regex_cb(htp, "[\\/](avatar)[\\/]([0-9a-fA-F]{32})", route_image, NULL);
    evhtp_set_regex_cb(htp, "[\\/]([0-9a-fA-F]{32})", route_image, NULL);

    // 404 routes
    evhtp_set_regex_cb(htp, "[\\/](.{1,})", route_generic, NULL);
    evhtp_set_gencb(htp, route_generic, NULL);

    // libevhtp has a cool wrapper for pthreads
    evhtp_use_threads(htp, NULL, threads, NULL);

    // aaaand bind a socket..
    if (evhtp_bind_socket(htp, "0.0.0.0", port, 1024) < 0) {
        fprintf(stderr, "Could not bind to socket %d: %s\n", port, strerror(errno));
        exit(-1);
    }
    fprintf(stdout, "Binded to socket %d\n", port);

    // and listen!
    event_base_loop(evbase, 0);

    // free stuff after event loop
    evhtp_unbind_socket(htp);
    evhtp_free(htp);
    event_base_free(evbase);
    //MagickWandTerminus();

    return 0;
}
Esempio n. 4
0
/* Terminate gracefully on SIGTERM */
void
sigterm_cb(int fd, short event, void * arg) {
    evbase_t     * evbase = (evbase_t *)arg;
    struct timeval tv     = { .tv_usec = 100000, .tv_sec = 0 }; /* 100 ms */

    event_base_loopexit(evbase, &tv);
}

void
init_thread_cb(evhtp_t * htp, evthr_t * thr, void * arg) {
    static int aux = 0;

    printf("Spinning up a thread: %d\n", ++aux);
    evthr_set_aux(thr, &aux);
}

int
main(int argc, char ** argv) {
    struct event *ev_sigterm;
    evbase_t    * evbase  = event_base_new();
    evhtp_t     * evhtp   = evhtp_new(evbase, NULL);

    evhtp_set_gencb(evhtp, frontend_cb, NULL);

#ifndef EVHTP_DISABLE_SSL
    evhtp_ssl_cfg_t scfg1 = { 0 };

    scfg1.pemfile  = "./server.pem";
    scfg1.privfile = "./server.pem";

    evhtp_ssl_init(evhtp, &scfg1);
#endif

    evhtp_use_threads(evhtp, init_thread_cb, 8, NULL);
#ifndef WIN32
    ev_sigterm = evsignal_new(evbase, SIGTERM, sigterm_cb, evbase);
    evsignal_add(ev_sigterm, NULL);
#endif
    evhtp_bind_socket(evhtp, "0.0.0.0", 8081, 1024);
    event_base_loop(evbase, 0);

    printf("Clean exit\n");
    return 0;
}
Esempio n. 5
0
int
main(int argc, char ** argv) {
    evbase_t * evbase = event_base_new();
    evhtp_t  * htp    = evhtp_new(evbase, NULL);
    
    evhtp_set_cb(htp, "/test", webif_test, NULL);
	evhtp_set_gencb(htp, webif_default, NULL);
	
#ifndef EVHTP_DISABLE_EVTHR
    evhtp_use_threads(htp, NULL, 8, NULL);
#endif
    evhtp_bind_socket(htp, "0.0.0.0", 8081, 2048);

    event_base_loop(evbase, 0);

    evhtp_unbind_socket(htp);
    evhtp_free(htp);
    event_base_free(evbase);

    return 0;
}
Esempio n. 6
0
int
main(int argc, char ** argv) {
    struct event     * ev_sigint;
    evbase_t         * evbase = NULL;
    evhtp_t          * htp    = NULL;
    evhtp_callback_t * cb_1   = NULL;
    evhtp_callback_t * cb_2   = NULL;
    evhtp_callback_t * cb_3   = NULL;
    evhtp_callback_t * cb_4   = NULL;
    evhtp_callback_t * cb_5   = NULL;

#ifndef EVHTP_DISABLE_REGEX
    evhtp_callback_t * cb_6   = NULL;
#endif
    evhtp_callback_t * cb_7   = NULL;
#ifndef EVHTP_DISABLE_REGEX
    evhtp_callback_t * cb_8   = NULL;
#endif
    evhtp_callback_t * cb_9   = NULL;
    evhtp_callback_t * cb_10  = NULL;
    evhtp_callback_t * cb_11  = NULL;
    evhtp_callback_t * cb_12  = NULL;

    if (parse_args(argc, argv) < 0) {
        exit(1);
    }

    srand((unsigned)time(NULL));

    evbase = event_base_new();
    htp    = evhtp_new(evbase, NULL);

    evhtp_set_parser_flags(htp, EVHTP_PARSE_QUERY_FLAG_LENIENT);
    evhtp_set_max_keepalive_requests(htp, max_keepalives);

    //htp->enable_nodelay = 1;
    //htp->enable_defer_accept = 1;
    htp->enable_reuseport = 1;

    cb_1   = evhtp_set_cb(htp, "/ref", test_default_cb, "fjdkls");
    cb_2   = evhtp_set_cb(htp, "/foo", test_foo_cb, "bar");
    cb_3   = evhtp_set_cb(htp, "/foo/", test_foo_cb, "bar");
    cb_4   = evhtp_set_cb(htp, "/bar", test_bar_cb, "baz");
    cb_5   = evhtp_set_cb(htp, "/500", test_500_cb, "500");
#ifndef EVHTP_DISABLE_REGEX
    cb_6   = evhtp_set_regex_cb(htp, "^(/anything/).*", test_regex, NULL);
#endif
    cb_7   = evhtp_set_cb(htp, "/pause", test_pause_cb, NULL);
#ifndef EVHTP_DISABLE_REGEX
    cb_8   = evhtp_set_regex_cb(htp, "^/create/(.*)", create_callback, NULL);
#endif
    cb_9   = evhtp_set_glob_cb(htp, "*/glob/*", test_glob_cb, NULL);
    cb_10  = evhtp_set_cb(htp, "/max_body_size", test_max_body, NULL);

    /* set a callback to test out chunking API */
    cb_11  = evhtp_set_cb(htp, "/chunkme", test_chunking, NULL);

    /* set a callback which takes ownership of the underlying bufferevent and
     * just starts echoing things
     */
    cb_12  = evhtp_set_cb(htp, "/ownme", test_ownership, NULL);

    /* set a callback to pause on each header for cb_7 */
    evhtp_set_hook(&cb_7->hooks, evhtp_hook_on_path, pause_init_cb, NULL);

    /* set a callback to set hooks specifically for the cb_6 callback */
#ifndef EVHTP_DISABLE_REGEX
    evhtp_set_hook(&cb_6->hooks, evhtp_hook_on_headers, test_regex_hdrs_cb, NULL);
#endif

    evhtp_set_hook(&cb_10->hooks, evhtp_hook_on_headers, set_max_body, NULL);

    /* set a default request handler */
    evhtp_set_gencb(htp, test_default_cb, "foobarbaz");

    /* set a callback invoked before a connection is accepted */
    //evhtp_set_pre_accept_cb(htp, test_pre_accept, &bind_port);

    /* set a callback to set per-connection hooks (via a post_accept cb) */
    evhtp_set_post_accept_cb(htp, set_my_connection_handlers, NULL);

#ifndef EVHTP_DISABLE_SSL
    if (ssl_pem != NULL) {
        evhtp_ssl_cfg_t scfg = {
            .pemfile            = ssl_pem,
            .privfile           = ssl_pem,
            .cafile             = ssl_ca,
            .capath             = ssl_capath,
            .ciphers            = "RC4+RSA:HIGH:+MEDIUM:+LOW",
            .ssl_opts           = SSL_OP_NO_SSLv2,
            .ssl_ctx_timeout    = 60 * 60 * 48,
            .verify_peer        = SSL_VERIFY_PEER,
            .verify_depth       = 42,
            .x509_verify_cb     = dummy_ssl_verify_callback,
            .x509_chk_issued_cb = dummy_check_issued_cb,
            .scache_type        = evhtp_ssl_scache_type_internal,
            .scache_size        = 1024,
            .scache_timeout     = 1024,
            .scache_init        = NULL,
            .scache_add         = NULL,
            .scache_get         = NULL,
            .scache_del         = NULL,
        };

        evhtp_ssl_init(htp, &scfg);
#ifndef EVHTP_DISABLE_EVTHR
        if (use_threads) {
            #define OPENSSL_THREAD_DEFINES
#include <openssl/opensslconf.h>
#if defined(OPENSSL_THREADS)
#else
            fprintf(stderr, "Your version of OpenSSL does not support threading!\n");
            exit(-1);
#endif
        }
#endif
    }
#endif

#ifndef EVHTP_DISABLE_EVTHR
    if (use_threads) {
        evhtp_use_threads(htp, NULL, num_threads, NULL);
    }
#endif

    if (evhtp_bind_socket(htp, bind_addr, bind_port, backlog) < 0) {
        fprintf(stderr, "Could not bind socket: %s\n", strerror(errno));
        exit(-1);
    }

    ev_sigint = evsignal_new(evbase, SIGINT, sigint, evbase);
    evsignal_add(ev_sigint, NULL);

    event_base_loop(evbase, 0);

    event_free(ev_sigint);
    evhtp_unbind_socket(htp);

    evhtp_free(htp);
    event_base_free(evbase);

    return 0;
} /* main */
Esempio n. 7
0
int
main(int argc, char *argv[])
{
    evbase_t *evbase = NULL;
    evhtp_t *htp = NULL;
    int daemon_mode = 1;
    int c;
    char *logfile = NULL;
    char *ccnet_debug_level_str = "info";
    char *http_debug_level_str = "debug";
    const char *debug_str = NULL;

    config_dir = DEFAULT_CONFIG_DIR;

    while ((c = getopt_long(argc, argv,
                short_opts, long_opts, NULL)) != EOF) {
        switch (c) {
        case 'h':
            usage();
            exit(0);
        case 'v':
            exit(-1);
            break;
        case 'c':
            config_dir = strdup(optarg);
            break;
        case 'd':
            seafile_dir = strdup(optarg);
            break;
        case 'p':
            bind_port = atoi(optarg);
            break;
        case 'b':
            bind_addr = strdup(optarg);
            break;
        case 't':
            num_threads = atoi(optarg);
            break;
        case 'r':
            root_dir = strdup(optarg);
            break;
        case 'f':
            daemon_mode = 0;
            break;
        case 'l':
            logfile = g_strdup(optarg);
            break;
        case 'g':
            ccnet_debug_level_str = optarg;
            break;
        case 'G':
            http_debug_level_str = optarg;
            break;
        case 'D':
            debug_str = optarg;
            break;
        default:
            usage();
            exit(-1);
        }
    }

#ifndef WIN32    
    if (daemon_mode)
        daemon(1, 0);
#endif    

    g_type_init();

    ccnet_client = ccnet_client_new();
    if ((ccnet_client_load_confdir(ccnet_client, config_dir)) < 0) {
        g_warning ("Read config dir error\n");
        return -1;
    }

    if (seafile_dir == NULL)
        seafile_dir = g_build_filename (config_dir, "seafile-data", NULL);
    if (logfile == NULL)
        logfile = g_build_filename (seafile_dir, "http.log", NULL);
    
    seaf = seafile_session_new(seafile_dir, ccnet_client);
    if (!seaf) {
        g_warning ("Failed to create seafile session.\n");
        exit (1);
    }
    seafile_session_init(seaf);

    seaf->client_pool = ccnet_client_pool_new (config_dir);

    if (!debug_str)
        debug_str = g_getenv("SEAFILE_DEBUG");
    seafile_debug_set_flags_string (debug_str);

    if (seafile_log_init (logfile, ccnet_debug_level_str,
                          http_debug_level_str) < 0) {
        g_warning ("Failed to init log.\n");
        exit (1);
    }

    evbase = event_base_new();
    htp = evhtp_new(evbase, NULL);

    if (access_file_init (htp) < 0)
        exit (1);

    if (upload_file_init (htp) < 0)
        exit (1);
    
    evhtp_set_gencb(htp, default_cb, NULL);

    evhtp_use_threads(htp, NULL, num_threads, NULL);

    if (evhtp_bind_socket(htp, bind_addr, bind_port, 128) < 0) {
        g_warning ("Could not bind socket: %s\n", strerror(errno));
        exit(-1);
    }

    event_base_loop(evbase, 0);

    return 0;
}
Esempio n. 8
0
File: test.c Progetto: pibi/libevhtp
int
main(int argc, char ** argv) {
    evbase_t         * evbase = NULL;
    evhtp_t          * htp    = NULL;
    evhtp_callback_t * cb_1   = NULL;
    evhtp_callback_t * cb_2   = NULL;
    evhtp_callback_t * cb_3   = NULL;
    evhtp_callback_t * cb_4   = NULL;
    evhtp_callback_t * cb_5   = NULL;
    evhtp_callback_t * cb_6   = NULL;
    evhtp_callback_t * cb_7   = NULL;
    evhtp_callback_t * cb_8   = NULL;

    if (parse_args(argc, argv) < 0) {
        exit(1);
    }

    srand((unsigned)time(NULL));

    evbase = event_base_new();
    htp    = evhtp_new(evbase, NULL);

    cb_1   = evhtp_set_cb(htp, "/ref", test_default_cb, "fjdkls");
    cb_2   = evhtp_set_cb(htp, "/foo", test_foo_cb, "bar");
    cb_3   = evhtp_set_cb(htp, "/foo/", test_foo_cb, "bar");
    cb_4   = evhtp_set_cb(htp, "/bar", test_bar_cb, "baz");
    cb_5   = evhtp_set_cb(htp, "/500", test_500_cb, "500");
    cb_6   = evhtp_set_regex_cb(htp, "^(/anything/).*", test_regex, NULL);
    cb_7   = evhtp_set_cb(htp, "/pause", test_pause_cb, NULL);
    cb_8   = evhtp_set_regex_cb(htp, "^/create/(.*)", create_callback, NULL);

    /* set a callback to pause on each header for cb_7 */
    evhtp_set_hook(&cb_7->hooks, evhtp_hook_on_path, pause_init_cb, NULL);

    /* set a callback to set hooks specifically for the cb_6 callback */
    evhtp_set_hook(&cb_6->hooks, evhtp_hook_on_headers, test_regex_hdrs_cb, NULL);

    /* set a default request handler */
    evhtp_set_gencb(htp, test_default_cb, "foobarbaz");

    /* set a callback invoked before a connection is accepted */
    evhtp_set_pre_accept_cb(htp, test_pre_accept, &bind_port);

    /* set a callback to set per-connection hooks (via a post_accept cb) */
    evhtp_set_post_accept_cb(htp, set_my_connection_handlers, NULL);

#ifndef DISABLE_SSL
    if (ssl_pem != NULL) {
        evhtp_ssl_cfg_t scfg = {
            .pemfile            = ssl_pem,
            .privfile           = ssl_pem,
            .cafile             = ssl_ca,
            .capath             = ssl_capath,
            .ciphers            = "RC4+RSA:HIGH:+MEDIUM:+LOW",
            .ssl_opts           = SSL_OP_NO_SSLv2,
            .verify_peer        = SSL_VERIFY_PEER,
            .verify_depth       = 42,
            .x509_verify_cb     = dummy_ssl_verify_callback,
            .x509_chk_issued_cb = dummy_check_issued_cb,
            .scache_type        = evhtp_ssl_scache_type_internal,
            .scache_size        = 1024,
            .scache_timeout     = 1024,
            .scache_init        = NULL,
            .scache_add         = NULL,
            .scache_get         = NULL,
            .scache_del         = NULL,
        };

        evhtp_ssl_init(htp, &scfg);

        if (use_threads) {
            #define OPENSSL_THREAD_DEFINES
#include <openssl/opensslconf.h>
#if defined(OPENSSL_THREADS)
#else
            fprintf(stderr, "Your version of OpenSSL does not support threading!\n");
            exit(-1);
#endif
        }
    }
#endif

#ifndef DISABLE_EVTHR
    if (use_threads) {
        evhtp_use_threads(htp, NULL, num_threads, NULL);
    }
#endif

    if (evhtp_bind_socket(htp, bind_addr, bind_port, 128) < 0) {
        fprintf(stderr, "Could not bind socket: %s\n", strerror(errno));
        exit(-1);
    }

    signal(SIGINT, sigint);

    event_base_loop(evbase, 0);
    return 0;
} /* main */
Esempio n. 9
0
File: main.c Progetto: buaazp/zimg
/**
 * @brief main The entrance of zimg.
 *
 * @param argc Count of args.
 * @param argv Arg list.
 *
 * @return It returns a int to system.
 */
int main(int argc, char **argv) {
    /* Set signal handlers */
    sigset_t sigset;
    sigemptyset(&sigset);
    struct sigaction siginfo = {
        .sa_sigaction = &sighandler,
        .sa_mask = sigset,
        .sa_flags = SA_RESTART,
    };
    sigaction(SIGINT, &siginfo, NULL);
    sigaction(SIGTERM, &siginfo, NULL);

    if (argc < 2) {
        usage(argc, argv);
        return -1;
    }

    settings_init();
    int i;
    for (i = 1; i < argc; i++) {
        if (strcmp(argv[i], "-d") == 0) {
            settings.is_daemon = 1;
        } else {
            conf_file = argv[i];
        }
    }

    if (conf_file == NULL) {
        usage(argc, argv);
        return -1;
    }

    if (is_file(conf_file) == -1) {
        fprintf(stderr, "'%s' is not a file or not exists!\n", conf_file);
        return -1;
    }

    if (load_conf(conf_file) == -1) {
        fprintf(stderr, "'%s' load failed!\n", conf_file);
        return -1;
    }

    if (bind_check(settings.port) == -1) {
        fprintf(stderr, "Port %d bind failed!\n", settings.port);
        return -1;
    }

    if (settings.is_daemon == 1) {
        if (daemon(1, 1) < 0) {
            fprintf(stderr, "Create daemon failed!\n");
            return -1;
        } else {
            fprintf(stdout, "zimg %s\n", settings.version);
            fprintf(stdout, "Copyright (c) 2013-2014 zimg.buaa.us\n");
            fprintf(stderr, "\n");
        }
    }
    //init the Path zimg need to use.
    //start log module... ./log/zimg.log
    if (mk_dirf(settings.log_name) != 1) {
        fprintf(stderr, "%s log path create failed!\n", settings.log_name);
        return -1;
    }
    log_init();

    if (settings.script_name[0] != '\0') {
        if (is_file(settings.script_name) == -1) {
            fprintf(stderr, "%s open failed!\n", settings.script_name);
            return -1;
        }
        settings.script_on = 1;
    }

    if (is_dir(settings.img_path) != 1) {
        if (mk_dirs(settings.img_path) != 1) {
            LOG_PRINT(LOG_DEBUG, "img_path[%s] Create Failed!", settings.img_path);
            fprintf(stderr, "%s Create Failed!\n", settings.img_path);
            return -1;
        }
    }
    LOG_PRINT(LOG_DEBUG, "Paths Init Finished.");

    if (settings.mode == 2) {
        LOG_PRINT(LOG_DEBUG, "Begin to Test Memcached Connection...");
        memcached_st *beans = memcached_create(NULL);
        char mserver[32];
        snprintf(mserver, 32, "%s:%d", settings.beansdb_ip, settings.beansdb_port);
        memcached_server_st *servers = memcached_servers_parse(mserver);
        servers = memcached_servers_parse(mserver);
        memcached_server_push(beans, servers);
        memcached_server_list_free(servers);
        memcached_behavior_set(beans, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL, 0);
        memcached_behavior_set(beans, MEMCACHED_BEHAVIOR_NO_BLOCK, 1);
        memcached_behavior_set(beans, MEMCACHED_BEHAVIOR_TCP_KEEPALIVE, 1);
        LOG_PRINT(LOG_DEBUG, "beansdb Connection Init Finished.");
        if (set_cache(beans, "zimg", "1") == -1) {
            LOG_PRINT(LOG_DEBUG, "Beansdb[%s] Connect Failed!", mserver);
            fprintf(stderr, "Beansdb[%s] Connect Failed!\n", mserver);
            memcached_free(beans);
            return -1;
        } else {
            LOG_PRINT(LOG_DEBUG, "beansdb connected to: %s", mserver);
        }
        memcached_free(beans);
    } else if (settings.mode == 3) {
        redisContext* c = redisConnect(settings.ssdb_ip, settings.ssdb_port);
        if (c->err) {
            redisFree(c);
            LOG_PRINT(LOG_DEBUG, "Connect to ssdb server faile");
            fprintf(stderr, "SSDB[%s:%d] Connect Failed!\n", settings.ssdb_ip, settings.ssdb_port);
            return -1;
        } else {
            LOG_PRINT(LOG_DEBUG, "Connect to ssdb server Success");
        }
    }

    //init magickwand
    MagickCoreGenesis((char *) NULL, MagickFalse);
    /*
    ExceptionInfo *exception=AcquireExceptionInfo();
    MagickInfo *jpeg_info = (MagickInfo *)GetMagickInfo("JPEG", exception);
    if(jpeg_info->thread_support != MagickTrue)
        LOG_PRINT(LOG_DEBUG, "thread_support != MagickTrue");
    jpeg_info->thread_support = MagickTrue;
    if(jpeg_info->thread_support != MagickTrue)
        LOG_PRINT(LOG_DEBUG, "thread_support != MagickTrue");
    MagickInfo *jpg_info = (MagickInfo *)GetMagickInfo("JPG", exception);
    jpg_info->thread_support = MagickTrue;
    */

    int result = pthread_key_create(&gLuaStateKey, thread_lua_dtor);
    if (result != 0) {
        LOG_PRINT(LOG_ERROR, "Could not allocate TLS key for lua_State.");
    }

    //begin to start httpd...
    LOG_PRINT(LOG_DEBUG, "Begin to Start Httpd Server...");
    LOG_PRINT(LOG_INFO, "zimg started");
    evbase = event_base_new();
    evhtp_t *htp = evhtp_new(evbase, NULL);

    evhtp_set_cb(htp, "/dump", dump_request_cb, NULL);
    evhtp_set_cb(htp, "/upload", post_request_cb, NULL);
    evhtp_set_cb(htp, "/admin", admin_request_cb, NULL);
    evhtp_set_cb(htp, "/info", info_request_cb, NULL);
    evhtp_set_cb(htp, "/echo", echo_cb, NULL);
    evhtp_set_gencb(htp, get_request_cb, NULL);
#ifndef EVHTP_DISABLE_EVTHR
    evhtp_use_threads(htp, init_thread, settings.num_threads, NULL);
#endif
    evhtp_set_max_keepalive_requests(htp, settings.max_keepalives);
    evhtp_bind_socket(htp, settings.ip, settings.port, settings.backlog);

    event_base_loop(evbase, 0);

    evhtp_unbind_socket(htp);
    //evhtp_free(htp);
    event_base_free(evbase);
    free_headers_conf(settings.headers);
    free_access_conf(settings.up_access);
    free_access_conf(settings.down_access);
    free_access_conf(settings.admin_access);
    free(settings.mp_set);

    return 0;
}
/* Functions */
int
genauthz_httprest_init(evbase_t * evbase, struct app_parent *app_p) {
    struct passwd *pwd = NULL;
    struct tq_listener_s *p_listener, *tmp_p_listener;
    struct tq_service_s *p_service, *tmp_p_service;

    if (evbase == NULL || app_p == NULL)
        return GA_BAD;

    /* Reset Application parent counter */
    app_p->total_call_count = 0;
    app_p->threads_online   = 0;

    for (p_listener = TAILQ_FIRST(&(app_p->listener_head));
         p_listener != NULL;
         tmp_p_listener = TAILQ_NEXT(p_listener, next),
                p_listener = tmp_p_listener) {

        p_listener->listener_call_count = 0; /* Reset counter */

        p_listener->evhtp = evhtp_new(evbase, NULL);
        if (p_listener->evhtp == NULL) {
            syslog(LOG_ERR, "Failed on evhtp_new()");
            goto cleanup;
        }

        /* Map the Application parent object to each listener */
        p_listener->app_parent = app_p;

        /* Setup security context */
        if (p_listener->scfg) {
            evhtp_ssl_init(p_listener->evhtp, p_listener->scfg);
        }

        /* Bind */
        if (evhtp_bind_socket(p_listener->evhtp, p_listener->bindip,
                              p_listener->port, p_listener->backlog) != 0) {
            syslog(LOG_ERR, "Failed to bind a listener to \"%s\" on port \'%d\'",
                            p_listener->bindip, p_listener->port);
            goto cleanup;
        }

        syslog(LOG_INFO, "Listening on \"%s\" on port \'%d\'%s",
                        p_listener->bindip, p_listener->port,
                        p_listener->scfg ? " with SSL." : "");

#if 0
        /* Register thread handler */
        evhtp_use_threads(p_listener->evhtp,
                          app_init_thread,
                          p_listener->thread_cnt,
                          p_listener);
#endif

        for (p_service = TAILQ_FIRST(&(p_listener->services_head));
             p_service != NULL;
             tmp_p_service = TAILQ_NEXT(p_service, next),
                    p_service = tmp_p_service) {

            syslog(LOG_INFO, "URI: \"%s\"", p_service->uri);

            /* Register thread handler */
            evhtp_use_threads(p_listener->evhtp,
                              app_init_thread,
                              p_service->thread_cnt,
                              p_service);

            /* Reset service counter */
            p_service->uri_call_count = 0;

            /* Service type switcher */
            switch(p_service->ltype) {
                case PAP:
                    if (evhtp_set_cb(p_listener->evhtp,
                                     p_service->uri,
                                     pap_cb,
                                     p_service) == NULL) {
                        syslog(LOG_ERR, "Failed to set the PAP callback for the URI \"%s\"", p_service->uri);
                        goto cleanup;
                    } else {
                        syslog(LOG_INFO, "Set the \"PAP\" callback on the URI \"%s\" with \'%d\' threads",
                                         p_service->uri, p_service->thread_cnt);
                    }
                    break;
                case PDP:
                    if (evhtp_set_cb(p_listener->evhtp,
                                     p_service->uri,
                                     pdp_cb,
                                     p_service) == NULL) {
                        syslog(LOG_ERR, "Failed to set the PDP callback for the URI \"%s\"", p_service->uri);
                        goto cleanup;
                    } else {
                        syslog(LOG_INFO, "Set the \"PDP\" callback on the URI \"%s\" with \'%d\' threads",
                                         p_service->uri, p_service->thread_cnt);
                    }
                    break;
                case CONTROL:
                    if (evhtp_set_cb(p_listener->evhtp,
                                     p_service->uri,
                                     control_cb,
                                     p_service) == NULL) {
                        syslog(LOG_ERR, "Failed to set the CONTROL callback for the URI \"%s\"", p_service->uri);
                        goto cleanup;
                    } else {
                        syslog(LOG_INFO, "Set the \"CONTROL\" callback on the URI \"%s\" with \'%d\' threads",
                                         p_service->uri, p_service->thread_cnt);
                    }
                    break;
                default:
                    if (evhtp_set_cb(p_listener->evhtp,
                                     p_service->uri,
                                     generic_http_cb,
                                     p_service) == NULL) {
                        syslog(LOG_ERR, "Failed to set the generic callback for the URI \"%s\"", p_service->uri);
                        goto cleanup;
                    } else {
                        syslog(LOG_INFO, "Set the \"generic_http_cb()\" callback on the URI \"%s\" with \'%d\' threads",
                                         p_service->uri, p_service->thread_cnt);
                    }
                    break;
            }
        }
    }

    /* Privilege downgrade */
    if (geteuid() == 0) {
        /* Test for effective seteuid()-only, like sudo, switch to caller ID */
        if (getuid() != 0) {
            if (getegid() == 0) {
                if (setegid(getgid()) < 0) {
                    return GA_BAD;
                }
            }
            if (seteuid(getuid()) < 0) {
                return GA_BAD;
            }
        } else {
            /* Lower privs after bind to 'okoeroo' or 'nobody' */
            pwd = getpwnam("nobody");
            if (pwd == NULL) {
                return GA_BAD;
            }
            if (getegid() == 0) {
                if (setegid(pwd->pw_gid) < 0)
                    return GA_BAD;
                if (setgid(pwd->pw_gid) < 0)
                    return GA_BAD;
            }
            if (setuid(pwd->pw_uid) < 0)
                return GA_BAD;
            if (seteuid(pwd->pw_uid) < 0)
                return GA_BAD;
        }
    }
    syslog(LOG_INFO, "Running as uid: %d, euid: %d, gid: %d, egid: %d", getuid(), geteuid(), getgid(), geteuid());

    return GA_GOOD;
cleanup:
    return GA_BAD;
}
Esempio n. 11
0
File: main.c Progetto: alemic/zimg
/**
 * @brief main The entrance of zimg.
 *
 * @param argc Count of args.
 * @param argv Arg list.
 *
 * @return It returns a int to system.
 */
int main(int argc, char **argv)
{
    int c;
    _init_path = getcwd(NULL, 0);
    LOG_PRINT(LOG_INFO, "Get init-path: %s", _init_path);

    /* Set signal handlers */
    sigset_t sigset;
    sigemptyset(&sigset);
    struct sigaction siginfo = {
        .sa_handler = sighandler,
        .sa_mask = sigset,
        .sa_flags = SA_RESTART,
    };
    sigaction(SIGINT, &siginfo, NULL);
    sigaction(SIGTERM, &siginfo, NULL);


    settings_init();
    while (-1 != (c = getopt(argc, argv,
                    "p:"
                    "t:"
                    "l"
                    "c"
                    "M:"
                    "m:"
                    "b:"
                    "h"
                    "k:"
                    )))
    {
        switch(c)
        {
            case 'p':
                settings.port = atoi(optarg);
                break;
            case 't':
                settings.num_threads = atoi(optarg);
                if (settings.num_threads <= 0) {
                    fprintf(stderr, "Number of threads must be greater than 0\n");
                    return 1;
                }
                /* There're other problems when you get above 64 threads.
                 * In the future we should portably detect # of cores for the
                 * default.
                 */
                if (settings.num_threads > 64) {
                    fprintf(stderr, "WARNING: Setting a high number of worker"
                            "threads is not recommended.\n"
                            " Set this value to the number of cores in"
                            " your machine or less.\n");
                }
                break;
            case 'l':
                settings.log = true;
                break;
            case 'c':
                settings.cache_on = true;
                break;
            case 'M':
                strcpy(settings.cache_ip, optarg);
                break;
            case 'm':
                settings.cache_port = atoi(optarg);
                break;
            case 'b':
                settings.backlog = atoi(optarg);
                break;
            case 'k':
                settings.max_keepalives = atoll(optarg);
                break;
            case 'h':
                printf("Usage: ./zimg -p port -t thread_num -M memcached_ip -m memcached_port -l[og] -c[ache] -b backlog_num -k max_keepalives -h[elp]\n");
                exit(1);
            default:
                fprintf(stderr, "Illegal argument \"%c\"\n", c);
                return 1;
        }
    }
    //init the Path zimg need to use.
    LOG_PRINT(LOG_INFO, "Begin to Init the Path zimg Using...");
//    if(is_dir(settings.root_path) != 1)
//    {
//        if(mk_dir(settings.root_path) != 1)
//        {
//            LOG_PRINT(LOG_ERROR, "root_path[%s] Create Failed!", settings.root_path);
//            return -1;
//        }
//    }
//
//
    //start log module... ./log/zimg.log
    if(settings.log)
    {
        const char *log_path = "./log";
        if(is_dir(log_path) != 1)
        {
            if(mk_dir(log_path) != 1)
            {
                LOG_PRINT(LOG_ERROR, "log_path[%s] Create Failed!", log_path);
                return -1;
            }
        }
        log_init();
    }

    if(is_dir(settings.img_path) != 1)
    {
        if(mk_dir(settings.img_path) != 1)
        {
            LOG_PRINT(LOG_ERROR, "img_path[%s] Create Failed!", settings.img_path);
            return -1;
        }
    }
    LOG_PRINT(LOG_INFO,"Paths Init Finished.");

   
    //init memcached connection...
    if(settings.cache_on == true)
    {
        LOG_PRINT(LOG_INFO, "Begin to Init Memcached Connection...");
        memcached_st *memc;
        memc= memcached_create(NULL);

        char mserver[32];
        sprintf(mserver, "%s:%d", settings.cache_ip, settings.cache_port);
        memcached_server_st *servers = memcached_servers_parse(mserver);

        memcached_server_push(memc, servers);
        memcached_server_list_free(servers);
        memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL, 0);
        //使用NO-BLOCK,防止memcache倒掉时挂死          
        memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, 1); 
        LOG_PRINT(LOG_INFO, "Memcached Connection Init Finished.");
        if(set_cache("zimg", "1") == -1)
        {
            LOG_PRINT(LOG_WARNING, "Memcached[%s] Connect Failed!", mserver);
            settings.cache_on = false;
        }
        else
        {
            LOG_PRINT(LOG_INFO, "memcached connection to: %s", mserver);
            settings.cache_on = true;
        }
        memcached_free(memc);
    }
    else
        LOG_PRINT(LOG_INFO, "Don't use memcached as cache.");
    //init magickwand
    MagickWandGenesis();

    //begin to start httpd...
    LOG_PRINT(LOG_INFO, "Begin to Start Httpd Server...");
    evbase = event_base_new();
    evhtp_t  * htp    = evhtp_new(evbase, NULL);

    evhtp_set_cb(htp, "/dump", dump_request_cb, NULL);
    evhtp_set_cb(htp, "/upload", post_request_cb, NULL);
    //evhtp_set_gencb(htp, echo_cb, NULL);
    evhtp_set_gencb(htp, send_document_cb, NULL);
#ifndef EVHTP_DISABLE_EVTHR
    evhtp_use_threads(htp, NULL, settings.num_threads, NULL);
#endif
    evhtp_set_max_keepalive_requests(htp, settings.max_keepalives);
    evhtp_bind_socket(htp, "0.0.0.0", settings.port, settings.backlog);

    event_base_loop(evbase, 0);

    evhtp_unbind_socket(htp);
    evhtp_free(htp);
    event_base_free(evbase);
    MagickWandTerminus();

    fprintf(stdout, "\nByebye!\n");
    return 0;
}
Esempio n. 12
0
int
main(int argc, char *argv[])
{
    evbase_t *evbase = NULL;
    evhtp_t *htp = NULL;
    int daemon_mode = 1;
    int c;
    char *logfile = NULL;
    char *ccnet_debug_level_str = "info";
    char *http_debug_level_str = "debug";
    const char *debug_str = NULL;
    char *temp_file_dir = NULL;

#ifdef WIN32
    argv = get_argv_utf8 (&argc);
#endif

    config_dir = DEFAULT_CONFIG_DIR;

    while ((c = getopt_long(argc, argv,
                short_opts, long_opts, NULL)) != EOF) {
        switch (c) {
        case 'h':
            usage();
            exit(0);
        case 'v':
            exit(-1);
            break;
        case 'c':
            config_dir = strdup(optarg);
            break;
        case 'd':
            seafile_dir = strdup(optarg);
            break;
        case 't':
            num_threads = atoi(optarg);
            break;
        case 'f':
            daemon_mode = 0;
            break;
        case 'l':
            logfile = g_strdup(optarg);
            break;
        case 'g':
            ccnet_debug_level_str = optarg;
            break;
        case 'G':
            http_debug_level_str = optarg;
            break;
        case 'D':
            debug_str = optarg;
            break;
        case 'k':
            temp_file_dir = optarg;
            break;
        case 'P':
            pidfile = optarg;
            break;
        default:
            usage();
            exit(-1);
        }
    }

#if !defined(WIN32) && !defined(__APPLE__)
    if (daemon_mode)
        daemon(1, 0);
#endif
#ifdef WIN32
    WSADATA     wsadata;
    WSAStartup(0x0101, &wsadata);
#endif

#if !GLIB_CHECK_VERSION(2, 35, 0)
    g_type_init();
#endif

    if (!debug_str)
        debug_str = g_getenv("SEAFILE_DEBUG");
    seafile_debug_set_flags_string (debug_str);

    if (seafile_dir == NULL)
        seafile_dir = g_build_filename (config_dir, "seafile-data", NULL);
    if (logfile == NULL)
        logfile = g_build_filename (seafile_dir, "http.log", NULL);

    if (seafile_log_init (logfile, ccnet_debug_level_str,
                          http_debug_level_str) < 0) {
        g_warning ("Failed to init log.\n");
        exit (1);
    }

    ccnet_client = ccnet_client_new();
    if ((ccnet_client_load_confdir(ccnet_client, config_dir)) < 0) {
        g_warning ("Read config dir error\n");
        return -1;
    }

    seaf = seafile_session_new (seafile_dir, ccnet_client);
    if (!seaf) {
        g_warning ("Failed to create seafile session.\n");
        exit (1);
    }
    if (seafile_session_init(seaf) < 0)
        exit (1);

    if (temp_file_dir == NULL)
        seaf->http_temp_dir = g_build_filename (seaf->seaf_dir, "httptemp", NULL);
    else
        seaf->http_temp_dir = g_strdup(temp_file_dir);

    seaf->client_pool = ccnet_client_pool_new (config_dir);

    load_httpserver_config (seaf);
    if (use_https) {
        seaf_message ("host = %s, port = %d, https = true, pemfile = %s, privkey = %s\n",
                      bind_addr, bind_port, pemfile, privkey);
    } else {
        seaf_message ("host = %s, port = %d, https = false\n", bind_addr, bind_port);
    }

    evbase = event_base_new();
    htp = evhtp_new(evbase, NULL);

    if (pemfile != NULL) {
        evhtp_ssl_cfg_t scfg;

        memset (&scfg, 0, sizeof(scfg));

        scfg.pemfile        = pemfile;
        scfg.privfile       = privkey;
        scfg.scache_type    = evhtp_ssl_scache_type_internal;
        scfg.scache_timeout = 5000;

        evhtp_ssl_init (htp, &scfg);
    }

    if (access_file_init (htp) < 0)
        exit (1);

    if (upload_file_init (htp) < 0)
        exit (1);

    evhtp_set_gencb(htp, default_cb, NULL);

    evhtp_use_threads(htp, NULL, num_threads, NULL);

    if (evhtp_bind_socket(htp, bind_addr, bind_port, 128) < 0) {
        g_warning ("Could not bind socket: %s\n", strerror(errno));
        exit(-1);
    }

    if (pidfile) {
        if (write_pidfile (pidfile) < 0) {
            seaf_message ("Failed to write pidfile\n");
            return -1;
        }
    }
    
    atexit (on_httpserver_exit);

    event_base_loop(evbase, 0);

    return 0;
}
Esempio n. 13
0
/**
 * @brief main The entrance of zimg.
 *
 * @param argc Count of args.
 * @param argv Arg list.
 *
 * @return It returns a int to system.
 */
int main(int argc, char **argv)
{
    int i;
    retry_sleep.tv_sec = 0;
    retry_sleep.tv_nsec = RETRY_TIME_WAIT;      //1000 ns = 1 us

    /* Set signal handlers */
    sigset_t sigset;
    sigemptyset(&sigset);
    struct sigaction siginfo = {
        .sa_handler = sighandler,
        .sa_mask = sigset,
        .sa_flags = SA_RESTART,
    };
    sigaction(SIGINT, &siginfo, NULL);
    sigaction(SIGTERM, &siginfo, NULL);

    if(argc < 2)
    {
        usage(argc, argv);
        return -1;
    }

    settings_init();
    const char *conf_file = NULL;
    for(i=1; i<argc; i++)
    {
        if(strcmp(argv[i], "-d") == 0){
            settings.is_daemon = 1;
        }else{
            conf_file = argv[i];
        }
    }

    if(conf_file == NULL)
    {
        usage(argc, argv);
        return -1;
    }

    if(is_file(conf_file) == -1)
    {
        fprintf(stderr, "'%s' is not a file or not exists!\n", conf_file);
        return -1;
    }

    if(load_conf(conf_file) == -1)
    {
        fprintf(stderr, "'%s' load failed!\n", conf_file);
        return -1;
    }


    if(settings.is_daemon == 1)
    {
        if(daemon(1, 1) < 0)
        {
            fprintf(stderr, "Create daemon failed!\n");
            return -1;
        }
        else
        {
            fprintf(stdout, "zimg %s\n", settings.version);
            fprintf(stdout, "Copyright (c) 2013-2014 zimg.buaa.us\n");
            fprintf(stderr, "\n");
        }
    }
    //init the Path zimg need to use.
    LOG_PRINT(LOG_DEBUG, "Begin to Init the Path zimg Using...");
    //start log module... ./log/zimg.log
    if(settings.log)
    {
        const char *log_path = "./log";
        if(is_dir(log_path) != 1)
        {
            if(mk_dir(log_path) != 1)
            {
                LOG_PRINT(LOG_DEBUG, "log_path[%s] Create Failed!", log_path);
                fprintf(stderr, "log_path[%s] Create Failed!\n", log_path);
                return -1;
            }
        }
        log_init();
    }

    if(is_dir(settings.img_path) != 1)
    {
        if(mk_dir(settings.img_path) != 1)
        {
            LOG_PRINT(LOG_DEBUG, "img_path[%s] Create Failed!", settings.img_path);
            fprintf(stderr, "%s Create Failed!\n", settings.img_path);
            return -1;
        }
    }
    LOG_PRINT(LOG_DEBUG,"Paths Init Finished.");

    if(settings.mode == 2)
    {
        LOG_PRINT(LOG_DEBUG, "Begin to Test Memcached Connection...");
        memcached_st *beans = memcached_create(NULL);
        char mserver[32];
        snprintf(mserver, 32, "%s:%d", settings.beansdb_ip, settings.beansdb_port);
        memcached_server_st *servers = memcached_servers_parse(mserver);
        servers = memcached_servers_parse(mserver);
        memcached_server_push(beans, servers);
        memcached_server_list_free(servers);
        memcached_behavior_set(beans, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL, 0);
        memcached_behavior_set(beans, MEMCACHED_BEHAVIOR_NO_BLOCK, 1); 
        memcached_behavior_set(beans, MEMCACHED_BEHAVIOR_TCP_KEEPALIVE, 1); 
        LOG_PRINT(LOG_DEBUG, "beansdb Connection Init Finished.");
        if(set_cache(beans, "zimg", "1") == -1)
        {
            LOG_PRINT(LOG_DEBUG, "Beansdb[%s] Connect Failed!", mserver);
            fprintf(stderr, "Beansdb[%s] Connect Failed!\n", mserver);
            memcached_free(beans);
            return -1;
        }
        else
        {
            LOG_PRINT(LOG_DEBUG, "beansdb connected to: %s", mserver);
        }
        memcached_free(beans);
    }
    else if(settings.mode == 3)
    {
        redisContext* c = redisConnect(settings.ssdb_ip, settings.ssdb_port);
        if(c->err)
        {
            redisFree(c);
            LOG_PRINT(LOG_DEBUG, "Connect to ssdb server faile");
            fprintf(stderr, "SSDB[%s:%d] Connect Failed!\n", settings.ssdb_ip, settings.ssdb_port);
            return -1;
        }
        else
        {
            LOG_PRINT(LOG_DEBUG, "Connect to ssdb server Success");
        }
    }

    //init magickwand
    MagickWandGenesis();

    //begin to start httpd...
    LOG_PRINT(LOG_DEBUG, "Begin to Start Httpd Server...");
    LOG_PRINT(LOG_INFO, "zimg started");
    evbase = event_base_new();
    evhtp_t *htp = evhtp_new(evbase, NULL);

    evhtp_set_cb(htp, "/dump", dump_request_cb, NULL);
    evhtp_set_cb(htp, "/upload", post_request_cb, NULL);
    //evhtp_set_gencb(htp, echo_cb, NULL);
    evhtp_set_gencb(htp, send_document_cb, NULL);
#ifndef EVHTP_DISABLE_EVTHR
    evhtp_use_threads(htp, init_thread, settings.num_threads, NULL);
#endif
    evhtp_set_max_keepalive_requests(htp, settings.max_keepalives);
    evhtp_bind_socket(htp, "0.0.0.0", settings.port, settings.backlog);

    event_base_loop(evbase, 0);

    evhtp_unbind_socket(htp);
    evhtp_free(htp);
    event_base_free(evbase);
    MagickWandTerminus();
    free_access_conf(settings.up_access);
    free_access_conf(settings.down_access);

    fprintf(stdout, "\nByebye!\n");
    return 0;
}
Esempio n. 14
0
int
main(int argc, char ** argv) {
    extern char * optarg;
    extern int    optind;
    extern int    opterr;
    extern int    optopt;
    int           c;

    while ((c = getopt(argc, argv, "t:a:p:b:ndrs:")) != -1) {
        switch (c) {
            case 't':
                num_threads  = atoi(optarg);
                break;
            case 'a':
                baddr        = strdup(optarg);
                break;
            case 'p':
                bport        = atoi(optarg);
                break;
            case 'b':
                backlog      = atoll(optarg);
            case 'n':
                nodelay      = 1;
                break;
            case 'd':
                defer_accept = 1;
                break;
            case 'r':
                reuse_port   = 1;
                break;
            case 's':
                payload_sz   = atoll(optarg);
                break;
            default:
                fprintf(stdout, "Usage: %s [flags]\n", argv[0]);
                fprintf(stdout, "  -t <n> : number of worker threads [Default: %d]\n", num_threads);
                fprintf(stdout, "  -a <s> : bind address             [Default: %s]\n", baddr);
                fprintf(stdout, "  -p <n> : bind port                [Default: %d]\n", bport);
                fprintf(stdout, "  -b <b> : listen backlog           [Default: %d]\n", backlog);
                fprintf(stdout, "  -s <n> : size of the response     [Default: %zu]\n", payload_sz);
                fprintf(stdout, "  -n     : disable nagle (nodelay)  [Default: %s]\n", nodelay ? "true" : "false");
                fprintf(stdout, "  -d     : enable deferred accept   [Default: %s]\n", defer_accept ? "true" : "false");
                fprintf(stdout, "  -r     : enable linux reuseport   [Default: %s]\n", reuse_port ? "true" : "false");
                exit(EXIT_FAILURE);
        } /* switch */
    }

    {
        struct event_base * evbase;
        evhtp_t           * htp;
        char                payload[payload_sz];

        evbase = event_base_new();
        evhtp_alloc_assert(evbase);

        htp    = evhtp_new(evbase, NULL);
        evhtp_alloc_assert(htp);

        evhtp_set_parser_flags(htp, EVHTP_PARSE_QUERY_FLAG_LENIENT);

        htp->enable_nodelay      = nodelay;
        htp->enable_defer_accept = defer_accept;
        htp->enable_reuseport    = reuse_port;

        memset(payload, 0x42, payload_sz);

        evhtp_assert(evhtp_set_cb(htp, "/data", response_cb, payload));

#ifndef EVHTP_DISABLE_EVTHR
        if (num_threads > 0) {
            evhtp_assert(evhtp_use_threads(htp, NULL, num_threads, NULL) != -1);
        }
#endif

        evhtp_errno_assert(evhtp_bind_socket(htp, baddr, bport, backlog) >= 0);
        event_base_loop(evbase, 0);
    }


    return 0;
} /* main */