#include <sys/cdefs.h>
#ifndef lint
#if 0
static char yysccsid[] = "@(#)yaccpar	1.9 (Berkeley) 02/21/93";
#else
__IDSTRING(yyrcsid, "$NetBSD: skeleton.c,v 1.14 1997/10/20 03:41:16 lukem Exp $");
#endif
#endif
#include <stdlib.h>
#define YYBYACC 1
#define YYMAJOR 1
#define YYMINOR 9
#define YYLEX yylex()
#define YYEMPTY -1
#define yyclearin (yychar=(YYEMPTY))
#define yyerrok (yyerrflag=0)
#define YYRECOVERING (yyerrflag!=0)
#define YYPREFIX "yy"
	/* getoption.c */

#pragma	alloca	/* For AIX */

#include	<assert.h>
#include	"emil.h"

#ifndef	NO_FNMATCH
#include	<fnmatch.h>
#ifndef	FNM_NOMATCH
#define	FNM_NOMATCH	1	/* This MAY work!  941223/TW */
#endif
#else
static	int	ematch(char * p, char * s)
{
	/* Returns 0 if match, 1 else. '*' is a wildcard */
	/* Suggest that you install fnmatch instead...   */
#ifdef DEBUG
  if (edebug)
    fprintf(stderr, "-   ematch (no fnmatch).\n");
#endif
  for (;*p;p++) 
    if (*p == '*') 
      {
	p++; 
	if (*p=='\0') 
	  return 0;
	while (*s != '\0') 
	  {
	    if (ematch(p, s) == 0) 
	      return 0; 
	    else 
	      s++;
	  }
	return	1;
      } 
    else 
      if (*p != *(s++)) 
	return 1;
  return *s;
}
#endif

static	int	line_count;
static	int	error_count;	/* used in lex */
static	int	should_load_config_file	= 1;
extern	FILE *	conf_fd;

void	* Yalloc(int siz)
{
	void	* Y;
	static	off_t	len	= 0,	/* Of allocated segment */
			offset	= 0;	/* Amount used thereof	*/
	static	char	* where;
        char ebuf[256];
	alloc_total += siz;
	assert(siz > 0); siz     = ((siz + 3) / 4) * 4;	/* Word align */
	
	if ((len - offset) < siz) {

		if (len==0)	len	= pz;
		else		len	+= pz;
		if (len < siz)	len	= siz;
		/*
		 sprintf(ebuf,"Yalloc: len=%d offset=%d l-d=%d siz=%d",
			len, offset, len-offset, siz);
		 logger(LOG_DEBUG,ebuf);
		*/
		where	= malloc(len);
		if (where == NULL) {
			sprintf(ebuf,"getoption cannot get memory (%d) %m",len);
			logger(LOG_ERR,ebuf);
			fprintf(stderr, "Emil: Yalloc cannot get memory\n");
			exit(EX_OSERR);
		}
		Y	= where;
		offset	= siz;
	}
	else {
		Y	= &where[offset];
		offset	+= siz;
	}
	bzero(Y,siz);
	return	Y;
}

#define	N_CONTEXT_TYPES	4	/* Mime, UUencode, Applefile */

struct	member_struct	{
	struct	member_struct	* mm;	/* Points to next      */
	char	*	name;	/* Of the config group	       */
	char	*	r;	/* Receiver selection criteria */
	char	*	s;	/* Sender   selection criteria */
	char	*	rmx;	/* Receiver MX        criteria */
};

struct	lookup_struct {
	struct	lookup_struct	* ll;
	char	* matchstring;
	char	* out;
};

struct mailer_struct {
  char    *name;
  char    *mailer[15];
  struct mailer_struct *next;
};
  

struct	lookup_struct	* table_start[N_CONTEXT_TYPES], 
			* table_end[N_CONTEXT_TYPES];

static	struct	config_struct	* g_start, /* Points to first group structure  */
				* g_end,   /* Points to the last group structure */	
				* gtmp;

static	struct	member_struct	* m_start, /* first member in chain */
				* m_end,   /* Last member in chain  */
				* mtmp;
