static int uwsgi_sni_cb(SSL *ssl, int *ad, void *arg) { const char *servername = SSL_get_servername(ssl, TLSEXT_NAMETYPE_host_name); if (!servername) return SSL_TLSEXT_ERR_NOACK; size_t servername_len = strlen(servername); struct uwsgi_string_list *usl = uwsgi.sni; while(usl) { if (!uwsgi_strncmp(usl->value, usl->len, (char *)servername, servername_len)) { SSL_set_SSL_CTX(ssl, usl->custom_ptr); return SSL_TLSEXT_ERR_OK; } usl = usl->next; } #ifdef UWSGI_PCRE struct uwsgi_regexp_list *url = uwsgi.sni_regexp; while(url) { if (uwsgi_regexp_match(url->pattern, url->pattern_extra, (char *)servername, servername_len) >= 0) { SSL_set_SSL_CTX(ssl, url->custom_ptr); return SSL_TLSEXT_ERR_OK; } url = url->next; } #endif if (uwsgi.sni_dir) { size_t sni_dir_len = strlen(uwsgi.sni_dir); char *sni_dir_cert = uwsgi_concat4n(uwsgi.sni_dir, sni_dir_len, "/", 1, (char *) servername, servername_len, ".crt", 4); char *sni_dir_key = uwsgi_concat4n(uwsgi.sni_dir, sni_dir_len, "/", 1, (char *) servername, servername_len, ".key", 4); char *sni_dir_client_ca = uwsgi_concat4n(uwsgi.sni_dir, sni_dir_len, "/", 1, (char *) servername, servername_len, ".ca", 3); if (uwsgi_file_exists(sni_dir_cert) && uwsgi_file_exists(sni_dir_key)) { char *client_ca = NULL; if (uwsgi_file_exists(sni_dir_client_ca)) { client_ca = sni_dir_client_ca; } usl = uwsgi_ssl_add_sni_item(uwsgi_str((char *)servername), sni_dir_cert, sni_dir_key, uwsgi.sni_dir_ciphers, client_ca); if (!usl) goto done; free(sni_dir_cert); free(sni_dir_key); free(sni_dir_client_ca); SSL_set_SSL_CTX(ssl, usl->custom_ptr); uwsgi_log("[uwsgi-sni for pid %d] added context for %s\n", (int) getpid(), servername); return SSL_TLSEXT_ERR_OK; } done: free(sni_dir_cert); free(sni_dir_key); free(sni_dir_client_ca); } return SSL_TLSEXT_ERR_NOACK; }
int uwsgi_logic_opt_if_not_exists(char *key, char *value) { if (!uwsgi_file_exists(uwsgi.logic_opt_data)) { add_exported_option(key, uwsgi_substitute(value, "%(_)", uwsgi.logic_opt_data), 0); return 1; } return 0; }
void uwsgi_subscribe(char *subscription, uint8_t cmd) { int subfile_size; int i; char *key = NULL; int keysize = 0; char *modifier1 = NULL; int modifier1_len = 0; char *socket_name = NULL; char *udp_address = subscription; char *udp_port = NULL; char *subscription_key = NULL; char *sign = NULL; // check for explicit socket_name char *equal = strchr(subscription, '='); if (equal) { socket_name = subscription; if (socket_name[0] == '=') { equal = strchr(socket_name + 1, '='); if (!equal) return; *equal = '\0'; struct uwsgi_socket *us = uwsgi_get_shared_socket_by_num(atoi(socket_name + 1)); if (!us) return; socket_name = us->name; } *equal = '\0'; udp_address = equal + 1; } // check for unix socket if (udp_address[0] != '/') { udp_port = strchr(udp_address, ':'); if (!udp_port) { if (equal) *equal = '='; return; } subscription_key = strchr(udp_port + 1, ':'); } else { subscription_key = strchr(udp_address + 1, ':'); } if (!subscription_key) { if (equal) *equal = '='; return; } udp_address = uwsgi_concat2n(udp_address, subscription_key - udp_address, "", 0); if (subscription_key[1] == '@') { if (!uwsgi_file_exists(subscription_key + 2)) goto clear; char *lines = uwsgi_open_and_read(subscription_key + 2, &subfile_size, 1, NULL); if (subfile_size > 0) { key = lines; for (i = 0; i < subfile_size; i++) { if (lines[i] == 0) { if (keysize > 0) { if (key[0] != '#' && key[0] != '\n') { modifier1 = strchr(key, ','); if (modifier1) { modifier1[0] = 0; modifier1++; modifier1_len = strlen(modifier1); keysize = strlen(key); } uwsgi_send_subscription(udp_address, key, keysize, uwsgi_str_num(modifier1, modifier1_len), 0, cmd, socket_name, sign); modifier1 = NULL; modifier1_len = 0; } } break; } else if (lines[i] == '\n') { if (keysize > 0) { if (key[0] != '#' && key[0] != '\n') { lines[i] = 0; modifier1 = strchr(key, ','); if (modifier1) { modifier1[0] = 0; modifier1++; modifier1_len = strlen(modifier1); keysize = strlen(key); } uwsgi_send_subscription(udp_address, key, keysize, uwsgi_str_num(modifier1, modifier1_len), 0, cmd, socket_name, sign); modifier1 = NULL; modifier1_len = 0; lines[i] = '\n'; } } key = lines + i + 1; keysize = 0; continue; } keysize++; } free(lines); } } else { modifier1 = strchr(subscription_key + 1, ','); if (modifier1) { modifier1[0] = 0; modifier1++; sign = strchr(modifier1 + 1, ','); if (sign) { *sign = 0; sign++; } modifier1_len = strlen(modifier1); } uwsgi_send_subscription(udp_address, subscription_key + 1, strlen(subscription_key + 1), uwsgi_str_num(modifier1, modifier1_len), 0, cmd, socket_name, sign); if (modifier1) modifier1[-1] = ','; if (sign) sign[-1] = ','; } clear: if (equal) *equal = '='; free(udp_address); }
static int uwsgi_pypy_init() { size_t rlen = 0; char *buffer = NULL; void *is_cpython_loaded = dlsym(RTLD_DEFAULT, "Py_Initialize"); if (is_cpython_loaded) { uwsgi_log("!!! Loading both PyPy and CPython in the same process IS PURE EVIL AND IT IS NOT SUPPORTED !!!\n"); exit(1); } if (dlsym(RTLD_DEFAULT, "rpython_startup_code")) { uwsgi_log("PyPy runtime detected, skipping libpypy-c loading\n"); goto ready; } else if (upypy.lib) { upypy.handler = dlopen(upypy.lib, RTLD_NOW | RTLD_GLOBAL); } else { if (upypy.home) { #ifdef __CYGWIN__ char *libpath = uwsgi_concat2(upypy.home, "/libpypy-c.dll"); #elif defined(__APPLE__) char *libpath = uwsgi_concat2(upypy.home, "/libpypy-c.dylib"); #else char *libpath = uwsgi_concat2(upypy.home, "/libpypy-c.so"); #endif if (uwsgi_file_exists(libpath)) { upypy.handler = dlopen(libpath, RTLD_NOW | RTLD_GLOBAL); } free(libpath); } // fallback to standard library search path if (!upypy.handler) { #ifdef __CYGWIN__ upypy.handler = dlopen("libpypy-c.dll", RTLD_NOW | RTLD_GLOBAL); #elif defined(__APPLE__) upypy.handler = dlopen("libpypy-c.dylib", RTLD_NOW | RTLD_GLOBAL); #else upypy.handler = dlopen("libpypy-c.so", RTLD_NOW | RTLD_GLOBAL); #endif } } if (!upypy.handler) { uwsgi_log("unable to load pypy library: %s\n", dlerror()); exit(1); } u_rpython_startup_code = dlsym(upypy.handler, "rpython_startup_code"); if (!u_rpython_startup_code) { uwsgi_log("unable to find rpython_startup_code() symbol\n"); exit(1); } u_pypy_setup_home = dlsym(upypy.handler, "pypy_setup_home"); if (!u_pypy_setup_home) { uwsgi_log("unable to find pypy_setup_home() symbol\n"); exit(1); } u_pypy_init_threads = dlsym(upypy.handler, "pypy_init_threads"); if (!u_pypy_init_threads) { uwsgi_log("!!! WARNING your libpypy-c does not export pypy_init_threads, multithreading will not work !!!\n"); } u_rpython_startup_code(); if (!upypy.home) { upypy.home = getenv("PYPY_HOME"); if (!upypy.home) { uwsgi_log("you have to specify a pypy home with --pypy-home\n"); exit(1); } } if (u_pypy_setup_home(upypy.home, 0)) { char *retry = uwsgi_concat2(upypy.home, "/lib_pypy"); if (uwsgi_is_dir(retry)) { // this time we use debug if (!u_pypy_setup_home(retry, 1)) { free(retry); goto ready; } } uwsgi_log("unable to set pypy home to \"%s\"\n", upypy.home); exit(1); } ready: u_pypy_execute_source = dlsym(upypy.handler, "pypy_execute_source"); if (!u_pypy_execute_source) { uwsgi_log("unable to find pypy_execute_source() symbol\n"); exit(1); } u_pypy_thread_attach = dlsym(upypy.handler, "pypy_thread_attach"); if (!u_pypy_thread_attach) { uwsgi_log("!!! WARNING your libpypy-c does not export pypy_thread_attach, multithreading will not work !!!\n"); } if (upypy.setup) { buffer = uwsgi_open_and_read(upypy.setup, &rlen, 1, NULL); } else { char *start = dlsym(RTLD_DEFAULT, "uwsgi_pypy_setup_start"); if (!start) { start = dlsym(RTLD_DEFAULT, "_uwsgi_pypy_setup_start"); } char *end = dlsym(RTLD_DEFAULT, "uwsgi_pypy_setup_end"); if (!end) { end = dlsym(RTLD_DEFAULT, "_uwsgi_pypy_setup_end"); } if (start && end) { buffer = uwsgi_concat2n(start, end-start, "", 0); } } if (!buffer) { uwsgi_log("you have to load a pypy setup file with --pypy-setup\n"); exit(1); } if (u_pypy_execute_source(buffer)) { exit(1); } free(buffer); // add items to the pythonpath struct uwsgi_string_list *usl = upypy.pp; while(usl) { if (uwsgi_pypy_hook_pythonpath) { uwsgi_pypy_hook_pythonpath(usl->value); } usl = usl->next; } return 0; }
void uwsgi_subscribe2(char *arg, uint8_t cmd) { char *s2_server = NULL; char *s2_key = NULL; char *s2_socket = NULL; char *s2_addr = NULL; char *s2_weight = NULL; char *s2_sign = NULL; char *s2_modifier1 = NULL; char *s2_modifier2 = NULL; char *s2_check = NULL; if (uwsgi_kvlist_parse(arg, strlen(arg), ',', '=', "server", &s2_server, "key", &s2_key, "socket", &s2_socket, "addr", &s2_addr, "weight", &s2_weight, "modifier1", &s2_modifier1, "modifier2", &s2_modifier2, "sign", &s2_sign, "check", &s2_check, NULL)) { return; } if (!s2_server || !s2_key) goto end; if (s2_check) { if (uwsgi_file_exists(s2_check)) goto end; } if (s2_weight) { uwsgi.weight = atoi(s2_weight); } if (s2_socket) { struct uwsgi_socket *us = uwsgi_get_socket_by_num(atoi(s2_socket)); if (us) { if (s2_addr) { free(s2_addr); } s2_addr = uwsgi_str(us->name); } } uint8_t modifier1 = 0; uint8_t modifier2 = 0; if (s2_modifier1) { modifier1 = atoi(s2_modifier1); } if (s2_modifier2) { modifier2 = atoi(s2_modifier2); } uwsgi_send_subscription(s2_server, s2_key, strlen(s2_key), modifier1, modifier2, cmd, s2_addr, s2_sign); end: if (s2_server) free(s2_server); if (s2_key) free(s2_key); if (s2_socket) free(s2_socket); if (s2_addr) free(s2_addr); if (s2_weight) free(s2_weight); if (s2_modifier1) free(s2_modifier1); if (s2_modifier2) free(s2_modifier2); if (s2_sign) free(s2_sign); if (s2_check) free(s2_check); }
void uwsgi_build_plugin(char *directory) { if (!uwsgi_file_exists(UWSGI_BUILD_DIR)) { if (mkdir(UWSGI_BUILD_DIR, S_IRWXU) < 0) { uwsgi_error("uwsgi_build_plugin()/mkdir() " UWSGI_BUILD_DIR "/"); _exit(1); } } char *dot_h = uwsgi_get_dot_h(); if (!dot_h) { uwsgi_log("unable to generate uwsgi.h"); _exit(1); } if (strlen(dot_h) == 0) { free(dot_h); uwsgi_log("invalid uwsgi.h"); _exit(1); } int dot_h_fd = open(UWSGI_BUILD_DIR "/uwsgi.h", O_WRONLY|O_CREAT|O_TRUNC, S_IRUSR|S_IWUSR); if (dot_h_fd < 0) { uwsgi_error_open(UWSGI_BUILD_DIR "/uwsgi.h"); free(dot_h); _exit(1); } ssize_t dot_h_len = (ssize_t) strlen(dot_h); if (write(dot_h_fd, dot_h, dot_h_len) != dot_h_len) { uwsgi_error("uwsgi_build_plugin()/write()"); _exit(1); } char *config_py = uwsgi_get_config_py(); if (!config_py) { uwsgi_log("unable to generate uwsgiconfig.py"); _exit(1); } if (strlen(config_py) == 0) { uwsgi_log("invalid uwsgiconfig.py"); _exit(1); } int config_py_fd = open(UWSGI_BUILD_DIR "/uwsgiconfig.py", O_WRONLY|O_CREAT|O_TRUNC, S_IRUSR|S_IWUSR); if (config_py_fd < 0) { uwsgi_error_open(UWSGI_BUILD_DIR "/uwsgiconfig.py"); _exit(1); } ssize_t config_py_len = (ssize_t) strlen(config_py); if (write(config_py_fd, config_py, config_py_len) != config_py_len) { uwsgi_error("uwsgi_build_plugin()/write()"); _exit(1); } char *cflags = uwsgi_get_cflags(); if (!cflags) { uwsgi_log("unable to find cflags\n"); _exit(1); } if (strlen(cflags) == 0) { uwsgi_log("invalid cflags\n"); _exit(1); } if (setenv("UWSGI_PLUGINS_BUILDER_CFLAGS", cflags, 1)) { uwsgi_error("uwsgi_build_plugin()/setenv()"); _exit(1); } // now run the python script char *argv[6]; argv[0] = getenv("PYTHON"); if (!argv[0]) argv[0] = "python"; argv[1] = UWSGI_BUILD_DIR "/uwsgiconfig.py"; argv[2] = "--extra-plugin"; char *space = strchr(directory, ' '); if (space) { *space = 0; argv[3] = directory; argv[4] = space+1; argv[5] = NULL; } else { argv[3] = directory; argv[4] = NULL; } execvp(argv[0], argv); // never here... _exit(1); }