1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145
|
%{
/**
* \file lexer.l
* Lexer for the rcfile.
*
* \author Adapted from fetchmail's rcfile_l.l by José Fonseca
*/
#include <stdio.h>
#include <string.h>
#include "parser.h"
#include "xmalloc.h"
int lineno = 1;
void escapes(const char *tp, char *cp, size_t n);
%}
%s NAME
%%
\"[^\"]*\" {
char buf[BUFSIZ];
yytext[strlen(yytext)-1] = '\0';
escapes(yytext+1, buf, BUFSIZ);
yylval.sval = xstrdup(buf);
BEGIN(0);
return STRING;
}
\'[^\']*\' {
char buf[BUFSIZ];
yytext[strlen(yytext)-1] = '\0';
escapes(yytext+1, buf, BUFSIZ);
yylval.sval = xstrdup(buf);
BEGIN(0);
return STRING;
}
<NAME>[^=;, \t\r\n]+ {
char buf[BUFSIZ];
escapes(yytext, buf, BUFSIZ);
yylval.sval = xstrdup(buf);
BEGIN(0);
return STRING;
}
identity { BEGIN(NAME); return IDENTITY; }
host(name)? { BEGIN(NAME); return HOSTNAME; }
user(name)? { BEGIN(NAME); return USERNAME; }
pass(word)? { BEGIN(NAME); return PASSWORD; }
(start)?tls { return STARTTLS; }
(certificate_)?passphrase { return CERTIFICATE_PASSPHRASE; }
preconnect { return PRECONNECT; }
postconnect { return POSTCONNECT; }
qualifydomain { return QUALIFYDOMAIN; }
helo { return HELO; }
force { return FORCE; }
reverse_path { return REVERSE_PATH; }
sender { return SENDER; }
message_id { return MSGID; }
mda { return MDA; }
force_mda { return FORCE_MDA; }
= { return MAP; }
disabled { return DISABLED; }
enabled { return ENABLED; }
required { return REQUIRED; }
default { return DEFAULT; }
(#.*)?\\?\n { lineno++; } /* newline is ignored */
-?[0-9]+/[^a-zA-Z] { yylval.number = atoi(yytext); return NUMBER; }
[^=;:, \t\r\n]+ {
char buf[BUFSIZ];
escapes(yytext, buf, BUFSIZ);
yylval.sval = xstrdup(buf);
return STRING;
}
[ \t\r]+ ; /* whitespace */
%%
/* process standard C-style escape sequences in a string */
void escapes(
const char *cp, /* source string with escapes */
char *tp, /* target buffer for digested string */
size_t n
)
{
while (*cp && --n)
{
int cval = 0;
if (*cp == '\\' && strchr("0123456789xX", cp[1]))
{
char *dp;
const char *hex = "00112233445566778899aAbBcCdDeEfF";
int dcount = 0;
if (*++cp == 'x' || *cp == 'X')
for (++cp; (dp = strchr(hex, *cp)) && (dcount++ < 2); cp++)
cval = (cval * 16) + (dp - hex) / 2;
else if (*cp == '0')
while (strchr("01234567",*cp) != (char*)NULL && (dcount++ < 3))
cval = (cval * 8) + (*cp++ - '0');
else
while ((strchr("0123456789",*cp)!=(char*)NULL)&&(dcount++ < 3))
cval = (cval * 10) + (*cp++ - '0');
}
else if (*cp == '\\') /* C-style character escapes */
{
switch (*++cp)
{
case '\\': cval = '\\'; break;
case 'n': cval = '\n'; break;
case 't': cval = '\t'; break;
case 'b': cval = '\b'; break;
case 'r': cval = '\r'; break;
default: cval = *cp;
}
cp++;
}
else
cval = *cp++;
*tp++ = cval;
}
*tp = '\0';
}
|