static int                      ma_count;
static struct   mailer_struct   * ma_start,
                                * ma_end,
                                * matmp;

static	char	* group_name;

static	int	Ycmp(char * pattern, char * string)
{
	char	p[255], s[255]; char	* c, *d, *t; int i;
	int	cc;

	/* Copy / fold */

	for (c=pattern,d=p,i=(sizeof(p)-2); *c && i > 0; c++,d++,i--)
	  *d = tolower(*c);
	*d = 0;

	for (c=string, d=s,i=(sizeof(s)-2); *c && i > 0; c++,d++,i--) 
	  *d = tolower(*c);
	*d = 0;


	/* Compare */
	
#ifndef	NO_FNMATCH
	cc = fnmatch(p, s, 0) != FNM_NOMATCH; /* 941223/TW */
#else
	cc = ematch(p, s) == 0;
#endif
#ifdef DEBUG
	if (edebug)
	  {
	    if (cc)
	      fprintf(stderr, "+   Ycmp: %s matches %s.\n", string, pattern);
	    else
	      fprintf(stderr, "+   Ycmp: %s does not match %s.\n", string, pattern);
	  }
#endif
	return	cc;
}

extern 	char	* yytext;	/* defined by flex */

/* static	int	yywrap()
	{
		return	1;
	}
*/

#define	yywrap()	1

