X-Git-Url: http://www.privoxy.org/gitweb/?p=privoxy.git;a=blobdiff_plain;f=jcc.c;h=2d96ac9fdcad3a4f2341ae3d918c7de42b2ee90b;hp=5c25ff75bfd5cf8b28c960c58512f7dcda2238a6;hb=f4464cf737ef3de89c27a86c20595bebc802b29a;hpb=366bca82dc0feb3a01ce5eaee18aee7de11dbf82 diff --git a/jcc.c b/jcc.c index 5c25ff75..2d96ac9f 100644 --- a/jcc.c +++ b/jcc.c @@ -1,4 +1,4 @@ -const char jcc_rcs[] = "$Id: jcc.c,v 1.178 2008/05/10 13:23:38 fabiankeil Exp $"; +const char jcc_rcs[] = "$Id: jcc.c,v 1.186 2008/09/04 08:13:58 fabiankeil Exp $"; /********************************************************************* * * File : $Source: /cvsroot/ijbswa/current/jcc.c,v $ @@ -33,6 +33,39 @@ const char jcc_rcs[] = "$Id: jcc.c,v 1.178 2008/05/10 13:23:38 fabiankeil Exp $" * * Revisions : * $Log: jcc.c,v $ + * Revision 1.186 2008/09/04 08:13:58 fabiankeil + * Prepare for critical sections on Windows by adding a + * layer of indirection before the pthread mutex functions. + * + * Revision 1.185 2008/08/30 12:03:07 fabiankeil + * Remove FEATURE_COOKIE_JAR. + * + * Revision 1.184 2008/08/22 15:34:45 fabiankeil + * - Silence LLVM/Clang complaint. + * - Make received_hup_signal static. + * - Hide definitions for basedir, pidfile and received_hup_signal + * from __EMX__ as they only seem to be used in case of #ifdef unix. + * + * Revision 1.183 2008/08/21 07:09:35 fabiankeil + * Accept Shoutcast responses again. Problem reported + * and fix suggested by Stefan in #2062860. + * + * Revision 1.182 2008/06/27 11:13:56 fabiankeil + * Fix possible NULL-pointer dereference reported + * by din_a4 in #2003937. Pointy hat to me. + * + * Revision 1.181 2008/05/21 15:47:15 fabiankeil + * Streamline sed()'s prototype and declare + * the header parse and add structures static. + * + * Revision 1.180 2008/05/21 15:26:32 fabiankeil + * - Mark csp as immutable for send_crunch_response(). + * - Fix comment spelling. + * + * Revision 1.179 2008/05/20 20:13:32 fabiankeil + * Factor update_server_headers() out of sed(), ditch the + * first_run hack and make server_patterns_light static. + * * Revision 1.178 2008/05/10 13:23:38 fabiankeil * Don't provide get_header() with the whole client state * structure when it only needs access to csp->iob. @@ -1108,7 +1141,7 @@ static int client_protocol_is_unsupported(const struct client_state *csp, char * static jb_err get_request_destination_elsewhere(struct client_state *csp, struct list *headers); static jb_err get_server_headers(struct client_state *csp); static const char *crunch_reason(const struct http_response *rsp); -static void send_crunch_response(struct client_state *csp, struct http_response *rsp); +static void send_crunch_response(const struct client_state *csp, struct http_response *rsp); /* * static int request_contains_null_bytes(const struct client_state *csp, char *buf, int len); */ @@ -1141,32 +1174,35 @@ static int32 server_thread(void *data); #define sleep(N) DosSleep(((N) * 100)) #endif -#ifdef FEATURE_PTHREAD -pthread_mutex_t log_mutex; -pthread_mutex_t log_init_mutex; +#ifdef MUTEX_LOCKS_AVAILABLE +/* + * XXX: Does the locking stuff really belong in this file? + */ +privoxy_mutex_t log_mutex; +privoxy_mutex_t log_init_mutex; #if !defined(HAVE_GETHOSTBYADDR_R) || !defined(HAVE_GETHOSTBYNAME_R) -pthread_mutex_t resolver_mutex; +privoxy_mutex_t resolver_mutex; #endif /* !defined(HAVE_GETHOSTBYADDR_R) || !defined(HAVE_GETHOSTBYNAME_R) */ #ifndef HAVE_GMTIME_R -pthread_mutex_t gmtime_mutex; +privoxy_mutex_t gmtime_mutex; #endif /* ndef HAVE_GMTIME_R */ #ifndef HAVE_LOCALTIME_R -pthread_mutex_t localtime_mutex; +privoxy_mutex_t localtime_mutex; #endif /* ndef HAVE_GMTIME_R */ #ifndef HAVE_RANDOM -pthread_mutex_t rand_mutex; +privoxy_mutex_t rand_mutex; #endif /* ndef HAVE_RANDOM */ -#endif /* FEATURE_PTHREAD */ +#endif /* def MUTEX_LOCKS_AVAILABLE */ -#if defined(unix) || defined(__EMX__) +#if defined(unix) const char *basedir = NULL; const char *pidfile = NULL; -int received_hup_signal = 0; +static int received_hup_signal = 0; #endif /* defined unix */ /* HTTP snipplets. */ @@ -1275,6 +1311,13 @@ static const struct cruncher crunchers_light[] = { }; +/* + * XXX: Don't we really mean + * + * #if defined(unix) + * + * here? + */ #if !defined(_WIN32) && !defined(__OS2__) && !defined(AMIGA) /********************************************************************* * @@ -1308,7 +1351,9 @@ static void sig_handler(int the_signal) break; case SIGHUP: +#if defined(unix) received_hup_signal = 1; +#endif break; default: @@ -1501,7 +1546,7 @@ static jb_err get_server_headers(struct client_state *csp) { /* * It's a bodyless continue response, don't - * stop header parsing after reaching it's end. + * stop header parsing after reaching its end. * * As a result Privoxy will concatenate the * next response's head and parse and deliver @@ -1627,7 +1672,7 @@ static const char *crunch_reason(const struct http_response *rsp) * Returns : Nothing. * *********************************************************************/ -static void send_crunch_response(struct client_state *csp, struct http_response *rsp) +static void send_crunch_response(const struct client_state *csp, struct http_response *rsp) { const struct http_request *http = csp->http; char status_code[4]; @@ -1910,10 +1955,15 @@ static jb_err change_request_destination(struct client_state *csp) log_error(LOG_LEVEL_ERROR, "Couldn't parse rewritten request: %s.", jb_err_to_string(err)); } - http->ocmd = strdup(http->cmd); /* XXX: ocmd is a misleading name */ - if (http->ocmd == NULL) + else { - log_error(LOG_LEVEL_FATAL, "Out of memory copying rewritten HTTP request line"); + /* XXX: ocmd is a misleading name */ + http->ocmd = strdup(http->cmd); + if (http->ocmd == NULL) + { + log_error(LOG_LEVEL_FATAL, + "Out of memory copying rewritten HTTP request line"); + } } return err; @@ -2175,7 +2225,7 @@ static void chat(struct client_state *csp) list_append_list_unique(csp->headers, headers); destroy_list(headers); - err = sed(client_patterns, add_client_headers, csp); + err = sed(csp, FILTER_CLIENT_HEADERS); if (JB_ERR_OK != err) { assert(err == JB_ERR_PARSE); @@ -2708,10 +2758,11 @@ static void chat(struct client_state *csp) assert(csp->headers->first->str); assert(!http->ssl); - if (strncmpic(csp->headers->first->str, "HTTP", 4)) + if (strncmpic(csp->headers->first->str, "HTTP", 4) && + strncmpic(csp->headers->first->str, "ICY", 3)) { /* - * It doesn't look like a HTTP response: + * It doesn't look like a HTTP (or Shoutcast) response: * tell the client and log the problem. */ if (strlen(csp->headers->first->str) > 30) @@ -2729,10 +2780,11 @@ static void chat(struct client_state *csp) return; } - /* we have now received the entire header. + /* + * We have now received the entire server header, * filter it and send the result to the client */ - if (JB_ERR_OK != sed(server_patterns, add_server_headers, csp)) + if (JB_ERR_OK != sed(csp, FILTER_SERVER_HEADERS)) { log_error(LOG_LEVEL_FATAL, "Failed to parse server headers."); } @@ -2910,6 +2962,97 @@ static void usage(const char *myname) #endif /* #if !defined(_WIN32) || defined(_WIN_CONSOLE) */ +#ifdef MUTEX_LOCKS_AVAILABLE +/********************************************************************* + * + * Function : privoxy_mutex_lock + * + * Description : Locks a mutex. + * + * Parameters : + * 1 : mutex = The mutex to lock. + * + * Returns : Void. May exit in case of errors. + * + *********************************************************************/ +void privoxy_mutex_lock(privoxy_mutex_t *mutex) +{ +#ifdef FEATURE_PTHREAD + int err = pthread_mutex_lock(mutex); + if (err) + { + if (mutex != &log_mutex) + { + log_error(LOG_LEVEL_FATAL, + "Mutex locking failed: %s.\n", strerror(err)); + } + exit(1); + } +#else + EnterCriticalSection(mutex); +#endif /* def FEATURE_PTHREAD */ +} + + +/********************************************************************* + * + * Function : privoxy_mutex_unlock + * + * Description : Unlocks a mutex. + * + * Parameters : + * 1 : mutex = The mutex to unlock. + * + * Returns : Void. May exit in case of errors. + * + *********************************************************************/ +void privoxy_mutex_unlock(privoxy_mutex_t *mutex) +{ +#ifdef FEATURE_PTHREAD + int err = pthread_mutex_unlock(mutex); + if (err) + { + if (mutex != &log_mutex) + { + log_error(LOG_LEVEL_FATAL, + "Mutex unlocking failed: %s.\n", strerror(err)); + } + exit(1); + } +#else + LeaveCriticalSection(mutex); +#endif /* def FEATURE_PTHREAD */ +} + + +/********************************************************************* + * + * Function : privoxy_mutex_init + * + * Description : Prepares a mutex. + * + * Parameters : + * 1 : mutex = The mutex to initialize. + * + * Returns : Void. May exit in case of errors. + * + *********************************************************************/ +static void privoxy_mutex_init(privoxy_mutex_t *mutex) +{ +#ifdef FEATURE_PTHREAD + int err = pthread_mutex_init(mutex, 0); + if (err) + { + printf("Fatal error. Mutex initialization failed: %s.\n", + strerror(err)); + exit(1); + } +#else + InitializeCriticalSection(mutex); +#endif /* def FEATURE_PTHREAD */ +} +#endif /* def MUTEX_LOCKS_AVAILABLE */ + /********************************************************************* * * Function : initialize_mutexes @@ -2923,15 +3066,13 @@ static void usage(const char *myname) *********************************************************************/ static void initialize_mutexes(void) { - int err = 0; - -#ifdef FEATURE_PTHREAD +#ifdef MUTEX_LOCKS_AVAILABLE /* * Prepare global mutex semaphores */ - err = pthread_mutex_init(&log_mutex, 0); + privoxy_mutex_init(&log_mutex); - if (!err) err = pthread_mutex_init(&log_init_mutex, 0); + privoxy_mutex_init(&log_init_mutex); /* * XXX: The assumptions below are a bit naive @@ -2942,37 +3083,24 @@ static void initialize_mutexes(void) * thread safe. */ #if !defined(HAVE_GETHOSTBYADDR_R) || !defined(HAVE_GETHOSTBYNAME_R) - if (!err) err = pthread_mutex_init(&resolver_mutex, 0); + privoxy_mutex_init(&resolver_mutex); #endif /* !defined(HAVE_GETHOSTBYADDR_R) || !defined(HAVE_GETHOSTBYNAME_R) */ /* * XXX: should we use a single mutex for * localtime() and gmtime() as well? */ #ifndef HAVE_GMTIME_R - if (!err) err = pthread_mutex_init(&gmtime_mutex, 0); + privoxy_mutex_init(&gmtime_mutex); #endif /* ndef HAVE_GMTIME_R */ #ifndef HAVE_LOCALTIME_R - if (!err) err = pthread_mutex_init(&localtime_mutex, 0); + privoxy_mutex_init(&localtime_mutex); #endif /* ndef HAVE_GMTIME_R */ #ifndef HAVE_RANDOM - if (!err) err = pthread_mutex_init(&rand_mutex, 0); + privoxy_mutex_init(&rand_mutex); #endif /* ndef HAVE_RANDOM */ -#endif /* FEATURE_PTHREAD */ - - /* - * TODO: mutex support for mingw32 would be swell. - */ - - if (err) - { - printf("Fatal error. Mutex initialization failed: %s.\n", - strerror(err)); - exit(1); - } - - return; +#endif /* def MUTEX_LOCKS_AVAILABLE */ } @@ -3188,15 +3316,6 @@ int main(int argc, const char *argv[]) random_seed = (unsigned int)time(NULL); #ifdef HAVE_RANDOM srandom(random_seed); -#elif defined (_WIN32) - /* - * See pick_from_range() in miscutil.c for details. - */ - log_error(LOG_LEVEL_INFO, - "No thread-safe PRNG implemented for your platform. " - "Using weak \'randomization\' factor which will " - "limit the already questionable usefulness of " - "header-time-randomizing actions (disabled by default)."); #else srand(random_seed); #endif /* ifdef HAVE_RANDOM */ @@ -3541,23 +3660,6 @@ static void listen_loop(void) } #endif -#ifdef __OS2__ -#ifdef FEATURE_COOKIE_JAR - /* - * Need a workaround here: we have to fclose() the jarfile, or we die because it's - * already open. I think unload_configfile() is not being run, which should do - * this work. Until that can get resolved, we'll use this workaround. - */ - if (csp) - if(csp->config) - if (csp->config->jar) - { - fclose(csp->config->jar); - csp->config->jar = NULL; - } -#endif /* FEATURE_COOKIE_JAR */ -#endif /* __OS2__ */ - if ( NULL == (csp = (struct client_state *) zalloc(sizeof(*csp))) ) { log_error(LOG_LEVEL_FATAL, "malloc(%d) for csp failed: %E", sizeof(*csp)); @@ -3855,13 +3957,6 @@ static void listen_loop(void) #endif freez(configfile); -#ifdef FEATURE_COOKIE_JAR - if (NULL != config->jar) - { - fclose(config->jar); - } -#endif - #if defined(_WIN32) && !defined(_WIN_CONSOLE) /* Cleanup - remove taskbar icon etc. */ TermLogWindow();