]> git.donarmstrong.com Git - lilypond.git/blobdiff - lily/lexer.l
release: 0.0.47
[lilypond.git] / lily / lexer.l
index 6f5945a60544bfaac62a223bbbc1ce7551f78f40..9ecc6f9e4d4d09bb852ad413a2b85ed01f699a7f 100644 (file)
@@ -4,29 +4,37 @@
 
 #include "string.hh"
 #include "string-convert.hh"
-#include "notename.hh"
-#include "lexer.hh"
+#include "my-lily-lexer.hh"
 #include "varray.hh"
 #include "parser.hh"
 #include "debug.hh"
 #include "input-score.hh"
 #include "parseconstruct.hh"
 #include "main.hh"
+#include "identifier.hh"
 
+#define start_quote()  \
+       yy_push_state(quote);\
+       yylval.string = new String
+
+#define yylval (*(YYSTYPE*)lexval_l)
+
+#define YY_USER_ACTION add_lexed_char(YYLeng());
 %}
 
 %option c++
 %option noyywrap
 %option nodefault
-%option yylineno
 %option debug
-%option yyclass="My_flex_lexer"
+%option yyclass="My_lily_lexer"
 %option stack
+%option never-interactive 
+%option warn
 
-%x notes
 %x incl
-%x quote
 %x lyrics
+%x notes
+%x quote
 
 
 
@@ -34,8 +42,8 @@ A             [a-zA-Z]
 AA             {A}|_
 N              [0-9]
 AN             {AA}|{N}