static	void	yyerror(char * msg)
{
	char	ebuf[2048];
	sprintf(ebuf,"Config file: %s at line %d around '%s'\n",msg,line_count+1, yytext);
	logger(LOG_ERR,ebuf);
	error_count++;
}
typedef union {
	char * string;
	int	val;
} YYSTYPE;
#define APPLETYPE 257
#define COLON 258
#define COMMA 259
#define EQUALS 260
#define CHARSET 261
#define TEXTENC 262
#define HENC 263
#define FORMAT 264
#define BIN 265
#define GROUP 266
#define MAILER 267
#define MEMBER 268
#define EOR 269
#define MATCH 270
#define HOSTNAME 271
#define STRING 272
#define QSTRING 273
#define YYERRCODE 256
short yylhs[] = {                                        -1,
    0,    0,    3,    1,    1,    5,    1,    7,    1,    1,
    2,    2,    8,    8,    8,    8,    8,    8,    6,    6,
    9,    4,    4,   10,
};
short yylen[] = {                                         2,
    0,    2,    0,    6,    4,    0,    6,    0,    6,    5,
    1,    3,    3,    3,    3,    3,    3,    3,    1,    3,
    1,    1,    3,    3,
};
short yydefred[] = {                                      1,
    0,    0,    0,    0,    0,    0,    2,    0,    0,    0,
    0,    0,    3,    8,    6,    0,    0,    0,    0,    0,
    0,    5,    0,    0,    0,    0,    0,    0,    0,    0,
   21,    0,    0,    0,    0,   22,   10,    0,    0,    0,
    0,    0,    0,    4,    0,    9,    0,    0,    0,    7,
   18,   13,   16,   17,   14,   15,   12,   20,   24,   23,
};
short yydgoto[] = {                                       1,
    7,   29,   18,   35,   20,   32,   19,   30,   33,   36,
};
short yysindex[] = {                                      0,
 -255, -270, -269, -268, -258, -241,    0, -240, -239, -238,
 -252, -250,    0,    0,    0, -249, -245, -256, -247, -246,
 -242,    0, -232, -231, -230, -229, -228, -227, -235, -224,
    0, -233, -222, -234, -259,    0,    0, -226, -225, -223,
 -221, -220, -219,    0, -256,    0, -247, -218, -246,    0,
    0,    0,    0,    0,    0,    0,    0,    0,    0,    0,
};
short yyrindex[] = {                                      0,
    0,    0,    0,    0,    0,    0,    0,    0,    0,    0,
    0,    0,    0,    0,    0,    0,    0,    0,    0,    0,
    0,    0,    0,    0,    0,    0,    0,    0,    0, -214,
    0,    0, -213,    0,    0,    0,    0,    0,    0,    0,
    0,    0,    0,    0,    0,    0,    0,    0,    0,    0,
    0,    0,    0,    0,    0,    0,    0,    0,    0,    0,
};
short yygindex[] = {                                      0,
    0,   -6,    0,    0,    0,   -7,    0,    0,    0,   -8,
};
#define YYTABLESIZE 56
short yytable[] = {                                      49,
   23,    8,    9,   10,   24,   25,   26,   27,   28,   50,
    2,    3,    4,   11,    5,    6,   12,   13,   14,   15,
   16,   17,   21,   22,   31,   34,   37,   38,   39,   40,
   41,   42,   43,   44,   45,   46,   47,   48,   57,   58,
   60,    0,    0,    0,    0,   51,   52,    0,   53,    0,
   54,   55,   56,   59,   11,   19,
};
short yycheck[] = {                                     259,
  257,  272,  272,  272,  261,  262,  263,  264,  265,  269,
  266,  267,  268,  272,  270,  271,  258,  258,  258,  258,
  273,  272,  272,  269,  272,  272,  269,  260,  260,  260,
  260,  260,  260,  269,  259,  269,  259,  272,   45,   47,
   49,   -1,   -1,   -1,   -1,  272,  272,   -1,  272,   -1,
  272,  272,  272,  272,  269,  269,
};
#define YYFINAL 1
#ifndef YYDEBUG
#define YYDEBUG 0
#endif
#define YYMAXTOKEN 273
#if YYDEBUG
char *yyname[] = {
"end-of-file",0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,"APPLETYPE","COLON","COMMA",
"EQUALS","CHARSET","TEXTENC","HENC","FORMAT","BIN","GROUP","MAILER","MEMBER",
"EOR","MATCH","HOSTNAME","STRING","QSTRING",
};
char *yyrule[] = {
"$accept : expressions",
"expressions :",
"expressions : expressions expression",
"$$1 :",
"expression : GROUP STRING COLON $$1 varvals EOR",
"expression : HOSTNAME COLON STRING EOR",
"$$2 :",
"expression : MEMBER STRING COLON $$2 users EOR",
"$$3 :",
"expression : MAILER STRING COLON $$3 mailers EOR",
"expression : MATCH STRING QSTRING STRING EOR",
"varvals : varval",
"varvals : varval COMMA varvals",
"varval : CHARSET EQUALS STRING",
"varval : FORMAT EQUALS STRING",
"varval : BIN EQUALS STRING",
"varval : TEXTENC EQUALS STRING",
"varval : HENC EQUALS STRING",
"varval : APPLETYPE EQUALS STRING",
"mailers : mailera",
"mailers : mailera COMMA mailers",
"mailera : STRING",
"users : user_definition",
"users : users COMMA user_definition",
"user_definition : STRING STRING STRING",
};
#endif
#ifdef YYSTACKSIZE
#undef YYMAXDEPTH
#define YYMAXDEPTH YYSTACKSIZE
#else
#ifdef YYMAXDEPTH
#define YYSTACKSIZE YYMAXDEPTH
#else
#define YYSTACKSIZE 10000
#define YYMAXDEPTH 10000
#endif
#endif
#define YYINITSTACKSIZE 200
int yydebug;
int yynerrs;
int yyerrflag;
int yychar;
short *yyssp;
YYSTYPE *yyvsp;
YYSTYPE yyval;
YYSTYPE yylval;
short *yyss;
short *yysslim;
YYSTYPE *yyvs;
int yystacksize;

#include	"lex.yy.c"

struct	config_struct *	getoption(char * r, char * s, char * rmx)
{
	struct	member_struct	* mm;
	struct	config_struct	* gg;

#ifdef	YYDEBUG
	extern	int	yydebug;
	yydebug	= 1;
#endif

	if (should_load_config_file) {
		should_load_config_file = 0;
		if ((yyin = conf_fd) == NULL)
		  if ((yyin = fopen(MAINCF,"r")) == NULL) {
			char	ebuf[512];
			strcpy(ebuf,"Cannot open '");
			strcat(ebuf,MAINCF);
			strcat(ebuf,"' ");
			logger(LOG_ALERT,ebuf);
			return NULL;
		}
		if (yyparse())	return	NULL;
		fclose(yyin);
	}

