/*
* Copyright (c) 2005 Sendmail, Inc. and its suppliers.
* All rights reserved.
*
* By using this file, you agree to the terms and conditions set
* forth in the LICENSE file which can be found at the top level of
* the sendmail distribution.
*/
#include "sm/generic.h"
SM_RCSID("@(#)$Id: t-extracthdr.c,v 1.10 2006/07/16 02:07:40 ca Exp $")
#include "sm/error.h"
#include "sm/assert.h"
#include "sm/sm_extracthdr.h"
#include "sm/io.h"
#include "sm/sysexits.h"
#include "sm/test.h"
static int Verbose = 0;
static int
testextracthdr(sm_file_T *fp, size_t chunksize)
{
sm_ret_T ret;
bool newchunk;
sm_xhdr_ctx_P sm_xhdr_ctx;
size_t len, off, thislen;
uchar *chunk;
char mail1[] = "From: someone@some.com\r\nTo: luser@victim.com\r\nSUBJECT: M$\r\nsucks\r\nMIME-Version: 1.0\r\nContent-Type: multipart/alternative; boundary=\"abcdef\"\r\n\r\noh really?\r\n";
off = 0;
ret = sm_xhdr_init(SM_XHDR_FL_SKIP_FIRST_BLANK, &sm_xhdr_ctx);
SM_TEST(sm_is_success(ret));
chunk = (uchar *) mail1;
len = thislen = strlen((char *)chunk);
newchunk = true;
if (fp != NULL)
{
ret = sm_refill(fp);
if (sm_is_err(ret))
return ret;
chunk = f_p(*fp);
len = thislen = f_r(*fp);
}
if (chunksize > 0 && thislen > chunksize)
thislen = chunksize;
do {
ret = sm_xhdr(chunk + off, thislen, newchunk, sm_xhdr_ctx);
newchunk = false;
if (ret == SM_XHDR_GOT1 || ret == SM_XHDR_GOTA ||
ret == SM_XHDR_GOTL)
{
sm_io_fprintf(smioout, "name: %#S\n",
sm_xhdr_ctx->sm_xhdr_name);
sm_io_fprintf(smioout, "value: %#S\n",
sm_xhdr_ctx->sm_xhdr_value);
}
if (ret == SM_XHDR_CONT && thislen + off < len)
{
newchunk = true;
off += thislen;
if (off + thislen > len)
thislen = len - off;
}
else if (ret == SM_XHDR_CONT && fp != NULL)
{
newchunk = true;
ret = sm_refill(fp);
if (sm_is_err(ret))
return ret;
chunk = f_p(*fp);
len = thislen = f_r(*fp);
if (chunksize > 0 && thislen > chunksize)
thislen = chunksize;
}
} while (!sm_is_err(ret) && ret != SM_XHDR_EOHDR
&& ret != SM_XHDR_GOTL);
if (Verbose > 0 && sm_is_err(ret))
sm_io_fprintf(smioout, "ret=%r, error=%m\n", ret, ret);
sm_io_flush(smioout);
ret = sm_xhdr_end(sm_xhdr_ctx);
SM_TEST(sm_is_success(ret));
return 0;
}
static void
usage(const char *prg)
{
sm_io_fprintf(smioerr,
"%s: usage: %s [options] [mail]\n"
"options:\n"
"-s n set chunksize to n\n"
"-V increase verbosity\n"
, prg, prg
);
exit(EX_USAGE);
}
int
main(int argc, char **argv)
{
int c;
size_t chunksize;
char *prg;
sm_file_T *fp;
chunksize = 0;
prg = argv[0];
while ((c = getopt(argc, argv, "s:V")) != -1)
{
switch (c)
{
case 's':
chunksize = strtoul(optarg, NULL, 0);
break;
case 'V':
++Verbose;
break;
default:
usage(prg);
break;
}
}
sm_test_begin(argc, argv, "test extracthdr");
argc -= optind;
argv += optind;
if (argc > 0)
{
for (c = 0; c < argc; c++)
{
sm_ret_T ret;
ret = sm_io_open(SmStStdio, argv[c], SM_IO_RDONLY, &fp,
SM_IO_WHAT_END);
SM_TEST(ret == SM_SUCCESS);
SM_TEST(fp != NULL);
if (fp != NULL)
(void) testextracthdr(fp, chunksize);
ret = sm_io_close(fp, SM_IO_CF_NONE);
}
}
else
(void) testextracthdr((sm_file_T *)0, chunksize);
return sm_test_end();
}
syntax highlighted by Code2HTML, v. 0.9.1