-PUNCT          [?!,.:;]
-ACCENT         [\\'"^]
+PUNCT          [?!,.:;']
+ACCENT         \\[`'"^]
 NATIONAL       [\241-\377]
 TEX            {AA}|-|{PUNCT}|{ACCENT}|{NATIONAL}
 
@@ -43,25 +51,32 @@ WORD                {A}{AN}*
 ALPHAWORD      {A}+
 INT            -?{N}+
 REAL           {INT}?(\.{N}*)?
-
-OPTSIGN                !?
-PITCHMOD       ['`]*{OPTSIGN}
-RESTNAME       r|s|p
+KEYWORD                \\{WORD}
+WHITE          [ \n\t\f]
+BLACK          [^ \n\t\f]
+RESTNAME       r
 NOTECOMMAND    \\{WORD}
-NOTENAME       [a-z]+
-UNOTENAME      [A-Z][a-z]*
 DOTS           \.+
-LYRICS         {TEX}+
-COMMENT                [%#].*\n
+LYRICS         {AA}[^0-9 \t\n\f]*
+COMMENT                %.*\n
 
 %%
 
-\$             {
-       yy_push_state(notes); 
+<lyrics,INITIAL,notes>{COMMENT}        {
 }
 
-\@             {
-       yy_push_state(lyrics); 
+
+
+include           {
+       yy_push_state(incl);
+}
+<incl>{WHITE}*      { /* eat the whitespace */ }
+<incl>\"[^"]*\"   { /* got the include file name */
+       String s (YYText()+1);
+       s = s.left_str(s.length_i()-1);
+       mtor << "#include `" << s << "\'\n";
+       new_input(s,source_l_g);
+       yy_pop_state();
 }
 
 <notes>{RESTNAME}      {
@@ -70,38 +85,37 @@ COMMENT             [%#].*\n
        mtor << "rest:"<< yylval.string;
        return RESTNAME;
 }
-<notes>{UNOTENAME}     {
-       int *p=yylval.ii;
-       return ret_notename(p, YYText(), -1);
+<INITIAL,lyrics,notes>\\\${BLACK}*{WHITE}      {
+       String s=YYText() + 2;
+       s=s.left_str(s.length_i() - 1);
+       return scan_escaped_word(s);
+}
+<INITIAL,lyrics,notes>\${BLACK}*{WHITE}                {
+       String s=YYText() + 1;
+       s=s.left_str(s.length_i() - 1);
+       return scan_bare_word(s);
+}
+<notes>{ALPHAWORD}/\'  {
+       post_quotes_b_ = true;
+       return scan_bare_word(YYText());
+}
+<notes>\'+             {
+       yylval.i = YYLeng();
+       if (post_quotes_b_) {
+               post_quotes_b_ = false;
+               return POST_QUOTES;
+       } else
+               return PRE_QUOTES;
 }
+<notes>{ALPHAWORD}     {
+       return scan_bare_word(YYText());
 
-<notes>{NOTENAME}      {
-       int *p=yylval.ii;
-       return ret_notename(p, YYText(), 0);
 }
 
 <notes>{NOTECOMMAND}   {
-       String c = YYText() +1;
-       mtor << "\\word: " << YYText()+1<<eol;
-       int l = lookup_keyword(c);
-       if (l != -1)
-               return l;
-       Identifier * id = lookup_identifier(c);
-       if (id) {               
-               yylval.id = id;
-               return IDENTIFIER;
-       }
-       String *sp = new String( c);
-       yylval.string=sp;
-       return STRING;
+       return scan_escaped_word(YYText()+1);
 }
 
-<notes>{PITCHMOD}      {
-       const char *s = YYText();
-       mtor << "pitchmod:"<< YYText()<<eol;
-       yylval.string = new String (s);
-       return PITCHMOD;
-}
 <notes>{DOTS}          {
        yylval.i = strlen(YYText());
        return DOTS;
@@ -110,36 +124,36 @@ COMMENT           [%#].*\n
        yylval.i = String_convert::dec2_i( String( YYText() ) );
        return INT;
 }
-<notes>{COMMENT}       {
-}
-<notes>[ \t\n]+                {
 
+<notes>\+\+            {
+       return CONCAT;
 }
-<notes>\$      {
-       yy_pop_state();
-}
-<notes>\"[^"]*\" {
-       String s (YYText()+1);
-       s = s.left_str(s.length_i()-1);
-       yylval.string = new String(s);
-       return STRING;
-}
-<notes>.       {
-       return yylval.c = YYText()[0];
+<notes>\" {
+       start_quote();
 }
 
+
 \"             {
-       yy_push_state(quote);
+       start_quote();
 }
-<quote>[^"]*   {
-       yylval.string = new String (YYText());
+<quote>\\\\    {
+       *yylval.string += '\\';
+}
+<quote>\\\"    {
+       *yylval.string +='\"';
+}
+<quote>[^"]+   {
+       *yylval.string += YYText();
 }
 <quote>\"      {
-       mtor << "quoted string\n";
+       mtor << "quoted string: `" << *yylval.string << "'\n";
        yy_pop_state();
        return STRING;
 }
 
+<lyrics>\" {
+       start_quote();
+}
 <lyrics>{DOTS}         {
        yylval.i = strlen(YYText());
        return DOTS;
@@ -149,35 +163,10 @@ COMMENT           [%#].*\n
        return INT;
 }
 <lyrics>{NOTECOMMAND}  {
-       String c = YYText() +1;
-       mtor << "\\word: " << YYText()+1<<eol;
-       int l = lookup_keyword(c);
-       if (l != -1)
-               return l;
-
-/* let's try passing tex's typesetting macros like \ss \alpha \c */
-       String* str_p = new String(YYText());//huh?
-       return STRING;  
-
-/* and skip identifiers...
-       Identifier * id = lookup_identifier(c);
-       if (id) {               
-               yylval.id = id;
-               return IDENTIFIER;
-       }
-       String *sp = new String( c);
-
-       yylval.string=sp;
-       return STRING;
-*/
-}
-<lyrics>\"[^"]*\" {
-       String s (YYText()+1);
-       s = s.left_str(s.length_i()-1);
-       yylval.string = new String(s);
-       return STRING;
+       return scan_escaped_word(YYText()+1);
 }
 <lyrics>{LYRICS} {
+       /* ugr. This sux. */
        String s (YYText()); 
        int i = 0;
        while ((i=s.index_i("_")) != -1) // change word binding "_" to " "
@@ -188,13 +177,11 @@ COMMENT           [%#].*\n
                s = s.left_str(i+2) + " " + s.right_str(s.length_i()-i-2);
                }
        yylval.string = new String(s);
+       mtor << "lyric : `" << s << "'\n";
        return STRING;
 }
 <lyrics>\|     {
        return YYText()[0];
-}
-<lyrics>{COMMENT}              { 
-
 }
 <lyrics>[{}]   {
        return YYText()[0];
@@ -202,50 +189,20 @@ COMMENT           [%#].*\n
 <lyrics>[()\[\]|/.^>_-] {
        return yylval.c = YYText()[0];
 }
-<lyrics>[ \t\n]+               {
-}
-<lyrics>@      {
-       yy_pop_state();
-}
 
 <<EOF>> {
-       mtor << "<<EOF>>";
+       mtor << "<<eof>>";
 
-       if (! close_input())
+       if (! close_input()) { 
          yyterminate(); // can't move this, since it actually rets a YY_NULL
+       }
 }
-
-
-include           {
-       yy_push_state(incl);
-}
-<incl>[ \t]*      { /* eat the whitespace */ }
-<incl>\"[^"]*\"+   { /* got the include file name */
-   String s (YYText()+1);
-   s = s.left_str(s.length_i()-1);
-   defined_ch_c_l = here_ch_c_l() - String( YYText() ).length_i() - 1;
-   new_input(s);
-   yy_pop_state();
+{WORD} {
+       return scan_bare_word(YYText());
 }
-
-
-{WORD}         {
-       mtor << "word: " << YYText()<<eol;
-       String c = YYText();
-       int l = lookup_keyword(c);
-       if (l != -1)
-               return l;
-       Identifier * id = lookup_identifier(c);
-       if (id) {               
-               yylval.id = id;
-               return IDENTIFIER;
-       }
-       String *sp = new String( c);
-       mtor << "new id: " << *sp << eol;
-       yylval.string=sp;
-       return STRING;
+{KEYWORD}      {
+       return scan_escaped_word(YYText()+1);
 }
-
 {REAL}         {
        Real r;
        int cnv=sscanf (YYText(), "%lf", &r);
@@ -265,17 +222,73 @@ include           {
        mtor << "misc char" <<c<<"\n";
        return c;
 }
-[ \t\n]+       {
+<*>{WHITE}+    {
        
 }
-
-{COMMENT}              {
-       //ignore
+<notes>.       {
+       return yylval.c = YYText()[0];
 }
-.              {
-       error( String( "illegal character: " ) + String( YYText()[0] ), here_ch_c_l() );
+
+<*>.           {
+       LexerError( String( "illegal character: " ) +String( YYText()[0] ));
        return YYText()[0];
 }
 
 %%
 
+void
+My_lily_lexer::push_note_state()
+{
+       yy_push_state(notes);
+}
+
+void
+My_lily_lexer::push_lyric_state()
+{
+       yy_push_state(lyrics);
+}
+void
+My_lily_lexer::pop_state()
+{
+       yy_pop_state();
+}
+
+int
+My_lily_lexer::scan_escaped_word(String str)
+{      
+       mtor << "\\word: `" << str<<"'\n";
+       int l = lookup_keyword(str);
+       if (l != -1) {
+               mtor << "(keyword)\n";
+               return l;
+       }
+       String *sp = new String( str);
+       yylval.string=sp;
+       return STRING;
+}
+int
+My_lily_lexer::scan_bare_word(String str)
+{
+       mtor << "word: `" << str<< "'\n";       
+       Identifier * id = lookup_identifier(str);
+       if (id) {
+               mtor << "(identifier)\n";
+               yylval.id = id;
+               return id->token_code_i_;
+       }
+
+       yylval.string=new String( str );
+       return STRING;
+}
+
+bool
+My_lily_lexer::note_state_b() const
+{
+       return YY_START == notes;
+}
+
+bool
+My_lily_lexer::lyric_state_b() const
+{
+       return YY_START == lyrics;
+}