	/* Look for member */

	for (mm = m_start; mm; mm = mm->mm)		/* Lookup member */
		if (Ycmp(mm->r,r) && Ycmp(mm->s,s) && Ycmp(mm->rmx,rmx))
			for (gg = g_start; gg; gg = gg->gg) /* Lookup group */
				if (strcasecmp(gg->name,mm->name)==0) 
					return gg;
	return	NULL;	/* group or member not found */
}


struct	config_struct *	getmember(char * name)
{
	struct	config_struct	* gg;

#ifdef	YYDEBUG
	extern	int	yydebug;
	yydebug	= 1;
#endif

	if (should_load_config_file) {
		should_load_config_file = 0;
		if ((yyin = conf_fd) == NULL)
		  if ((yyin = fopen(MAINCF,"r")) == NULL) {
			char	ebuf[512];
			strcpy(ebuf,"Cannot open '");
			strcat(ebuf,MAINCF);
			strcat(ebuf,"' ");
			logger(LOG_ALERT,ebuf);
			return NULL;
		}
		if (yyparse())	return	NULL;
		fclose(yyin);
	}

	for (gg = g_start; gg; gg = gg->gg) /* Lookup group */
	  if (strcasecmp(gg->name,name)==0) 
	    return gg;
	return	NULL;	/* group or member not found */
}

static	void	confextr_error(int level, char * txt, char * context, char * match, char * output)
{
	char	buf[255];
	strcpy(buf,txt);
	strcat(buf," confextr(\"");
	if (context) strcat(buf,context); else strcat(buf,"<NULL>");
	strcat(buf,"\", \"");
	if (match) strcat(buf,match); else strcat(buf,"<NULL>");
	strcat(buf,"\", \"");
	if (output) strcat(buf,output); else strcat(buf,"<NULL>");
	strcat(buf,"\")");
	logger(level,buf);
}

char	* confextr(char * context, char * match, char * output)
{
	int	context_type;
	struct	lookup_struct	* l;

	if (should_load_config_file) {
		should_load_config_file = 0;
		if ((yyin = conf_fd)          == NULL &&
		    (yyin = fopen(MAINCF,"r"))==NULL) {
			perror("cannot open config file");
			return NULL;
		}
		if (yyparse())	return	NULL;
		fclose(yyin);
	}

	if 	(context == NULL || 
		(match == NULL && output == NULL) ||
		(match != NULL && output != NULL))	{
		confextr_error(LOG_ERR, "Confextr: Invalid parameter combination",
			context,match,output);
		return NULL;
	}

	if	(strcasecmp(context,"MIME")==0)		context_type	= 0;
	else if	(strcasecmp(context,"UUENCODE")==0)	context_type	= 1;
	else if	(strcasecmp(context,"APPLEFILE")==0)	context_type	= 2;
	else if	(strcasecmp(context,"MAILTOOL")==0)	context_type	= 3;
	else	{
		confextr_error(LOG_ERR, "Confextr: invalid context", context, match, output);
		return NULL;
	}

	if (match == NULL) {
		if (output == NULL)	return NULL;
		for (l = table_start[context_type]; l; l = l->ll)
			if (strcasecmp(l->out,output)==0) return	l->matchstring;
		confextr_error(LOG_DEBUG, "Confextr: Info: Match not found", context, match, output);
		return	NULL;
	}
	else if (output == NULL) {
		if (match == NULL)	return NULL;
		for (l = table_start[context_type]; l; l = l->ll)
			if (strcasecmp(l->matchstring,match)==0) return	l->out;
		confextr_error(LOG_DEBUG, "Confextr: Info: Output not found", context, match, output);
		return	NULL;
	}
	else	{
		confextr_error(LOG_ERR, "Confextr: both match & output set", context, match, output);
		return	NULL;
	}
}



