Use existing error reporting.
[mono.git] / mcs / mcs / cs-tokenizer.cs
index ce616923b6cfcc4f7ddf87d4b727a063b746cf07..5d1c92c54159e13f22995161cdc23ca7d69ac297 100644 (file)
@@ -14,7 +14,6 @@
 
 using System;
 using System.Text;
-using System.Collections;
 using System.Collections.Generic;
 using System.IO;
 using System.Globalization;
@@ -117,6 +116,17 @@ namespace Mono.CSharp
                                entry.column = column;
                                return entry;
                        }
+
+                       //
+                       // Used for token not required by expression evaluator
+                       //
+                       public static LocatedToken CreateOptional (int row, int col)
+                       {
+#if false
+                               return Create (row, col);
+#endif
+                               return null;
+                       }
                        
                        public static void Initialize ()
                        {
@@ -144,13 +154,14 @@ namespace Mono.CSharp
                int col = 0;
                int previous_col;
                int current_token;
+               int tab_size;
                bool handle_get_set = false;
                bool handle_remove_add = false;
                bool handle_where = false;
                bool handle_typeof = false;
                bool lambda_arguments_parsing;
                Location current_comment_location = Location.Null;
-               ArrayList escaped_identifiers;
+               List<Location> escaped_identifiers;
                int parsing_generic_less_than;
                
                //
@@ -243,6 +254,11 @@ namespace Mono.CSharp
                        get { return handle_typeof; }
                        set { handle_typeof = value; }
                }
