Ejemplo n.º 1
0
        public static Token Read(this Peekable <Token> tokens)
        {
            Token val;

            if (!tokens.Peek(out val))
            {
                throw new ParserException(tokens.Previous, "Unexpected end of file", true);
            }
            return(val);
        }
Ejemplo n.º 2
0
        public static string Consume(this Peekable <Token> tokens, TokenType type)
        {
            var token = tokens.Read();

            token.Assert(type);
            string s = token.Value;

            tokens.Consume();
            return(s);
        }
Ejemplo n.º 3
0
        internal static T ConsumeEnum <T>(this Peekable <Token> tokens) where T : struct
        {
            var token = tokens.Read();
            var value = tokens.ConsumeString();

            if (!EnumCache <T> .TryGet(token.Value, out T val))
            {
                token.Throw(ErrorCode.InvalidEnum, "Unable to parse " + typeof(T).Name);
            }
            return(val);
        }
Ejemplo n.º 4
0
        public static bool ConsumeIf(this Peekable <Token> tokens, TokenType type, string value)
        {
            Token token;

            if (tokens.Peek(out token) && token.Is(type, value))
            {
                tokens.Consume();
                return(true);
            }
            return(false);
        }
Ejemplo n.º 5
0
 public static bool SkipToEndStatementOrObject(this Peekable <Token> tokens)
 {
     while (tokens.Peek(out var token))
     {
         tokens.Consume();
         if (token.Is(TokenType.Symbol, "}") || token.Is(TokenType.Symbol, ";"))
         {
             return(true);
         }
     }
     return(false);
 }
Ejemplo n.º 6
0
 private static bool SkipToSymbol(this Peekable <Token> tokens, string symbol)
 {
     while (tokens.Peek(out var token))
     {
         tokens.Consume();
         if (token.Is(TokenType.Symbol, symbol))
         {
             return(true);
         }
     }
     return(false);
 }
Ejemplo n.º 7
0
        internal static int ConsumeInt32(this Peekable <Token> tokens, int?max = null)
        {
            var token = tokens.Read();

            token.Assert(TokenType.AlphaNumeric);
            tokens.Consume();

            if (TryParseInt32(token.Value, out int val, max))
            {
                return(val);
            }
            throw token.Throw(ErrorCode.InvalidInteger, "Unable to parse integer");
        }
Ejemplo n.º 8
0
        internal static T ConsumeEnum <T>(this Peekable <Token> tokens, bool ignoreCase = true) where T : struct
        {
            var token = tokens.Read();
            var value = tokens.ConsumeString();

            T val;

            if (!EnumCache <T> .TryGet(token.Value, out val))
            {
                token.Throw("Unable to parse " + typeof(T).Name);
            }
            return(val);
        }
Ejemplo n.º 9
0
 public static bool SkipToEndOptions(this Peekable <Token> tokens)
 {
     while (tokens.Peek(out var token))
     {
         if (token.Is(TokenType.Symbol, ";") || token.Is(TokenType.Symbol, "}"))
         {
             return(true); // but don't consume
         }
         tokens.Consume();
         if (token.Is(TokenType.Symbol, "]"))
         {
             return(true);
         }
     }
     return(false);
 }
Ejemplo n.º 10
0
        internal static bool ConsumeBoolean(this Peekable <Token> tokens)
        {
            var token = tokens.Read();

            token.Assert(TokenType.AlphaNumeric);
            tokens.Consume();
            if (string.Equals("true", token.Value, StringComparison.OrdinalIgnoreCase))
            {
                return(true);
            }
            if (string.Equals("false", token.Value, StringComparison.OrdinalIgnoreCase))
            {
                return(false);
            }
            throw token.Throw("Unable to parse boolean");
        }
Ejemplo n.º 11
0
        public static bool SkipToEndStatement(this Peekable <Token> tokens)
        {
            Token token;

            while (tokens.Peek(out token))
            {
                if (token.Is(TokenType.Symbol, "}"))
                {
                    return(true); // but don't consume
                }
                tokens.Consume();
                if (token.Is(TokenType.Symbol, ";"))
                {
                    return(true);
                }
            }
            return(false);
        }
Ejemplo n.º 12
0
 public static bool SkipToEndObject(this Peekable <Token> tokens) => SkipToSymbol(tokens, "}");
Ejemplo n.º 13
0
        internal static string ConsumeString(this Peekable <Token> tokens, bool asBytes = false)
        {
            var token = tokens.Read();

            switch (token.Type)
            {
            case TokenType.StringLiteral:
                MemoryStream ms = null;
                do
                {
                    ReadStringBytes(ref ms, token.Value);
                    tokens.Consume();
                } while (tokens.Peek(out token) && token.Type == TokenType.StringLiteral);     // literal concat is a thing
                if (ms == null)
                {
                    return("");
                }

                if (!asBytes)
                {
#if NETSTANDARD1_3
                    string s = ms.TryGetBuffer(out var segment)
                            ? Encoding.UTF8.GetString(segment.Array, segment.Offset, segment.Count)
                            : Encoding.UTF8.GetString(ms.ToArray());
#else
                    string s = Encoding.UTF8.GetString(ms.GetBuffer(), 0, (int)ms.Length);
#endif
                    return(s.Replace("\\", @"\\")
                           .Replace("\'", @"\'")
                           .Replace("\"", @"\""")
                           .Replace("\r", @"\r")
                           .Replace("\n", @"\n")
                           .Replace("\t", @"\t"));
                }

                var sb = new StringBuilder((int)ms.Length);
                int b;
                ms.Position = 0;
                while ((b = ms.ReadByte()) >= 0)
                {
                    switch (b)
                    {
                    case '\n': sb.Append(@"\n"); break;

                    case '\r': sb.Append(@"\r"); break;

                    case '\t': sb.Append(@"\t"); break;

                    case '\'': sb.Append(@"\'"); break;

                    case '\"': sb.Append(@"\"""); break;

                    case '\\': sb.Append(@"\\"); break;

                    default:
                        if (b >= 32 && b < 127)
                        {
                            sb.Append((char)b);
                        }
                        else
                        {
                            // encode as 3-part octal
                            sb.Append('\\')
                            .Append((char)(((b >> 6) & 7) + (int)'0'))
                            .Append((char)(((b >> 3) & 7) + (int)'0'))
                            .Append((char)(((b >> 0) & 7) + (int)'0'));
                        }
                        break;
                    }
                }
                return(sb.ToString());

            case TokenType.AlphaNumeric:
                tokens.Consume();
                return(token.Value);

            default:
                throw token.Throw(ErrorCode.InvalidString);
            }
        }
Ejemplo n.º 14
0
 public static bool Is(this Peekable <Token> tokens, TokenType type, string value = null)
 => tokens.Peek(out var val) && val.Is(type, value);
Ejemplo n.º 15
0
        public static bool Is(this Peekable <Token> tokens, TokenType type, string value = null)
        {
            Token val;

            return(tokens.Peek(out val) && val.Is(type, value));
        }