X-Git-Url: http://www.privoxy.org/gitweb/?a=blobdiff_plain;f=filters.c;h=c4bfd9a7faad86a40d5904452cb2070218fd6984;hb=5d9cfc05611df825ca8e09bd578506ef62f17cd9;hp=43cdaccc0e915f6433661e8862bc1049315acffc;hpb=2b292d6a663868131e45f4789d0a29df79e1489a;p=privoxy.git diff --git a/filters.c b/filters.c index 43cdaccc..c4bfd9a7 100644 --- a/filters.c +++ b/filters.c @@ -1,4 +1,4 @@ -const char filters_rcs[] = "$Id: filters.c,v 1.133 2010/09/14 07:16:07 fabiankeil Exp $"; +const char filters_rcs[] = "$Id: filters.c,v 1.147 2011/10/30 16:15:43 fabiankeil Exp $"; /********************************************************************* * * File : $Source: /cvsroot/ijbswa/current/filters.c,v $ @@ -50,11 +50,6 @@ const char filters_rcs[] = "$Id: filters.c,v 1.133 2010/09/14 07:16:07 fabiankei #include #include -#ifdef HAVE_RFC2553 -#include -#include -#endif /* def HAVE_RFC2553 */ - #ifndef _WIN32 #ifndef __OS2__ #include @@ -294,6 +289,10 @@ int block_acl(const struct access_control_addr *dst, const struct client_state * { return(0); } + else + { + return(1); + } } else if ( #ifdef HAVE_RFC2553 @@ -486,7 +485,7 @@ int acl_addr(const char *aspec, struct access_control_addr *aca) * of octets (128-bit CPU could do it in one iteration). */ /* - * Octets after prefix can be ommitted because of + * Octets after prefix can be omitted because of * previous initialization to zeros. */ for (i = 0; (i < addr_len) && masklength; i++) @@ -575,7 +574,7 @@ struct http_response *block_url(struct client_state *csp) } if (csp->action->flags & ACTION_REDIRECT) { - log_error(LOG_LEVEL_ERROR, "redirect{} overruled by block."); + log_error(LOG_LEVEL_ERROR, "redirect{} overruled by block."); } /* * Else, prepare a response @@ -669,7 +668,7 @@ struct http_response *block_url(struct client_state *csp) if(csp->action->flags & ACTION_HANDLE_AS_EMPTY_DOCUMENT) { /* - * Send empty document. + * Send empty document. */ new_content_type = csp->action->string[ACTION_STRING_CONTENT_TYPE]; @@ -715,27 +714,8 @@ struct http_response *block_url(struct client_state *csp) { jb_err err; struct map * exports; - char *p; - - /* - * Workaround for stupid Netscape bug which prevents - * pages from being displayed if loading a referenced - * JavaScript or style sheet fails. So make it appear - * as if it succeeded. - */ - if ( NULL != (p = get_header_value(csp->headers, "User-Agent:")) - && !strncmpic(p, "mozilla", 7) /* Catch Netscape but */ - && !strstr(p, "Gecko") /* save Mozilla, */ - && !strstr(p, "compatible") /* MSIE */ - && !strstr(p, "Opera")) /* and Opera. */ - { - rsp->status = strdup("200 Request for blocked URL"); - } - else - { - rsp->status = strdup("403 Request for blocked URL"); - } + rsp->status = strdup("403 Request blocked by Privoxy"); if (rsp->status == NULL) { free_http_response(rsp); @@ -856,7 +836,7 @@ struct http_response *trust_url(struct client_state *csp) * Export the protocol, host, port, and referrer information */ err = map(exports, "hostport", 1, csp->http->hostport, 1); - if (!err) err = map(exports, "protocol", 1, csp->http->ssl ? "https://" : "http://", 1); + if (!err) err = map(exports, "protocol", 1, csp->http->ssl ? "https://" : "http://", 1); if (!err) err = map(exports, "path", 1, csp->http->path, 1); if (NULL != (p = get_header_value(csp->headers, "Referer:"))) @@ -976,7 +956,7 @@ struct http_response *trust_url(struct client_state *csp) * 2 : b = The filter list to compile * * Returns : NULL in case of errors, otherwise the - * pcrs job list. + * pcrs job list. * *********************************************************************/ pcrs_job *compile_dynamic_pcrs_job_list(const struct client_state *csp, const struct re_filterfile_spec *b) @@ -1003,10 +983,9 @@ pcrs_job *compile_dynamic_pcrs_job_list(const struct client_state *csp, const st dummy = pcrs_compile_dynamic_command(pattern->str, variables, &error); if (NULL == dummy) { - assert(error < 0); log_error(LOG_LEVEL_ERROR, - "Adding filter job \'%s\' to dynamic filter %s failed: %s", - pattern->str, b->name, pcrs_strerror(error)); + "Compiling dynamic pcrs job '%s' for '%s' failed with error code %d: %s", + pattern->str, b->name, error, pcrs_strerror(error)); continue; } else @@ -1046,7 +1025,7 @@ pcrs_job *compile_dynamic_pcrs_job_list(const struct client_state *csp, const st * 2 : pcrs_command = pcrs command formatted as string (s@foo@bar@) * * - * Returns : NULL if the pcrs_command didn't change the url, or + * Returns : NULL if the pcrs_command didn't change the url, or * the result of the modification. * *********************************************************************/ @@ -1105,7 +1084,7 @@ char *rewrite_url(char *old_url, const char *pcrs_command) * * Parameters : * 1 : subject = the string to check - * 2 : redirect_mode = +fast-redirect{} mode + * 2 : redirect_mode = +fast-redirect{} mode * * Returns : NULL if no URL was found, or * the last URL found. @@ -1128,20 +1107,48 @@ char *get_last_url(char *subject, const char *redirect_mode) if (0 == strcmpic(redirect_mode, "check-decoded-url")) { - log_error(LOG_LEVEL_REDIRECTS, "Decoding \"%s\" if necessary.", subject); - new_url = url_decode(subject); - if (new_url != NULL) + log_error(LOG_LEVEL_REDIRECTS, + "Checking \"%s\" for encoded redirects.", subject); + /* + * Check each parameter in the URL separately. + * Sectionize the URL at "?" and "&", + * then URL-decode each component, + * and look for a URL in the decoded result. + * Keep the last one we spot. + */ + char *found = NULL; + char *token = strtok(subject, "?&"); + while (token) { - freez(subject); - subject = new_url; + char *dtoken = url_decode(token); + if (!dtoken) continue; + char *h1 = strstr(dtoken, "http://"); + char *h2 = strstr(dtoken, "https://"); + char *h = (h1 && h2 + ? (h1 < h2 ? h1 : h2) + : (h1 ? h1 : h2)); + if (h) + { + freez(found); + found = strdup(h); + } + token = strtok(NULL, "?&"); } - else + + if (found) { - log_error(LOG_LEVEL_ERROR, "Unable to decode \"%s\".", subject); + freez(subject); + return found; } + + freez(subject); + return NULL; } - log_error(LOG_LEVEL_REDIRECTS, "Checking \"%s\" for redirects.", subject); + /* Else, just look for a URL inside this one, without decoding anything. */ + + log_error(LOG_LEVEL_REDIRECTS, + "Checking \"%s\" for unencoded redirects.", subject); /* * Find the last URL encoded in the request @@ -1164,7 +1171,7 @@ char *get_last_url(char *subject, const char *redirect_mode) )) { /* - * Return new URL if we found a redirect + * Return new URL if we found a redirect * or if the subject already was a URL. * * The second case makes sure that we can @@ -1270,7 +1277,7 @@ struct http_response *redirect_url(struct client_state *csp) #endif /* def FEATURE_FAST_REDIRECTS */ csp->action->flags &= ~ACTION_REDIRECT; - /* Did any redirect action trigger? */ + /* Did any redirect action trigger? */ if (new_url) { if (0 == strcmpic(new_url, csp->http->url)) @@ -1524,7 +1531,7 @@ static char *pcrs_filter_response(struct client_state *csp) struct re_filterfile_spec *b; struct list_entry *filtername; - /* + /* * Sanity first */ if (csp->iob->cur >= csp->iob->eod) @@ -1806,8 +1813,14 @@ static jb_err remove_chunked_transfer_coding(char *buffer, size_t *size) if ((newsize += chunksize) >= *size) { + /* + * XXX: The message is a bit confusing. Isn't the real problem that + * the specified chunk size is greater than the number of bytes + * left in the buffer? This probably means the connection got + * closed prematurely. To be investigated after 3.0.17 is out. + */ log_error(LOG_LEVEL_ERROR, - "Chunk size %d exceeds buffer size %d in \"chunked\" transfer coding", + "Chunk size %d exceeds buffer size %d in \"chunked\" transfer coding", chunksize, *size); return JB_ERR_PARSE; } @@ -1823,7 +1836,7 @@ static jb_err remove_chunked_transfer_coding(char *buffer, size_t *size) break; } } - + /* XXX: Should get its own loglevel. */ log_error(LOG_LEVEL_RE_FILTER, "De-chunking successful. Shrunk from %d to %d", *size, newsize); @@ -2202,7 +2215,7 @@ const struct forward_spec *forward_url(struct client_state *csp, /********************************************************************* * - * Function : direct_response + * Function : direct_response * * Description : Check if Max-Forwards == 0 for an OPTIONS or TRACE * request and if so, return a HTTP 501 to the client. @@ -2211,7 +2224,7 @@ const struct forward_spec *forward_url(struct client_state *csp, * requests properly. Still, what we do here is rfc- * compliant, whereas ignoring or forwarding are not. * - * Parameters : + * Parameters : * 1 : csp = Current client state (buffers, headers, etc...) * * Returns : http_response if , NULL if nonmatch or handler fail @@ -2227,7 +2240,7 @@ struct http_response *direct_response(struct client_state *csp) { for (p = csp->headers->first; (p != NULL) ; p = p->next) { - if (!strncmpic("Max-Forwards:", p->str, 13)) + if (!strncmpic(p->str, "Max-Forwards:", 13)) { unsigned int max_forwards; @@ -2251,7 +2264,7 @@ struct http_response *direct_response(struct client_state *csp) { return cgi_error_memory(); } - + if (NULL == (rsp->status = strdup("501 Not Implemented"))) { free_http_response(rsp); @@ -2352,7 +2365,7 @@ int content_requires_filtering(struct client_state *csp) * Description : Checks whether there are any content filters * enabled for the current request. * - * Parameters : + * Parameters : * 1 : action = Action spec to check. * * Returns : TRUE for yes, FALSE otherwise