summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/filter.c2
-rw-r--r--src/flexdef.h3
-rw-r--r--src/main.c4
-rw-r--r--src/misc.c7
-rw-r--r--src/options.c3
-rw-r--r--src/options.h3
-rw-r--r--src/scan.l41
-rw-r--r--src/yylex.c9
8 files changed, 49 insertions, 23 deletions
diff --git a/src/filter.c b/src/filter.c
index 1ac199f..9d0ace5 100644
--- a/src/filter.c
+++ b/src/filter.c
@@ -390,7 +390,7 @@ int filter_fix_linedirs (struct filter *chain)
/* Adjust the line directives. */
in_gen = true;
snprintf (buf, readsz, "#line %d \"%s\"\n",
- lineno + 1, filename);
+ lineno, filename);
}
else {
/* it's a #line directive for code we didn't write */
diff --git a/src/flexdef.h b/src/flexdef.h
index a727ede..a4d1896 100644
--- a/src/flexdef.h
+++ b/src/flexdef.h
@@ -1063,9 +1063,10 @@ extern struct Buf defs_buf; /* a char* buffer to save #define'd some symbols
extern struct Buf yydmap_buf; /* a string buffer to hold yydmap elements */
extern struct Buf m4defs_buf; /* Holds m4 definitions. */
extern struct Buf top_buf; /* contains %top code. String buffer. */
+extern bool no_section3_escape; /* True if the undocumented option --unsafe-no-m4-sect3-escape was passed */
/* For blocking out code from the header file. */
-#define OUT_BEGIN_CODE() outn("m4_ifdef( [[M4_YY_IN_HEADER]],,[[")
+#define OUT_BEGIN_CODE() outn("m4_ifdef( [[M4_YY_IN_HEADER]],,[[m4_dnl")
#define OUT_END_CODE() outn("]])")
/* For setjmp/longjmp (instead of calling exit(2)). Linkage in main.c */
diff --git a/src/main.c b/src/main.c
index 805c48b..e0ffbc3 100644
--- a/src/main.c
+++ b/src/main.c
@@ -1427,6 +1427,10 @@ void flexinit (int argc, char **argv)
break;
case OPT_HEX:
trace_hex = 1;
+ break;
+ case OPT_NO_SECT3_ESCAPE:
+ no_section3_escape = true;
+ break;
} /* switch */
} /* while scanopt() */
diff --git a/src/misc.c b/src/misc.c
index 753ada3..e4e3f88 100644
--- a/src/misc.c
+++ b/src/misc.c
@@ -362,8 +362,8 @@ void line_directive_out (FILE *output_file, int do_infile)
s3 = &filename[sizeof (filename) - 2];
while (s2 < s3 && *s1) {
- if (*s1 == '\\')
- /* Escape the '\' */
+ if (*s1 == '\\' || *s1 == '"')
+ /* Escape the '\' or '"' */
*s2++ = '\\';
*s2++ = *s1++;
@@ -512,7 +512,8 @@ unsigned char myesc (unsigned char array[])
{ /* \<octal> */
int sptr = 1;
- while (isascii (array[sptr]) &&
+ while (sptr <= 3 &&
+ isascii (array[sptr]) &&
isdigit (array[sptr]))
/* Don't increment inside loop control
* because if isdigit() is a macro it might
diff --git a/src/options.c b/src/options.c
index 3f3a39f..366bc2e 100644
--- a/src/options.c
+++ b/src/options.c
@@ -271,7 +271,8 @@ optspec_t flexopts[] = {
,
{"--noyyset_lloc", OPT_NO_YYSET_LLOC, 0}
,
-
+ {"--unsafe-no-m4-sect3-escape", OPT_NO_SECT3_ESCAPE, 0}
+ ,
{0, 0, 0} /* required final NULL entry. */
};
diff --git a/src/options.h b/src/options.h
index 8555343..5b51c23 100644
--- a/src/options.h
+++ b/src/options.h
@@ -125,7 +125,8 @@ enum flexopt_flag_t {
OPT_YYCLASS,
OPT_YYLINENO,
OPT_YYMORE,
- OPT_YYWRAP
+ OPT_YYWRAP,
+ OPT_NO_SECT3_ESCAPE,
};
#endif
diff --git a/src/scan.l b/src/scan.l
index afafa7d..9a2bd83 100644
--- a/src/scan.l
+++ b/src/scan.l
@@ -41,6 +41,9 @@ extern const char *escaped_qstart, *escaped_qend;
#define M4QSTART "[["
#define M4QEND "]]"
+#define SECT3_ESCAPED_QSTART "[" M4QEND M4QSTART "[" M4QEND M4QSTART
+#define SECT3_ESCAPED_QEND M4QEND "]" M4QSTART M4QEND "]" M4QSTART
+
#define ACTION_ECHO add_action( yytext )
#define ACTION_IFDEF(def, should_define) \
{ \
@@ -110,6 +113,8 @@ extern const char *escaped_qstart, *escaped_qend;
%x GROUP_MINUS_PARAMS
%x EXTENDED_COMMENT
%x COMMENT_DISCARD
+%x SECT3_NOESCAPE
+%x CHARACTER_CONSTANT
WS [[:blank:]]+
OPTWS [[:blank:]]*
@@ -240,8 +245,8 @@ M4QEND "]]"
}
. /* ignore spurious characters */
}
-<ACTION,CODEBLOCK,ACTION_STRING,PERCENT_BRACE_ACTION,COMMENT>{
- "M4"|"YY"|"m4" add_action(M4QSTART); ACTION_ECHO; add_action(M4QEND);
+<ACTION,CODEBLOCK,ACTION_STRING,PERCENT_BRACE_ACTION,COMMENT,CHARACTER_CONSTANT>{
+ M4|YY|m4 add_action(M4QSTART); ACTION_ECHO; add_action(M4QEND);
{M4QSTART} ACTION_ECHO_QSTART;
{M4QEND} ACTION_ECHO_QEND;
}
@@ -285,9 +290,9 @@ M4QEND "]]"
buf_strnappend(&top_buf, M4QEND, 2);
}
- [^{}\r\n] {
- buf_strnappend(&top_buf, yytext, yyleng);
- }
+ ([^{}\r\nmMY\[\]]+)|[^{}\r\n] {
+ buf_strnappend(&top_buf, yytext, yyleng);
+ }
<<EOF>> {
linenum = brace_start_line;
@@ -920,10 +925,11 @@ nmstr[yyleng - 2 - end_is_ws] = '\0'; /* chop trailing brace */
<ACTION>{
"{" ACTION_ECHO; ++bracelevel;
"}" ACTION_ECHO; --bracelevel;
- [^[:alpha:]_{}"'/\n\[\]]+ ACTION_ECHO;
+ [^[:alpha:]_{}\"'/\n\[\]]+ ACTION_ECHO;
[\[\]] ACTION_ECHO;
{NAME} ACTION_ECHO;
- "'"([^'\\\n]|\\.)*"'" ACTION_ECHO; /* character constant */
+ "'"([^\'\\\n]|\\.)"'" ACTION_ECHO; /* character constant */
+ "'" ACTION_ECHO; yy_push_state(CHARACTER_CONSTANT);
\" ACTION_ECHO; BEGIN(ACTION_STRING);
{NL} {
++linenum;
@@ -941,14 +947,20 @@ nmstr[yyleng - 2 - end_is_ws] = '\0'; /* chop trailing brace */
}
<ACTION_STRING>{
- [^]"\\\n[]+ ACTION_ECHO;
+ [^\]\"\\\n\[MmY]+ ACTION_ECHO;
+ \" ACTION_ECHO; BEGIN(ACTION);
+}
+<CHARACTER_CONSTANT>{
+ [^\[\]\'\\\nMmY]+ ACTION_ECHO;
+ \' ACTION_ECHO; yy_pop_state();
+}
+<ACTION_STRING,CHARACTER_CONSTANT>{
\\. ACTION_ECHO;
{NL} ++linenum; ACTION_ECHO;
- \" ACTION_ECHO; BEGIN(ACTION);
. ACTION_ECHO;
}
-<COMMENT,COMMENT_DISCARD,ACTION,ACTION_STRING><<EOF>> {
+<COMMENT,COMMENT_DISCARD,ACTION,ACTION_STRING,CHARACTER_CONSTANT><<EOF>> {
synerr( _( "EOF encountered inside an action" ) );
yyterminate();
}
@@ -969,10 +981,15 @@ nmstr[yyleng - 2 - end_is_ws] = '\0'; /* chop trailing brace */
<SECT3>{
- /* "M4"|"m4"|"YY" fprintf (yyout, "[[%s]]", yytext); */
+ "M4"|"m4"|"YY" {
+ if (no_section3_escape) {
+ ECHO;
+ } else
+ fprintf (yyout, "[[%s]]", yytext);
+ }
{M4QSTART} fwrite (escaped_qstart, 1, strlen(escaped_qstart) - 0, yyout);
{M4QEND} fwrite (escaped_qend, 1, strlen(escaped_qend) - 0, yyout);
- [^\[\]\n]*(\n?) ECHO;
+ [^\[\]MmY\n]*(\n?) ECHO;
(.|\n) ECHO;
<<EOF>> {
//fwrite(M4QEND, 1, strlen(M4QEND), yyout);
diff --git a/src/yylex.c b/src/yylex.c
index c3de1d5..521db7f 100644
--- a/src/yylex.c
+++ b/src/yylex.c
@@ -37,18 +37,19 @@
/* yylex - scan for a regular expression token */
-
extern char *yytext;
+extern FILE *yyout;
+bool no_section3_escape = false;
int yylex (void)
{
int toktype;
static int beglin = false;
- if (eofseen)
+ if (eofseen) {
toktype = EOF;
- else
+ } else {
toktype = flexscan ();
-
+ }
if (toktype == EOF || toktype == 0) {
eofseen = 1;