char **	get_mailer(char * mailer)
{
	struct	mailer_struct	* mm;

#ifdef	YYDEBUG
	extern	int	yydebug;
	yydebug	= 1;
#endif

	if (should_load_config_file) {
		should_load_config_file = 0;
		if ((yyin = conf_fd)          == NULL &&
		    (yyin = fopen(MAINCF,"r"))==NULL) {
			char	ebuf[512];
			strcpy(ebuf,"Cannot open '");
			strcat(ebuf,MAINCF);
			strcat(ebuf,"' ");
			logger(LOG_ALERT,ebuf);
			return NULL;
		}
		if (yyparse())	return	NULL;
		fclose(yyin);
	}

	/* Look for member */

	for (mm = ma_start; mm != NULL; mm = mm->next)		/* Lookup mailer */
	  {
	    if (cmatch(mm->name, mailer))
	      {
		char *c;
		int i;
		for (i = 0; mm->mailer[i] != NULL; i++)
		  {
		    c = mm->mailer[i];
		    if (*c == '$')
		      {
			c++;
			switch (*c) {
			case 's':
			case 'S':
			  mm->mailer[i] = sender;
			  break;
			case 'r':
			case 'R':
			  mm->mailer[i] = recipient;
			  break;
			case 'x':
			case 'X':
			  mm->mailer[i] = rmx;
			  break;
			default:
			  break;
			}
		      }
		  }
		return(mm->mailer);
	      }
	  }
	return NULL;
}

/* allocate initial stack or double stack size, up to YYMAXDEPTH */
int yyparse __P((void));
static int yygrowstack __P((void));
static int yygrowstack()
{
    int newsize, i;
    short *newss;
    YYSTYPE *newvs;

    if ((newsize = yystacksize) == 0)
        newsize = YYINITSTACKSIZE;
    else if (newsize >= YYMAXDEPTH)
        return -1;
    else if ((newsize *= 2) > YYMAXDEPTH)
        newsize = YYMAXDEPTH;
    i = yyssp - yyss;
    if ((newss = (short *)realloc(yyss, newsize * sizeof *newss)) == NULL)
        return -1;
    yyss = newss;
    yyssp = newss + i;
    if ((newvs = (YYSTYPE *)realloc(yyvs, newsize * sizeof *newvs)) == NULL)
        return -1;
    yyvs = newvs;
    yyvsp = newvs + i;
    yystacksize = newsize;
    yysslim = yyss + newsize - 1;
    return 0;
}

