X-Git-Url: http://www.privoxy.org/gitweb/?p=privoxy.git;a=blobdiff_plain;f=pcrs.c;h=0553a53e9ac34ed700aab8c0d835cacf58075913;hp=4d112271a08a71f63d622f0ad72c8d684fccf21d;hb=584674c60a8487df489d44e926eb9a3dc6130a23;hpb=37b60a3260c885bfa3f33d94a186a2741fca52f5 diff --git a/pcrs.c b/pcrs.c index 4d112271..0553a53e 100644 --- a/pcrs.c +++ b/pcrs.c @@ -1,4 +1,4 @@ -const char pcrs_rcs[] = "$Id: pcrs.c,v 1.46 2014/11/14 10:40:10 fabiankeil Exp $"; +const char pcrs_rcs[] = "$Id: pcrs.c,v 1.50 2016/05/25 10:50:28 fabiankeil Exp $"; /********************************************************************* * * File : $Source: /cvsroot/ijbswa/current/pcrs.c,v $ @@ -80,6 +80,8 @@ static int is_hex_sequence(const char *sequence); *********************************************************************/ const char *pcrs_strerror(const int error) { + static char buf[100]; + if (error != 0) { switch (error) @@ -119,7 +121,11 @@ const char *pcrs_strerror(const int error) * version. If Privoxy is linked against a newer * PCRE version all bets are off ... */ - default: return "Unknown error. Privoxy out of sync with PCRE?"; + default: + snprintf(buf, sizeof(buf), + "Error code %d. For details, check the pcre documentation.", + error); + return buf; } } /* error >= 0: No error */ @@ -176,6 +182,38 @@ static int pcrs_parse_perl_options(const char *optstring, int *flags) } +#ifdef FUZZ +/********************************************************************* + * + * Function : pcrs_compile_fuzzed_replacement + * + * Description : Wrapper around pcrs_compile_replacement() for + * fuzzing purposes. + * + * Parameters : + * 1 : replacement = replacement part of s/// operator + * in perl syntax + * 2 : errptr = pointer to an integer in which error + * conditions can be returned. + * + * Returns : pcrs_substitute data structure, or NULL if an + * error is encountered. In that case, *errptr has + * the reason. + * + *********************************************************************/ +extern pcrs_substitute *pcrs_compile_fuzzed_replacement(const char *replacement, int *errptr) +{ + int capturecount = PCRS_MAX_SUBMATCHES; /* XXX: fuzzworthy? */ + int trivial_flag = 0; /* We don't want to fuzz strncpy() */ + + *errptr = 0; /* XXX: Should pcrs_compile_replacement() do this? */ + + return pcrs_compile_replacement(replacement, trivial_flag, capturecount, errptr); + +} +#endif + + /********************************************************************* * * Function : pcrs_compile_replacement @@ -206,7 +244,14 @@ static pcrs_substitute *pcrs_compile_replacement(const char *replacement, int tr size_t length; char *text; pcrs_substitute *r; - +#ifdef FUZZ + static const char *replacement_stack; + static const size_t *length_stack; + static pcrs_substitute *r_stack; + + replacement_stack = replacement; + length_stack = &length; +#endif i = k = l = quoted = 0; /* @@ -227,6 +272,10 @@ static pcrs_substitute *pcrs_compile_replacement(const char *replacement, int tr } memset(r, '\0', sizeof(pcrs_substitute)); +#ifdef FUZZ + r_stack = r; +#endif + length = strlen(replacement); if (NULL == (text = (char *)malloc(length + 1))) @@ -369,8 +418,12 @@ static pcrs_substitute *pcrs_compile_replacement(const char *replacement, int tr goto plainchar; } + assert(l < PCRS_MAX_SUBMATCHES - 1); + assert(r->backref[l] < PCRS_MAX_SUBMATCHES + 2); /* Valid and in range? -> record */ - if (0 <= r->backref[l] && r->backref[l] < PCRS_MAX_SUBMATCHES + 2) + if ((0 <= r->backref[l]) && + (r->backref[l] < PCRS_MAX_SUBMATCHES + 2) && + (l < PCRS_MAX_SUBMATCHES - 1)) { r->backref_count[r->backref[l]] += 1; r->block_offset[++l] = k;