📄 config.c
字号:
else cse_close(&s, "close"); if (is_change > 0) { char buf[128]; time_t now = host->last_update; buf[0] = 0;#ifndef WIN32 ctime_r(&now, buf);#else strcpy(buf, ctime(&now));#endif sprintf(host->config_source, "Resin (%s)", buf); } if (is_change > 0 || prev_update < host->config->start_time || host->config->update_interval >= AUTO_WRITE_TIME) { write_config(host->config); } return 1; } else { ERR(("%s:%d:cse_update_host_from_resin(): can't open any connections\n", __FILE__, __LINE__)); } return 0;}/** * Initialize the configuration. */voidcse_init_config(config_t *config){ LOG(("%s:%d:cse_init_config(): initializing\n", __FILE__, __LINE__)); if (! config->p) config->p = cse_create_pool(config); /* // XXX: need to free these now. */ config->hosts = 0; config->error = 0; /* for (i = 0; i < CACHE_SIZE; i++) { if (g_url_cache[i].uri) { free(g_url_cache[i].uri); free(g_url_cache[i].host); } g_url_cache[i].uri = 0; } */ if (! config->start_time) config->start_time = time(0); config->update_count++; /* config->enable_caucho_status = 0; */ config->disable_session_failover = 0; config->update_interval = 15; strcpy(config->session_url_prefix, ";jsessionid="); strcpy(config->session_cookie, "JSESSIONID"); config->config_cluster.config = config; #ifdef WIN32 strcpy(config->work_dir, "/temp"); mkdir(config->work_dir); chmod(config->work_dir, 0775);#else strcpy(config->work_dir, "/tmp");#endif /* cse_add_host(&config->config_cluster, "localhost", 6802); cse_update_from_resin(config); */ if (! config->lock) { config->lock = cse_create_lock(config); LOG(("%s:%d:cse_init_config(): config lock %p\n", __FILE__, __LINE__, config->lock)); config->config_lock = cse_create_lock(config); } /* read_all_config(config); */}voidcse_add_config_server(mem_pool_t *pool, config_t *config, const char *host, int port){ cse_add_host(pool, &config->config_cluster, host, port); if (! *config->config_file) { sprintf(config->config_file, "%s_%d", host, port); } if (*config->work_dir) { sprintf(config->config_path, "%s/%s", config->work_dir, config->config_file); read_all_config(config); }}/** * Matches the host information in the config */static voidcse_update_host(config_t *config, resin_host_t *host, time_t now){ struct stat st; if (now < host->last_update + config->update_interval) { /* If current value is still valid, return */ return; } if (config->config_path && stat(config->config_path, &st) == 0) { if (config->last_file_update < st.st_mtime) { config->last_file_update = st.st_mtime; read_all_config_impl(config); } if (now < host->last_update + config->update_interval && config->start_time <= host->last_update) { /* * If the cached value is still valid and Resin has been checked * at least once since startup, use the cached value. */ return; } } LOG(("%s:%d:cse_update_host(): %s:%d(%p) old:%d now:%d()\n", __FILE__, __LINE__, host->name, host->port, host, host->last_update, now)); cse_update_host_from_resin(host, now); LOG(("%s:%d:cse_update_host(): complete %s:%d(%p) old:%d now:%d()\n", __FILE__, __LINE__, host->name, host->port, host, host->last_update, now));}/** * Matches the host information in the config */static resin_host_t *cse_match_host_impl(config_t *config, const char *host_name, int port, time_t now){ resin_host_t *host = cse_create_host(config, host_name, port); cse_update_host(config, host, now); if (host != host->canonical) cse_update_host(config, host->canonical, now); return host->canonical;}/** * Matches the host information in the config */resin_host_t *cse_match_host(config_t *config, const char *host_name, int port, time_t now){ resin_host_t *host; if (config) cse_lock(config->config_lock); host = cse_match_host_impl(config, host_name, port, now); if (config) cse_unlock(config->config_lock); return host;}/** * tests if 'full' starts with 'part' * * If it's not an exact match, the next character of 'full' must be '/'. * That way, a servlet mapping of '/foo/ *' will match /foo, /foo/bar, but * not /foolish. */static intcse_starts_with(const char *full, const char *part){ char ch1, ch2; while ((ch2 = *part++) && (ch1 = *full++) && ch1 == ch2) { } if (ch2) return 0; else if (! *full) return 1; else if (*full == '/') return 1; #ifdef WIN32 /* special case so web-inf. will match */ if (full[0] != '.') return 0; else if (full[1] == 0 || full[1] == '/' || full[1] == '\\') return 1; else if (full[1] != '.') return 0; else if (full[2] == 0 || full[2] == '/' || full[2] == '\\') return 1;#endif return 0;}static intcse_match_suffix(const char *full, const char *suffix){ int len = strlen(suffix); do { char *match = strstr(full, suffix); if (! match) return 0; if (! match[len] || match[len] == '/') return 1;#ifdef WIN32 { char ch; if ((ch = match[len]) == '.' || ch == ' ') { for (; (ch = match[len]) == '.' || ch == ' '; len++) { } if (! match[len] || match[len] == '/') return 1; } }#endif full = match + len; } while (*full); return 0;}static inthex_to_digit(int hex){ if (hex >= '0' && hex <= '9') return hex - '0'; else if (hex >= 'a' && hex <= 'f') return hex - 'a' + 10; else if (hex >= 'A' && hex <= 'F') return hex - 'A' + 10; else return 0;}/** * Normalizes the URI, unescaping the HTTP URL encodings. */static voidnormalize_uri(config_t *config, const char *raw_uri, char *uri, int len, int unescape){ int i, k; int ch; int test_ch = config->session_url_prefix[0]; int prefix_len = strlen(config->session_url_prefix); k = 0; for (i = 0; (ch = raw_uri[i]) && i + 1 < len; i++) { /* strip the session_url_prefix */ if (ch == test_ch && ! strncmp(raw_uri + i, config->session_url_prefix, prefix_len)) { break; } if (ch == '%' && unescape) { int h1 = raw_uri[i + 1]; if (h1 == 'u') { ch = hex_to_digit(raw_uri[i + 2]); ch = 16 * ch + hex_to_digit(raw_uri[i + 3]); ch = 16 * ch + hex_to_digit(raw_uri[i + 4]); ch = 16 * ch + hex_to_digit(raw_uri[i + 5]); i += 4; } else { ch = hex_to_digit(h1); ch = 16 * ch + hex_to_digit(raw_uri[i + 2]); i += 2; if ((ch & 0xf0) == 0xc0 && raw_uri[i + 1] == '%' && i + 3 < len) { int ch2 = hex_to_digit(raw_uri[i + 2]); ch2 = 16 * ch2 + hex_to_digit(raw_uri[i + 3]); if (ch2 >= 0x80) { ch = ((ch & 0x3f) << 6) + (ch2 & 0x3f); i += 3; } } } } else if (ch == ':') break; if (ch == '/' && k > 0 && (uri[k - 1] == '/' || uri[k - 1] == '\\')) continue;#ifdef WIN32 if (ch >= 0 && isupper(ch)) uri[k++] = tolower(ch); else if (ch >= 0) uri[k++] = ch;#else if (ch >= 0) uri[k++] = ch;#endif } uri[k] = 0;}static resin_host_t *cse_is_match(config_t *config, const char *raw_host, int port, const char *raw_uri, int unescape, time_t now){ char uri[16 * 1024]; char host_name[1024]; char *suburi; int len = sizeof(uri) - 1; int host_len = sizeof(host_name) - 1; web_app_t *app_ptr; web_app_t *app; int has_host; unsigned int best_len; location_t *loc; int i; int ch; resin_host_t *host; int is_match = 0; for (i = 0; raw_host && (ch = raw_host[i]) && i + 1 < host_len; i++) { if (isupper(ch)) host_name[i] = tolower(ch); else host_name[i] = ch; } host_name[i] = 0; host = cse_match_host(config, host_name, port, now); if (! host) return 0; host = host->canonical; /* unconfigured hosts automatically match */ if (! host->has_data) return host; normalize_uri(config, raw_uri, uri, len, unescape); has_host = 0; best_len = 0; app = 0; for (app_ptr = host->applications; app_ptr; app_ptr = app_ptr->next) { /** * The uri prefix must match. */ if (! cse_starts_with(uri, app_ptr->context_path)) continue; if (strlen(app_ptr->context_path) < best_len) continue; LOG(("%s:%d:cse_is_match(): app-match host:%s%s with host:%s uri:%s\n", __FILE__, __LINE__, host->name, app_ptr->context_path ? app_ptr->context_path : "", host_name, uri)); best_len = strlen(app_ptr->context_path); app = app_ptr; } if (! app) return 0; if (! app->has_data) { host->last_update = 0; return host; } suburi = uri + best_len; is_match = 0; for (loc = app->locations; loc; loc = loc->next) { LOG(("%s:%d:cse_is_match(): match host:%s%s prefix:%s suffix:%s with host:%s uri:%s next:%x ignore:%d exact:%d\n", __FILE__, __LINE__, host->name, app->context_path ? app->context_path : "null", loc->prefix ? loc->prefix : "null", loc->suffix ? loc->suffix : "null", host_name, uri, loc->next, loc->ignore, loc->is_exact)); if (loc->is_exact && ! strcmp(suburi, loc->prefix)) { } else if (loc->is_exact) continue; else if (! cse_starts_with(suburi, loc->prefix)) continue; else if (loc->suffix && ! cse_match_suffix(suburi, loc->suffix)) continue; if (loc->ignore) is_match = -1; else if (! is_match) is_match = 1; } if (strstr(suburi, "/j_security_check")) return host; return is_match > 0 ? host : 0;}/** * Tests if the request matches a Resin URL. * * @param config the plugin configuration structure * @param host the request's host * @param port the request's port * @param url the request's uri */resin_host_t *cse_match_request(config_t *config, const char *host, int port, const char *uri, int unescape, time_t now){ int hash = port; int i; hash_t *entry; char *test_uri; char *test_host; int test_port; int test_count; resin_host_t *test_match_host; resin_host_t *match_host; /* If no ResinConfigServer, never match unless explicit, bug #3 */ if (! config || ! config->config_cluster.srun_size) return 0; if (! host) host = ""; if (! uri) uri = ""; for (i = 0; host[i]; i++) hash = 65531 * hash + host[i]; for (i = 0; uri[i]; i++) hash = 65531 * hash + uri[i]; if (hash < 0) hash = -hash; hash = hash % CACHE_SIZE; entry = &g_url_cache[hash]; test_count = entry->count; test_uri = entry->uri; test_host = entry->host; test_port = entry->port; test_match_host = entry->match_host; cse_lock(config->lock); if (g_update_count != entry->update_count) { } else if (test_count != entry->count) { } else if (! test_uri || strcmp(test_uri, uri)) { } else if (! test_host || strcmp(test_host, host)) { } else if (test_port && test_port != port) { } else if (! test_match_host && config->last_update + config->update_interval < now) { /* if non-match, the timeout is the config update time */ } else if (test_match_host && test_match_host->last_update + config->update_interval < now) { } else { cse_unlock(config->lock); return test_match_host; } cse_unlock(config->lock); match_host = cse_is_match(config, host, port, uri, unescape, now); cse_lock(config->lock); entry->update_count = g_update_count; entry->count++; entry->match_host = match_host; if (entry->uri) { free(entry->host); free(entry->uri); entry->uri = 0; entry->host = 0; } LOG(("%s:%d:cse_match_request(): entry %s %s match:%s\n", __FILE__, __LINE__, host, uri, (match_host != 0) ? "yes" : "no")); entry->host = strdup(host ? host : ""); entry->uri = strdup(uri); entry->port = port; entry->count++; config->last_update = now; cse_unlock(config->lock); return match_host;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -