home *** CD-ROM | disk | FTP | other *** search
/ Fresh Fish 5 / FreshFish_July-August1994.bin / bbs / gnu / flex-2.4.6-src.lha / src / amiga / flex-2.4.6 / scan.l < prev    next >
Text File  |  1994-01-04  |  13KB  |  573 lines

  1. /* scan.l - scanner for flex input */
  2.  
  3. %{
  4. /*-
  5.  * Copyright (c) 1990 The Regents of the University of California.
  6.  * All rights reserved.
  7.  *
  8.  * This code is derived from software contributed to Berkeley by
  9.  * Vern Paxson.
  10.  * 
  11.  * The United States Government has rights in this work pursuant
  12.  * to contract no. DE-AC03-76SF00098 between the United States
  13.  * Department of Energy and the University of California.
  14.  *
  15.  * Redistribution and use in source and binary forms are permitted provided
  16.  * that: (1) source distributions retain this entire copyright notice and
  17.  * comment, and (2) distributions including binaries display the following
  18.  * acknowledgement:  ``This product includes software developed by the
  19.  * University of California, Berkeley and its contributors'' in the
  20.  * documentation or other materials provided with the distribution and in
  21.  * all advertising materials mentioning features or use of this software.
  22.  * Neither the name of the University nor the names of its contributors may
  23.  * be used to endorse or promote products derived from this software without
  24.  * specific prior written permission.
  25.  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
  26.  * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
  27.  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
  28.  */
  29.  
  30. /* $Header: scan.l,v 1.2 94/01/04 14:33:09 vern Exp $ */
  31.  
  32. #include "flexdef.h"
  33. #include "parse.h"
  34.  
  35. #define ACTION_ECHO add_action( yytext )
  36. #define MARK_END_OF_PROLOG mark_prolog();
  37.  
  38. #define YY_DECL \
  39.     int flexscan()
  40.  
  41. #define RETURNCHAR \
  42.     yylval = (unsigned char) yytext[0]; \
  43.     return CHAR;
  44.  
  45. #define RETURNNAME \
  46.     strcpy( nmstr, yytext ); \
  47.     return NAME;
  48.  
  49. #define PUT_BACK_STRING(str, start) \
  50.     for ( i = strlen( str ) - 1; i >= start; --i ) \
  51.         unput((str)[i])
  52.  
  53. #define CHECK_REJECT(str) \
  54.     if ( all_upper( str ) ) \
  55.         reject = true;
  56.  
  57. #define CHECK_YYMORE(str) \
  58.     if ( all_lower( str ) ) \
  59.         yymore_used = true;
  60. %}
  61.  
  62. %x SECT2 SECT2PROLOG SECT3 CODEBLOCK PICKUPDEF SC CARETISBOL NUM QUOTE
  63. %x FIRSTCCL CCL ACTION RECOVER BRACEERROR C_COMMENT ACTION_COMMENT
  64. %x ACTION_STRING PERCENT_BRACE_ACTION USED_LIST CODEBLOCK_2
  65.  
  66. WS        [ \t]+
  67. OPTWS        [ \t]*
  68. NOT_WS        [^ \t\n]
  69.  
  70. NL        (\n|\r\n|\n\r)
  71.  
  72. NAME        ([a-z_][a-z_0-9-]*)
  73. NOT_NAME    [^a-z_*\n]+
  74.  
  75. SCNAME        {NAME}
  76.  
  77. ESCSEQ        (\\([^\n]|[0-9]{1,3}|x[0-9a-f]{1,2}))
  78.  
  79. FIRST_CCL_CHAR    ([^\\\n]|{ESCSEQ})
  80. CCL_CHAR    ([^\\\n\]]|{ESCSEQ})
  81.  
  82. %%
  83.     static int bracelevel, didadef, indented_code, checking_used;
  84.  
  85.     int doing_codeblock = false;
  86.     int i;
  87.     Char nmdef[MAXLINE], myesc();
  88.  
  89.  
  90. ^{WS}            indented_code = true; BEGIN(CODEBLOCK);
  91. ^"/*"            ACTION_ECHO; BEGIN(C_COMMENT);
  92. ^"%s"{NAME}?        return SCDECL;
  93. ^"%x"{NAME}?        return XSCDECL;
  94. ^"%{".*{NL}        {
  95.             ++linenum;
  96.             line_directive_out( (FILE *) 0 );
  97.             indented_code = false;
  98.             BEGIN(CODEBLOCK);
  99.             }
  100.  
  101. {WS}            return WHITESPACE;
  102.  
  103. ^"%%".*            {
  104.             sectnum = 2;
  105.             bracelevel = 0;
  106.             mark_defs1();
  107.             line_directive_out( (FILE *) 0 );
  108.             BEGIN(SECT2PROLOG);
  109.             return SECTEND;
  110.             }
  111.  
  112. ^"%pointer".*{NL}    {
  113.             if ( lex_compat )
  114.                 warn( "%pointer incompatible with -l option" );
  115.             else
  116.                 yytext_is_array = false;
  117.             ++linenum;
  118.             }
  119. ^"%array".*{NL}        {
  120.             if ( C_plus_plus )
  121.                 warn( "%array incompatible with -+ option" );
  122.             else
  123.                 yytext_is_array = true;
  124.             ++linenum;
  125.             }
  126.  
  127. ^"%used"        {
  128.             warn( "%used/%unused have been deprecated" );
  129.             checking_used = REALLY_USED; BEGIN(USED_LIST);
  130.             }
  131. ^"%unused"        {
  132.             warn( "%used/%unused have been deprecated" );
  133.             checking_used = REALLY_NOT_USED; BEGIN(USED_LIST);
  134.             }
  135.  
  136.  
  137. ^"%"[aceknopr]{OPTWS}[0-9]*{OPTWS}{NL}    ++linenum;    /* ignore */
  138.  
  139. ^"%"[^sxanpekotcru{}].*    synerr( "unrecognized '%' directive" );
  140.  
  141. ^{NAME}            {
  142.             strcpy( nmstr, yytext );
  143.             didadef = false;
  144.             BEGIN(PICKUPDEF);
  145.             }
  146.  
  147. {SCNAME}        RETURNNAME;
  148. ^{OPTWS}{NL}        ++linenum; /* allows blank lines in section 1 */
  149. {OPTWS}{NL}        ++linenum; return '\n';
  150.  
  151.  
  152. <C_COMMENT>"*/"        ACTION_ECHO; BEGIN(INITIAL);
  153. <C_COMMENT>"*/".*{NL}    ++linenum; ACTION_ECHO; BEGIN(INITIAL);
  154. <C_COMMENT>[^*\n]+    ACTION_ECHO;
  155. <C_COMMENT>"*"        ACTION_ECHO;
  156. <C_COMMENT>{NL}        ++linenum; ACTION_ECHO;
  157.  
  158.  
  159. <CODEBLOCK>^"%}".*{NL}    ++linenum; BEGIN(INITIAL);
  160. <CODEBLOCK>"reject"    ACTION_ECHO; CHECK_REJECT(yytext);
  161. <CODEBLOCK>"yymore"    ACTION_ECHO; CHECK_YYMORE(yytext);
  162. <CODEBLOCK>{NAME}|{NOT_NAME}|.    ACTION_ECHO;
  163. <CODEBLOCK>{NL}        {
  164.             ++linenum;
  165.             ACTION_ECHO;
  166.             if ( indented_code )
  167.                 BEGIN(INITIAL);
  168.             }
  169.  
  170.  
  171. <PICKUPDEF>{WS}        /* separates name and definition */
  172.  
  173. <PICKUPDEF>{NOT_WS}.*    {
  174.             strcpy( (char *) nmdef, yytext );
  175.  
  176.             /* Skip trailing whitespace. */
  177.             for ( i = strlen( (char *) nmdef ) - 1;
  178.                   i >= 0 && (nmdef[i] == ' ' || nmdef[i] == '\t');
  179.                   --i )
  180.                 ;
  181.  
  182.             nmdef[i + 1] = '\0';
  183.  
  184.             ndinstal( nmstr, nmdef );
  185.             didadef = true;
  186.             }
  187.  
  188. <PICKUPDEF>{NL}        {
  189.             if ( ! didadef )
  190.                 synerr( "incomplete name definition" );
  191.             BEGIN(INITIAL);
  192.             ++linenum;
  193.             }
  194.  
  195. <RECOVER>.*{NL}        ++linenum; BEGIN(INITIAL); RETURNNAME;
  196.  
  197.  
  198. <USED_LIST>{NL}        ++linenum; BEGIN(INITIAL);
  199. <USED_LIST>{WS}
  200. <USED_LIST>"reject"    {
  201.             if ( all_upper( yytext ) )
  202.                 reject_really_used = checking_used;
  203.             else
  204.                 synerr(
  205.                 "unrecognized %used/%unused construct" );
  206.             }
  207. <USED_LIST>"yymore"    {
  208.             if ( all_lower( yytext ) )
  209.                 yymore_really_used = checking_used;
  210.             else
  211.                 synerr(
  212.                 "unrecognized %used/%unused construct" );
  213.             }
  214. <USED_LIST>{NOT_WS}+    synerr( "unrecognized %used/%unused construct" );
  215.  
  216.  
  217. <SECT2PROLOG>^"%{".*    ++bracelevel; yyless( 2 );    /* eat only %{ */
  218. <SECT2PROLOG>^"%}".*    --bracelevel; yyless( 2 );    /* eat only %} */
  219.  
  220. <SECT2PROLOG>^{WS}.*    ACTION_ECHO;    /* indented code in prolog */
  221.  
  222. <SECT2PROLOG>^{NOT_WS}.*    {    /* non-indented code */
  223.             if ( bracelevel <= 0 )
  224.                 { /* not in %{ ... %} */
  225.                 yyless( 0 );    /* put it all back */
  226.                 mark_prolog();
  227.                 BEGIN(SECT2);
  228.                 }
  229.             else
  230.                 ACTION_ECHO;
  231.             }
  232.  
  233. <SECT2PROLOG>.*        ACTION_ECHO;
  234. <SECT2PROLOG>{NL}    ++linenum; ACTION_ECHO;
  235.  
  236. <SECT2PROLOG><<EOF>>    {
  237.             mark_prolog();
  238.             sectnum = 0;
  239.             yyterminate(); /* to stop the parser */
  240.             }
  241.  
  242. <SECT2>^{OPTWS}{NL}    ++linenum; /* allow blank lines in section 2 */
  243.  
  244. <SECT2>^({WS}|"%{")    {
  245.             indented_code = (yytext[0] != '%');
  246.             doing_codeblock = true;
  247.             bracelevel = 1;
  248.  
  249.             if ( indented_code )
  250.                 ACTION_ECHO;
  251.  
  252.             BEGIN(CODEBLOCK_2);
  253.             }
  254.  
  255. <SECT2>^"<"        BEGIN(SC); return '<';
  256. <SECT2>^"^"        return '^';
  257. <SECT2>\"        BEGIN(QUOTE); return '"';
  258. <SECT2>"{"/[0-9]        BEGIN(NUM); return '{';
  259. <SECT2>"{"[^0-9\n][^}\n]*    BEGIN(BRACEERROR);
  260. <SECT2>"$"/([ \t]|{NL})    return '$';
  261.  
  262. <SECT2>{WS}"%{"        {
  263.             bracelevel = 1;
  264.             BEGIN(PERCENT_BRACE_ACTION);
  265.             return '\n';
  266.             }
  267. <SECT2>{WS}"|".*{NL}    continued_action = true; ++linenum; return '\n';
  268.  
  269. <SECT2>{WS}        {
  270.             /* This rule is separate from the one below because
  271.              * otherwise we get variable trailing context, so
  272.              * we can't build the scanner using -{f,F}.
  273.              */
  274.             bracelevel = 0;
  275.             continued_action = false;
  276.             BEGIN(ACTION);
  277.             return '\n';
  278.             }
  279.  
  280. <SECT2>{OPTWS}{NL}    {
  281.             bracelevel = 0;
  282.             continued_action = false;
  283.             BEGIN(ACTION);
  284.             unput( '\n' );    /* so <ACTION> sees it */
  285.             return '\n';
  286.             }
  287.  
  288. <SECT2>"<<EOF>>"    return EOF_OP;
  289.  
  290. <SECT2>^"%%".*        {
  291.             sectnum = 3;
  292.             BEGIN(SECT3);
  293.             yyterminate(); /* to stop the parser */
  294.             }
  295.  
  296. <SECT2>"["{FIRST_CCL_CHAR}{CCL_CHAR}*    {
  297.             int cclval;
  298.  
  299.             strcpy( nmstr, yytext );
  300.  
  301.             /* Check to see if we've already encountered this
  302.              * ccl.
  303.              */
  304.             if ( (cclval = ccllookup( (Char *) nmstr )) )
  305.                 {
  306.                 if ( input() != ']' )
  307.                     synerr( "bad character class" );
  308.  
  309.                 yylval = cclval;
  310.                 ++cclreuse;
  311.                 return PREVCCL;
  312.                 }
  313.             else
  314.                 {
  315.                 /* We fudge a bit.  We know that this ccl will
  316.                  * soon be numbered as lastccl + 1 by cclinit.
  317.                  */
  318.                 cclinstal( (Char *) nmstr, lastccl + 1 );
  319.  
  320.                 /* Push back everything but the leading bracket
  321.                  * so the ccl can be rescanned.
  322.                  */
  323.                 yyless( 1 );
  324.  
  325.                 BEGIN(FIRSTCCL);
  326.                 return '[';
  327.                 }
  328.             }
  329.  
  330. <SECT2>"{"{NAME}"}"    {
  331.             register Char *nmdefptr;
  332.             Char *ndlookup();
  333.  
  334.             strcpy( nmstr, yytext + 1 );
  335.             nmstr[yyleng - 2] = '\0';  /* chop trailing brace */
  336.  
  337.             if ( ! (nmdefptr = ndlookup( nmstr )) )
  338.                 format_synerr( "undefined definition {%s}",
  339.                         nmstr );
  340.  
  341.             else
  342.                 { /* push back name surrounded by ()'s */
  343.                 int len = strlen( (char *) nmdefptr );
  344.  
  345.                 if ( lex_compat || nmdefpt