#define YYABORT goto yyabort
#define YYREJECT goto yyabort
#define YYACCEPT goto yyaccept
#define YYERROR goto yyerrlab
int
yyparse()
{
    int yym, yyn, yystate;
#if YYDEBUG
    char *yys;

    if ((yys = getenv("YYDEBUG")) != NULL)
    {
        yyn = *yys;
        if (yyn >= '0' && yyn <= '9')
            yydebug = yyn - '0';
    }
#endif

    yynerrs = 0;
    yyerrflag = 0;
    yychar = (-1);

    if (yyss == NULL && yygrowstack()) goto yyoverflow;
    yyssp = yyss;
    yyvsp = yyvs;
    *yyssp = yystate = 0;

yyloop:
    if ((yyn = yydefred[yystate]) != 0) goto yyreduce;
    if (yychar < 0)
    {
        if ((yychar = yylex()) < 0) yychar = 0;
#if YYDEBUG
        if (yydebug)
        {
            yys = 0;
            if (yychar <= YYMAXTOKEN) yys = yyname[yychar];
            if (!yys) yys = "illegal-symbol";
            printf("%sdebug: state %d, reading %d (%s)\n",
                    YYPREFIX, yystate, yychar, yys);
        }
#endif
    }
    if ((yyn = yysindex[yystate]) && (yyn += yychar) >= 0 &&
            yyn <= YYTABLESIZE && yycheck[yyn] == yychar)
    {
#if YYDEBUG
        if (yydebug)
            printf("%sdebug: state %d, shifting to state %d\n",
                    YYPREFIX, yystate, yytable[yyn]);
#endif
        if (yyssp >= yysslim && yygrowstack())
        {
            goto yyoverflow;
        }
        *++yyssp = yystate = yytable[yyn];
        *++yyvsp = yylval;
        yychar = (-1);
        if (yyerrflag > 0)  --yyerrflag;
        goto yyloop;
    }
    if ((yyn = yyrindex[yystate]) && (yyn += yychar) >= 0 &&
            yyn <= YYTABLESIZE && yycheck[yyn] == yychar)
    {
        yyn = yytable[yyn];
        goto yyreduce;
    }
    if (yyerrflag) goto yyinrecovery;
    goto yynewerror;
yynewerror:
    yyerror("syntax error");
    goto yyerrlab;
yyerrlab:
    ++yynerrs;
yyinrecovery:
    if (yyerrflag < 3)
    {
        yyerrflag = 3;
        for (;;)
        {
            if ((yyn = yysindex[*yyssp]) && (yyn += YYERRCODE) >= 0 &&
                    yyn <= YYTABLESIZE && yycheck[yyn] == YYERRCODE)
            {
#if YYDEBUG
                if (yydebug)
                    printf("%sdebug: state %d, error recovery shifting\
 to state %d\n", YYPREFIX, *yyssp, yytable[yyn]);
#endif
                if (yyssp >= yysslim && yygrowstack())
                {
                    goto yyoverflow;
                }
                *++yyssp = yystate = yytable[yyn];
                *++yyvsp = yylval;
                goto yyloop;
            }
            else
            {
#if YYDEBUG
                if (yydebug)
                    printf("%sdebug: error recovery discarding state %d\n",
                            YYPREFIX, *yyssp);
#endif
                if (yyssp <= yyss) goto yyabort;
                --yyssp;
                --yyvsp;
            }
        }
    }
    else
    {
        if (yychar == 0) goto yyabort;
#if YYDEBUG
        if (yydebug)
        {
            yys = 0;
            if (yychar <= YYMAXTOKEN) yys = yyname[yychar];
            if (!yys) yys = "illegal-symbol";
            printf("%sdebug: state %d, error recovery discards token %d (%s)\n",
                    YYPREFIX, yystate, yychar, yys);
        }
#endif
        yychar = (-1);
        goto yyloop;
    }
yyreduce:
#if YYDEBUG
    if (yydebug)
        printf("%sdebug: state %d, reducing by rule %d (%s)\n",
                YYPREFIX, yystate, yyn, yyrule[yyn]);
#endif
    yym = yylen[yyn];
    yyval = yyvsp[1-yym];
    switch (yyn)
    {
case 3:
{
			/* this backward method is becase we want to look at first hit */
			gtmp	= g_end;
			g_end  	= Yalloc(sizeof(struct config_struct));
			if (g_start == NULL) 	g_start	= g_end;
			else			gtmp->gg= g_end;
			strcpy((g_end->name=Yalloc(strlen(yyvsp[-1].string)+1)),yyvsp[-1].string);
		  }
break;
case 5:
{
                        hostname = (char *)NEWSTR(yyvsp[-1].string);
                  }
break;
case 6:
{
			strcpy((group_name=Yalloc(strlen(yyvsp[-1].string)+1)),yyvsp[-1].string);
		  }
break;
case 8:
{
                        
                        matmp = ma_end;
                        ma_end = (struct mailer_struct *)Yalloc(sizeof(struct mailer_struct));                         
                        ma_end->name = NEWSTR(yyvsp[-1].string);
                        if (ma_start == NULL)  ma_start = ma_end;
                        else                   matmp->next = ma_end;
                        ma_count = 0;
                  }
break;
case 10:
{
			/* Add a entry to match table */
			int	ctyp;
			struct	lookup_struct	* ttmp, ** ts, ** te;
			if	(strcasecmp(yyvsp[-3].string,"MIME")==0)	ctyp	= 0;
			else if	(strcasecmp(yyvsp[-3].string,"UUENCODE")==0)	ctyp	= 1;
			else if	(strcasecmp(yyvsp[-3].string,"APPLEFILE")==0)	ctyp	= 2;
			else if	(strcasecmp(yyvsp[-3].string,"MAILTOOL")==0)	ctyp	= 3;
			else	{
				yyerror("Wrong context type for match");
				YYERROR;
			}
			ts = &table_start[ctyp]; te = &table_end[ctyp];
			ttmp		= *te;
			*te		= Yalloc(sizeof(struct lookup_struct));
			if (*ts == NULL)  *ts	= *te;
			else		ttmp->ll= *te;
			strcpy(((*te)->matchstring=Yalloc(strlen(yyvsp[-2].string)+1)),yyvsp[-2].string);
			strcpy(((*te)->out=Yalloc(strlen(yyvsp[-1].string)+1)),yyvsp[-1].string);
		}
break;
case 13:
{
			strcpy((g_end->charset	= Yalloc(strlen(yyvsp[0].string)+1)),yyvsp[0].string);
		  }
break;
case 14:
{
			strcpy((g_end->format	= Yalloc(strlen(yyvsp[0].string)+1)),yyvsp[0].string);
		  }
break;
case 15:
{
			strcpy((g_end->bin	= Yalloc(strlen(yyvsp[0].string)+1)),yyvsp[0].string);
		  }
break;
case 16:
{
			strcpy((g_end->text	= Yalloc(strlen(yyvsp[0].string)+1)),yyvsp[0].string);
		  }
break;
case 17:
{
			strcpy((g_end->header	= Yalloc(strlen(yyvsp[0].string)+1)),yyvsp[0].string);
		  }
break;
case 18:
{
			strcpy((g_end->appletype = Yalloc(strlen(yyvsp[0].string)+1)),yyvsp[0].string);
		  }
break;
case 21:
{
                         ma_end->mailer[ma_count] = NEWSTR(yyvsp[0].string);
                         ma_count++;
                }
break;
case 24:
{
			mtmp	= m_end;
			m_end	= Yalloc(sizeof(struct	member_struct));
			if (m_start == NULL)	m_start	= m_end;
			else			mtmp->mm= m_end;
			m_end->name		= group_name;
			strcpy((m_end->r	= Yalloc(strlen(yyvsp[-2].string)+1)),yyvsp[-2].string);
			strcpy((m_end->s	= Yalloc(strlen(yyvsp[-1].string)+1)),yyvsp[-1].string);
			strcpy((m_end->rmx	= Yalloc(strlen(yyvsp[0].string)+1)),yyvsp[0].string);
		  }
break;
    }
    yyssp -= yym;
    yystate = *yyssp;
    yyvsp -= yym;
    yym = yylhs[yyn];
    if (yystate == 0 && yym == 0)
    {
#if YYDEBUG
        if (yydebug)
            printf("%sdebug: after reduction, shifting from state 0 to\
 state %d\n", YYPREFIX, YYFINAL);
#endif
        yystate = YYFINAL;
        *++yyssp = YYFINAL;
        *++yyvsp = yyval;
        if (yychar < 0)
        {
            if ((yychar = yylex()) < 0) yychar = 0;
#if YYDEBUG
            if (yydebug)
            {
                yys = 0;
                if (yychar <= YYMAXTOKEN) yys = yyname[yychar];
                if (!yys) yys = "illegal-symbol";
                printf("%sdebug: state %d, reading %d (%s)\n",
                        YYPREFIX, YYFINAL, yychar, yys);
            }
#endif
        }
        if (yychar == 0) goto yyaccept;
        goto yyloop;
    }
    if ((yyn = yygindex[yym]) && (yyn += yystate) >= 0 &&
            yyn <= YYTABLESIZE && yycheck[yyn] == yystate)
        yystate = yytable[yyn];
    else
        yystate = yydgoto[yym];
#if YYDEBUG
    if (yydebug)
        printf("%sdebug: after reduction, shifting from state %d \
to state %d\n", YYPREFIX, *yyssp, yystate);
#endif
    if (yyssp >= yysslim && yygrowstack())
    {
        goto yyoverflow;
    }
    *++yyssp = yystate;
    *++yyvsp = yyval;
    goto yyloop;
yyoverflow:
    yyerror("yacc stack overflow");
yyabort:
    return (1);
yyaccept:
    return (0);
}


syntax highlighted by Code2HTML, v. 0.9.1