+
+               public int TabSize {
+                       get { return tab_size; }
+                       set { tab_size = value; }
+               }
                
                public XmlCommentState doc_state {
                        get { return xml_doc_state; }
@@ -262,7 +278,7 @@ namespace Mono.CSharp
                void AddEscapedIdentifier (Location loc)
                {
                        if (escaped_identifiers == null)
-                               escaped_identifiers = new ArrayList ();
+                               escaped_identifiers = new List<Location> ();
 
                        escaped_identifiers.Add (loc);
                }
@@ -290,7 +306,7 @@ namespace Mono.CSharp
                // Values for the associated token returned
                //
                internal int putback_char;      // Used by repl only
-               Object val;
+               object val;
 
                //
                // Pre-processor
@@ -303,7 +319,7 @@ namespace Mono.CSharp
                //
                // pre-processor if stack state:
                //
-               Stack ifstack;
+               Stack<int> ifstack;
 
                static System.Text.StringBuilder string_builder;
 
@@ -341,7 +357,8 @@ namespace Mono.CSharp
                // on its own to deamiguate a token in behalf of the
                // parser.
                //
-               Stack position_stack = new Stack (2);
+               Stack<Position> position_stack = new Stack<Position> (2);
+
                class Position {
                        public int position;
                        public int line;
@@ -350,9 +367,10 @@ namespace Mono.CSharp
                        public bool hidden;
                        public int putback_char;
                        public int previous_col;
-                       public Stack ifstack;
+                       public Stack<int> ifstack;
                        public int parsing_generic_less_than;
                        public int current_token;
+                       public object val;
 
                        public Position (Tokenizer t)
                        {
@@ -363,10 +381,16 @@ namespace Mono.CSharp
                                hidden = t.hidden;
                                putback_char = t.putback_char;
                                previous_col = t.previous_col;
-                               if (t.ifstack != null && t.ifstack.Count != 0)
-                                       ifstack = (Stack)t.ifstack.Clone ();
+                               if (t.ifstack != null && t.ifstack.Count != 0) {
+                                       // There is no simple way to clone Stack<T> all
+                                       // methods reverse the order
+                                       var clone = t.ifstack.ToArray ();
+                                       Array.Reverse (clone);
+                                       ifstack = new Stack<int> (clone);
+                               }
                                parsing_generic_less_than = t.parsing_generic_less_than;
                                current_token = t.current_token;
+                               val = t.val;
                        }
                }
                
@@ -377,7 +401,7 @@ namespace Mono.CSharp
 
                public void PopPosition ()
                {
-                       Position p = (Position) position_stack.Pop ();
+                       Position p = position_stack.Pop ();
 
                        reader.Position = p.position;
                        ref_line = p.ref_line;
@@ -389,6 +413,7 @@ namespace Mono.CSharp
                        ifstack = p.ifstack;
                        parsing_generic_less_than = p.parsing_generic_less_than;
                        current_token = p.current_token;
+                       val = p.val;
                }
 
                // Do not reset the position, ignore it.
@@ -726,6 +751,11 @@ namespace Mono.CSharp
 
                        xml_comment_buffer = new StringBuilder ();
 
+                       if (Environment.OSVersion.Platform == PlatformID.Win32NT)
+                               tab_size = 4;
+                       else
+                               tab_size = 8;
+
                        //
                        // FIXME: This could be `Location.Push' but we have to
                        // find out why the MS compiler allows this
@@ -762,8 +792,7 @@ namespace Mono.CSharp
 
                //
                // Open parens micro parser. Detects both lambda and cast ambiguity.
-               //
-               
+               //      
                int TokenizeOpenParens ()
                {
                        int ptoken;
@@ -784,12 +813,8 @@ namespace Mono.CSharp
                                        //
                                        // Expression inside parens is lambda, (int i) => 
                                        //
-                                       if (current_token == Token.ARROW) {
-                                               if (RootContext.Version <= LanguageVersion.ISO_2)
-                                                       Report.FeatureIsNotAvailable (Location, "lambda expressions");
-
+                                       if (current_token == Token.ARROW)
                                                return Token.OPEN_PARENS_LAMBDA;
-                                       }
 
                                        //
                                        // Expression inside parens is single type, (int[])
@@ -1951,9 +1976,9 @@ namespace Mono.CSharp
 
                        if (arg.StartsWith (w_restore)) {
                                int[] codes = ParseNumbers (arg.Substring (w_restore.Length));
-                               Hashtable w_table = Report.warning_ignore_table;
+                               var w_table = Report.warning_ignore_table;
                                foreach (int code in codes) {
-                                       if (w_table != null && w_table.Contains (code))
+                                       if (w_table != null && w_table.ContainsKey (code))
                                                Report.Warning (1635, 1, Location, "Cannot restore warning `CS{0:0000}' because it was disabled globally", code);
                                        Report.RegisterWarningRegion (Location).WarningEnable (Location, code, Report);
                                }
@@ -2223,7 +2248,7 @@ namespace Mono.CSharp
                                        Error_UnexpectedDirective ("no #region for this #endregion");
                                        return true;
                                }
-                               int pop = (int) ifstack.Pop ();
+                               int pop = ifstack.Pop ();
                                        
                                if ((pop & REGION) == 0)
                                        Report.Error (1027, Location, "Expected `#endif' directive");
@@ -2232,13 +2257,13 @@ namespace Mono.CSharp
                                
                        case "if":
                                if (ifstack == null)
-                                       ifstack = new Stack (2);
+                                       ifstack = new Stack<int> (2);
 
                                int flags = region_directive ? REGION : 0;
                                if (ifstack.Count == 0){
                                        flags |= PARENT_TAKING;
                                } else {
-                                       int state = (int) ifstack.Peek ();
+                                       int state = ifstack.Peek ();
                                        if ((state & TAKING) != 0) {
                                                flags |= PARENT_TAKING;
                                        }
@@ -2256,7 +2281,7 @@ namespace Mono.CSharp
                                        Error_UnexpectedDirective ("no #if for this #endif");
                                        return true;
                                } else {
-                                       pop = (int) ifstack.Pop ();
+                                       pop = ifstack.Pop ();
                                        
                                        if ((pop & REGION) != 0)
                                                Report.Error (1038, Location, "#endregion directive expected");
@@ -2268,7 +2293,7 @@ namespace Mono.CSharp
                                        if (ifstack.Count == 0)
                                                return true;
 
-                                       int state = (int) ifstack.Peek ();
+                                       int state = ifstack.Peek ();
                                        return (state & TAKING) != 0;
                                }
 
@@ -2277,7 +2302,7 @@ namespace Mono.CSharp
                                        Error_UnexpectedDirective ("no #if for this #elif");
                                        return true;
                                } else {
-                                       int state = (int) ifstack.Pop ();
+                                       int state = ifstack.Pop ();
 
                                        if ((state & REGION) != 0) {
                                                Report.Error (1038, Location, "#endregion directive expected");
@@ -2308,7 +2333,7 @@ namespace Mono.CSharp
                                        Error_UnexpectedDirective ("no #if for this #else");
                                        return true;
                                } else {
-                                       int state = (int) ifstack.Peek ();
+                                       int state = ifstack.Peek ();
 
                                        if ((state & REGION) != 0) {
                                                Report.Error (1038, Location, "#endregion directive expected");
@@ -2557,7 +2582,7 @@ namespace Mono.CSharp
                        while ((c = get_char ()) != -1) {
                                switch (c) {
                                case '\t':
-                                       col = ((col + 8) / 8) * 8;
+                                       col = ((col + tab_size) / tab_size) * tab_size;
                                        continue;
 
                                case ' ':
@@ -2604,8 +2629,10 @@ namespace Mono.CSharp
                                        // To block doccomment inside attribute declaration.
                                        if (doc_state == XmlCommentState.Allowed)
                                                doc_state = XmlCommentState.NotAllowed;
+                                       val = LocatedToken.CreateOptional (ref_line, col);
                                        return Token.OPEN_BRACKET;
                                case ']':
+                                       val = LocatedToken.CreateOptional (ref_line, col);
                                        return Token.CLOSE_BRACKET;
                                case '(':
                                        val = LocatedToken.Create (ref_line, col);
@@ -2653,22 +2680,29 @@ namespace Mono.CSharp
 
                                        return Token.OPEN_PARENS;
                                case ')':
+                                       val = LocatedToken.CreateOptional (ref_line, col);
                                        return Token.CLOSE_PARENS;
                                case ',':
+                                       val = LocatedToken.CreateOptional (ref_line, col);
                                        return Token.COMMA;
                                case ';':
+                                       val = LocatedToken.CreateOptional (ref_line, col);
                                        return Token.SEMICOLON;
                                case '~':
+                                       val = LocatedToken.Create (ref_line, col);
                                        return Token.TILDE;
                                case '?':
+                                       val = LocatedToken.Create (ref_line, col);
                                        return TokenizePossibleNullableType ();
                                case '<':
+                                       val = LocatedToken.Create (ref_line, col);
                                        if (parsing_generic_less_than++ > 0)
                                                return Token.OP_GENERICS_LT;
 
                                        return TokenizeLessThan ();
 
                                case '>':
+                                       val = LocatedToken.Create (ref_line, col);
                                        d = peek_char ();
 
                                        if (d == '='){
@@ -2695,6 +2729,7 @@ namespace Mono.CSharp
                                        return Token.OP_GT;
 
                                case '+':
+                                       val = LocatedToken.Create (ref_line, col);
                                        d = peek_char ();
                                        if (d == '+') {
                                                d = Token.OP_INC;
@@ -2707,6 +2742,7 @@ namespace Mono.CSharp
                                        return d;
 
                                case '-':
+                                       val = LocatedToken.Create (ref_line, col);
                                        d = peek_char ();
                                        if (d == '-') {
                                                d = Token.OP_DEC;
@@ -2721,6 +2757,7 @@ namespace Mono.CSharp
                                        return d;
 
                                case '!':
+                                       val = LocatedToken.Create (ref_line, col);
                                        if (peek_char () == '='){
                                                get_char ();
                                                return Token.OP_NE;
@@ -2728,6 +2765,7 @@ namespace Mono.CSharp
                                        return Token.BANG;
 
                                case '=':
+                                       val = LocatedToken.Create (ref_line, col);
                                        d = peek_char ();
                                        if (d == '='){
                                                get_char ();
@@ -2741,6 +2779,7 @@ namespace Mono.CSharp
                                        return Token.ASSIGN;
 
                                case '&':
+                                       val = LocatedToken.Create (ref_line, col);
                                        d = peek_char ();
                                        if (d == '&'){
                                                get_char ();
@@ -2753,6 +2792,7 @@ namespace Mono.CSharp
                                        return Token.BITWISE_AND;
 
                                case '|':
+                                       val = LocatedToken.Create (ref_line, col);
                                        d = peek_char ();
                                        if (d == '|'){
                                                get_char ();
@@ -2765,16 +2805,17 @@ namespace Mono.CSharp
                                        return Token.BITWISE_OR;
 
                                case '*':
+                                       val = LocatedToken.Create (ref_line, col);
                                        if (peek_char () == '='){
                                                get_char ();
                                                return Token.OP_MULT_ASSIGN;
                                        }
-                                       val = LocatedToken.Create (ref_line, col);
                                        return Token.STAR;
 
                                case '/':
                                        d = peek_char ();
                                        if (d == '='){
+                                               val = LocatedToken.Create (ref_line, col);
                                                get_char ();
                                                return Token.OP_DIV_ASSIGN;
                                        }
@@ -2851,6 +2892,7 @@ namespace Mono.CSharp
                                        return Token.DIV;
 
                                case '%':
+                                       val = LocatedToken.Create (ref_line, col);
                                        if (peek_char () == '='){
                                                get_char ();
                                                return Token.OP_MOD_ASSIGN;
@@ -2858,6 +2900,7 @@ namespace Mono.CSharp
                                        return Token.PERCENT;
 
                                case '^':
+                                       val = LocatedToken.Create (ref_line, col);
                                        if (peek_char () == '='){
                                                get_char ();
                                                return Token.OP_XOR_ASSIGN;
@@ -2865,6 +2908,7 @@ namespace Mono.CSharp
                                        return Token.CARRET;
 
                                case ':':
+                                       val = LocatedToken.Create (ref_line, col);
                                        if (peek_char () == ':') {
                                                get_char ();
                                                return Token.DOUBLE_COLON;
@@ -3172,7 +3216,7 @@ namespace Mono.CSharp
                public void cleanup ()
                {
                        if (ifstack != null && ifstack.Count >= 1) {
-                               int state = (int) ifstack.Pop ();
+                               int state = ifstack.Pop ();
                                if ((state & REGION) != 0)
                                        Report.Error (1038, Location, "#endregion directive expected");
                                else