コード例 #1
0
ファイル: passthrough.c プロジェクト: Distrotech/bogofilter
static bool write_header(rc_t status, readfunc_t rf, void *rfarg)
{
    ssize_t rd;
    char   *out;

    bool hadlf = true;
    bool seen_subj = false;

    bool seen_place_header = false;

    int bogolen = strlen(spam_header_name);
    const char *subjstr = "Subject:";
    int subjlen = strlen(subjstr);

    eol = NULL;

    /* print headers */
    while ((rd = rf(&out, rfarg)) > 0)
    {
	if (eol == NULL) {
	    if (memcmp(out+rd-1, NL, 1) == 0)
		eol = NL;
	    if (rd >=2 && memcmp(out+rd-2, CRLF, 2) == 0)
		eol = CRLF;
	}

	/* skip over spam_header_name ("X-Bogosity:") lines */
	while (rd >= bogolen && 
	       memcmp(out, spam_header_name, bogolen) == 0) {
	    while (((rd = rf(&out, rfarg)) > 0) && 
		   (out[0] == ' ' || out[0] == '\t') )
		/* empty loop */ ;
	}

	/* detect spam_header_place line */
	if ( !seen_place_header &&
	     *spam_header_place != '\0' &&
	    memcmp(out, spam_header_place, strlen(spam_header_place)) == 0)
	{
	    seen_place_header = true;
	    write_spam_info();
	}

	/* detect end of headers */
	if (is_eol(out, rd) ||
	    is_hb_delim(out, rd, have_body))
	    /* check for non-empty blank line */
	    break;

	/* rewrite "Subject: " line */
	if (!seen_subj && rd >= subjlen) {
	    const char *tag = NULL;

	    if (status == RC_SPAM && spam_subject_tag != NULL)
		tag = spam_subject_tag;

	    if (status == RC_UNSURE && unsure_subject_tag != NULL)
		tag = unsure_subject_tag;

	    if (tag != NULL && strncasecmp(out, subjstr, subjlen) == 0) {
		seen_subj = true;
		(void) fprintf(fpo, "%.*s %s", subjlen, out, tag);
		if (out[subjlen] != ' ')
		    fputc(' ', fpo);
		(void) fwrite(out + subjlen, 1, rd - subjlen, fpo);
		continue;
	    }
	}

	hadlf = (out[rd-1] == '\n');
	(void) fwrite(out, 1, rd, fpo);
	if (ferror(fpo)) cleanup_exit(EX_ERROR, 1);
    }

    if (!seen_place_header)
	write_spam_info();

    if (!hadlf)
	(void) fputs(eol, fpo);

    return seen_subj;
}
コード例 #2
0
void write_message(rc_t status)
{
    ssize_t rd;
    readfunc_t rf = NULL;	/* assignment to quench warning */
    void *rfarg = 0;		/* assignment to quench warning */
    char *out;
    textdata_t *text;
    int seen_subj = 0;

    if (passthrough) {
	int hadlf = 1;
	int bogolen = strlen(spam_header_name);
	const char *subjstr = "Subject:";
	int subjlen = strlen(subjstr);
	/* initialize */
	switch (passmode) {
	    case PASS_MEM:
		rf = read_mem;
		text = textblock_head();
		rfarg = &text;
		break;
	    case PASS_SEEK:
		rf = read_seek;
		rfarg = fpin;
		rewind(rfarg);
		break;
	    default:
		abort();
	}

	/* print headers */
	while ((rd = rf(&out, rfarg)) > 0)
	{
	    /* skip over spam_header ("X-Bogosity:") lines */
	    while (rd >= bogolen && memcmp(out, spam_header_name, bogolen) == 0) {
		while (((rd = rf(&out, rfarg)) > 0) && 
		       (out[0] == ' ' || out[0] == '\t') )
		    /* empty loop */ ;
	    }

	    /* detect end of headers */
	    if (is_eol(out, rd) ||
		is_hb_delim(out, rd, have_body))
		/* check for non-empty blank line */
		break;

	    /* rewrite "Subject: " line */
	    if (status == RC_SPAM &&
		rd >= subjlen && 
		spam_subject_tag != NULL &&
		strncasecmp(out, subjstr, subjlen) == 0) {
		(void) fprintf(fpo, "%.*s %s", subjlen, out, spam_subject_tag);
		if (out[subjlen] != ' ')
		    fputc(' ', fpo);
		(void) fwrite(out + subjlen, 1, rd - subjlen, fpo);
		seen_subj = 1;
		continue;
	    }

	    hadlf = (out[rd-1] == '\n');
	    (void) fwrite(out, 1, rd, fpo);
	    if (ferror(fpo)) cleanup_exit(2, 1);
	}

	if (!hadlf)
	    fputc('\n', fpo);
    }

    if (passthrough || verbose || terse) {
	typedef char *formatter(char *buff, size_t size);
	formatter *fcn = terse ? format_terse : format_header;
	char buff[256];
	/* print spam-status at the end of the header
	 * then mark the beginning of the message body */
	(*fcn)(buff, sizeof(buff));
	fputs (buff, fpo);
	fputs ("\n", fpo);
    }

    if (verbose || passthrough || Rtable) {
	verbose += passthrough;
	print_stats( stdout );
	verbose -= passthrough;
    }

    if (passthrough && !seen_subj &&
	status == RC_SPAM && spam_subject_tag != NULL) {
	(void) fprintf(fpo, "Subject: %s\n", spam_subject_tag);
    }

    if (passthrough) {
	int hadlf = 1;
	/* If the message terminated early (without body or blank
	 * line between header and body), enforce a blank line to
	 * prevent anything past us from choking. */
	(void)fputc('\n', fpo);

	/* print body */
	while ((rd = rf(&out, rfarg)) > 0)
	{
	    (void) fwrite(out, 1, rd, fpo);
	    hadlf = (out[rd-1] == '\n');
	    if (ferror(fpo)) cleanup_exit(2, 1);
	}

	if (!hadlf) fputc('\n', fpo);

	if (fflush(fpo) || ferror(fpo) || (fpo != stdout && fclose(fpo))) {
	    cleanup_exit(2, 1);
	}
    }
}