Beispiel #1
0
        public static string evalute(SpokeItem condition, int tabIndex)
        {
            StringBuilder sb = new StringBuilder();

            if (condition == null)
            {
                return(sb.ToString());
            }
            switch (condition.IType)
            {
            case ISpokeItem.Array:
                sb.Append("[");
                for (int index = 0; index < ((SpokeArray)condition).Parameters.Length; index++)
                {
                    var spokeItem = ((SpokeArray)condition).Parameters[index];
                    sb.Append(evalute(spokeItem, tabIndex));

                    if (index < ((SpokeArray)condition).Parameters.Length - 1)
                    {
                        sb.Append(",");
                    }
                }
                sb.Append("]");
                break;

            case ISpokeItem.Float:
                sb.Append(((SpokeFloat)condition).Value);

                break;

            case ISpokeItem.Int:
                sb.Append(((SpokeInt)condition).Value);
                break;

            case ISpokeItem.Variable:
                if (((SpokeVariable)condition).Parent != null)
                {
                    sb.Append(evalute(((SpokeVariable)condition).Parent, tabIndex));
                    if (myShowIndex)
                    {
                        sb.Append("." + ((SpokeVariable)condition).VariableIndex);
                    }
                    else
                    {
                        sb.Append("." + ((SpokeVariable)condition).VariableName);
                    }
                    return(sb.ToString());
                }
                if (myShowIndex)
                {
                    sb.Append(((SpokeVariable)condition).VariableIndex);
                }
                else
                {
                    sb.Append(((SpokeVariable)condition).VariableName);
                }
                break;

            case ISpokeItem.ArrayIndex:
                sb.Append(evalute(((SpokeArrayIndex)condition).Parent, tabIndex));

                sb.Append("[");

                sb.Append(evalute(((SpokeArrayIndex)condition).Index, tabIndex));

                sb.Append("]");
                break;

            case ISpokeItem.Current:
                sb.Append("this");

                break;

            case ISpokeItem.Null:
                sb.Append("null");
                break;

            case ISpokeItem.AnonMethod:

                if (((SpokeAnonMethod)condition).Parent != null)
                {
                    sb.Append("(");
                    sb.Append("(");
                    sb.Append(evalute(((SpokeAnonMethod)condition).Parent, tabIndex));

                    sb.Append(")=>");

                    if (((SpokeAnonMethod)condition).RunOnVar != null)
                    {
                        evalute(((SpokeAnonMethod)condition).RunOnVar, tabIndex);
                        //                            sb.Append(".");
                    }


                    if (((SpokeAnonMethod)condition).Parameters != null)
                    {
                        sb.Append("|(");

                        for (int index = 0; index < ((SpokeAnonMethod)condition).Parameters.Length; index++)
                        {
                            var p = ((SpokeAnonMethod)condition).Parameters[index];
                            if (p.ByRef)
                            {
                                sb.Append("ref ");
                            }
                            sb.Append(p.Name);
                            if (index < ((SpokeAnonMethod)condition).Parameters.Length - 1)
                            {
                                sb.Append(",");
                            }
                        }
                        sb.Append(")");
                    }



                    sb.Append(evaluateLines(((SpokeAnonMethod)condition).Lines, tabIndex + 1));

                    sb.AppendLine();
                    for (int i = 0; i < tabIndex; i++)
                    {
                        sb.Append("  \t");
                    }

                    sb.Append(")");
                }
                else
                {
                    sb.Append("(");


                    if (((SpokeAnonMethod)condition).Parameters != null)
                    {
                        sb.Append("|(");

                        for (int index = 0; index < ((SpokeAnonMethod)condition).Parameters.Length; index++)
                        {
                            var p = ((SpokeAnonMethod)condition).Parameters[index];
                            if (p.ByRef)
                            {
                                sb.Append("ref ");
                            }
                            sb.Append(p.Name);
                            if (index < ((SpokeAnonMethod)condition).Parameters.Length - 1)
                            {
                                sb.Append(",");
                            }
                        }
                        sb.Append(")=>");
                    }



                    sb.Append(evaluateLines(((SpokeAnonMethod)condition).Lines, tabIndex + 1));
                    sb.AppendLine();
                    for (int i = 0; i < tabIndex; i++)
                    {
                        sb.Append("  \t");
                    }

                    sb.Append(")");
                }


                break;

            case ISpokeItem.MethodCall:


                var gf = ((SpokeMethodCall)condition);


                if (gf.Parent is SpokeAnonMethod)
                {
                    sb.Append("(");

                    sb.Append("|(");
                    var ds = ((SpokeAnonMethod)gf.Parent);
                    for (int index = 0; index < ds.Parameters.Length; index++)
                    {
                        ParamEter p = ds.Parameters[index];

                        if (p.ByRef)
                        {
                            sb.Append("ref ");
                        }

                        sb.Append(p.Name + " = ");

                        sb.Append(evalute(gf.Parameters[index + 1], tabIndex));



                        if (index < ds.Parameters.Length - 1)
                        {
                            sb.Append(",");
                        }
                    }
                    sb.Append(")");



                    sb.Append(evaluateLines(((SpokeAnonMethod)gf.Parent).Lines, tabIndex + 1));

                    sb.AppendLine();
                    for (int i = 0; i < tabIndex; i++)
                    {
                        sb.Append("  \t");
                    }

                    sb.Append(")");
                }
                else
                {
                    var d = ((SpokeVariable)gf.Parent);
                    if (d.Parent == null)
                    {
                        sb.Append(d.VariableName + "(");
                        for (int index = 0; index < gf.Parameters.Length; index++)
                        {
                            var spokeItem = gf.Parameters[index];
                            sb.Append(evalute(spokeItem, tabIndex));

                            if (index < gf.Parameters.Length - 1)
                            {
                                sb.Append(",");
                            }
                        }
                        sb.Append(")");
                    }
                    else
                    {
                        sb.Append(evalute(d.Parent, tabIndex));

                        sb.Append("." + d.VariableName + "(");
                        for (int index = 0; index < gf.Parameters.Length; index++)
                        {
                            var spokeItem = gf.Parameters[index];
                            sb.Append(evalute(spokeItem, tabIndex));

                            if (index < gf.Parameters.Length - 1)
                            {
                                sb.Append(",");
                            }
                        }
                        sb.Append(")");
                    }
                }



                break;

            case ISpokeItem.String:
                sb.Append("\"" + ((SpokeString)condition).Value + "\"");
                break;

            case ISpokeItem.Bool:
                sb.Append(((SpokeBool)condition).Value);
                break;

            case ISpokeItem.Construct:

                var rf = (SpokeConstruct)condition;

                sb.Append("Create ");

                if (rf.ClassName != null)
                {
                    sb.Append(rf.ClassName);
                }
                sb.Append("(");
                for (int index = 0; index < rf.Parameters.Length; index++)
                {
                    var spokeItem = rf.Parameters[index];
                    sb.Append(evalute(spokeItem, tabIndex));

                    if (index < rf.Parameters.Length - 1)
                    {
                        sb.Append(",");
                    }
                }
                sb.Append(")");

                sb.Append("{");
                for (int index = 0; index < rf.SetVars.Length; index++)
                {
                    var spokeItem = rf.SetVars[index];
                    sb.Append(spokeItem.Name
                              + ":");
                    sb.Append(evalute(spokeItem.Item, tabIndex));

                    if (index < rf.SetVars.Length - 1)
                    {
                        sb.Append(",");
                    }
                }
                sb.Append("}");



                break;

            case ISpokeItem.Addition:

                sb.Append("(");

                sb.Append(evalute(((SpokeAddition)condition).LeftSide, tabIndex));

                sb.Append("+");
                sb.Append(evalute(((SpokeAddition)condition).RightSide, tabIndex));

                sb.Append(")");

                break;

            case ISpokeItem.Subtraction:
                sb.Append("(");

                sb.Append(evalute(((SpokeSubtraction)condition).LeftSide, tabIndex));

                sb.Append("-");

                sb.Append(evalute(((SpokeSubtraction)condition).RightSide, tabIndex));
                sb.Append(")");


                break;

            case ISpokeItem.Multiplication:

                sb.Append("(");
                sb.Append(evalute(((SpokeMultiplication)condition).LeftSide, tabIndex));

                sb.Append("*");
                sb.Append(evalute(((SpokeMultiplication)condition).RightSide, tabIndex));

                sb.Append(")");


                break;

            case ISpokeItem.Division: sb.Append("(");

                sb.Append(evalute(((SpokeDivision)condition).LeftSide, tabIndex));

                sb.Append("/");
                sb.Append(evalute(((SpokeDivision)condition).RightSide, tabIndex));

                sb.Append(")");

                break;

            case ISpokeItem.Greater:
                sb.Append(evalute(((SpokeGreaterThan)condition).LeftSide, tabIndex));

                sb.Append(">");
                sb.Append(evalute(((SpokeGreaterThan)condition).RightSide, tabIndex));


                break;

            case ISpokeItem.Less:

                sb.Append(evalute(((SpokeLessThan)condition).LeftSide, tabIndex));

                sb.Append(">");
                sb.Append(evalute(((SpokeLessThan)condition).RightSide, tabIndex));



                break;

            case ISpokeItem.And:

                sb.Append(evalute(((SpokeAnd)condition).LeftSide, tabIndex));

                sb.Append("&&");

                sb.Append(evalute(((SpokeAnd)condition).RightSide, tabIndex));


                break;

            case ISpokeItem.Or:

                sb.Append(evalute(((SpokeOr)condition).LeftSide, tabIndex));

                sb.Append("||");
                sb.Append(evalute(((SpokeOr)condition).RightSide, tabIndex));

                break;

            case ISpokeItem.GreaterEqual:
                sb.Append(evalute(((SpokeGreaterThanOrEqual)condition).LeftSide, tabIndex));

                sb.Append(">=");
                sb.Append(evalute(((SpokeGreaterThanOrEqual)condition).RightSide, tabIndex));


                break;

            case ISpokeItem.LessEqual:
                sb.Append(evalute(((SpokeLessThanOrEqual)condition).LeftSide, tabIndex));

                sb.Append("<=");
                sb.Append(evalute(((SpokeLessThanOrEqual)condition).RightSide, tabIndex));


                break;

            case ISpokeItem.Equality:
                sb.Append(evalute(((SpokeEquality)condition).LeftSide, tabIndex));

                sb.Append("==");
                sb.Append(evalute(((SpokeEquality)condition).RightSide, tabIndex));


                break;

            case ISpokeItem.NotEqual:
                sb.Append(evalute(((SpokeNotEqual)condition).LeftSide, tabIndex));

                sb.Append("!=");
                sb.Append(evalute(((SpokeNotEqual)condition).RightSide, tabIndex));


                break;

            default:
                throw new ArgumentOutOfRangeException();
            }
            return(sb.ToString());
        }
Beispiel #2
0
        public Tuple <List <Class>, List <TokenMacroPiece> > Run(string fs)
        {
            var words = getWords(fs);



            var lines = words.Aggregate(new List <LineToken>()
            {
                new LineToken()
            }, (old, n) =>
            {
                old.Last().Tokens.Add(n);
                if (n.Type == Token.NewLine)
                {
                    if (old.Any() && (old.Last().Tokens.Count == 0))
                    {
                        return(old);
                    }


                    if (old.Any() && ((old.Last().Tokens.First().Type == Token.Tab || old.Last().Tokens.First().Type == Token.NewLine) && old.Last().Tokens.Count == 1))
                    {
                        old.Last().Tokens.Clear();
                        return(old);
                    }
                    old.Add(new LineToken());
                    return(old);
                }
                return(old);
            });



            foreach (var a in lines)
            {
                if (!(!a.Tokens.Any() || (a.Tokens[0].Type == Token.Class || a.Tokens[0].Type == Token.Macro || a.Tokens[0].Type == Token.Tab)))
                {
                }
            }



            for (int index = lines.Count - 1; index >= 0; index--)
            {
                var lineToken = lines[index];
                if (lineToken.Tokens.Count == 0)
                {
                    lines.RemoveAt(index);
                    continue;
                }
                if (lineToken.Tokens[0].Type == Token.Tab)
                {
                    if (lineToken.Tokens.Count == 1)
                    {
                        lines.RemoveAt(index);
                        continue;
                    }
                    if (lineToken.Tokens[1].Type == Token.NewLine)
                    {
                        lines.RemoveAt(index);
                        continue;
                    }
back:
                    if (lineToken.Tokens[1].Type == Token.Tab)
                    {
                        ((TokenTab)lineToken.Tokens[0]).TabIndex += ((TokenTab)lineToken.Tokens[1]).TabIndex;
                        lineToken.Tokens.RemoveAt(1);
                        goto back;
                    }
                }
            }


            int done  = 0;
            int indes = 0;
            List <List <LineToken> > macros;
            List <TokenMacroPiece>   allMacros = new List <TokenMacroPiece>();

            if (lines.Any() && lines[0].Tokens[0].Type == Token.Macro)
            {
                macros = lines.Aggregate(new List <List <LineToken> >()
                {
                },
                                         delegate(List <List <LineToken> > old, LineToken n)
                {
                    if (n.Tokens.Count == 0)
                    {
                        return(old);
                    }
                    indes = indes + 1;
                    if (done > 0 || n.Tokens[0].Type == Token.Class)
                    {
                        if (done == 0)
                        {
                            done = indes - 2;
                        }
                        return(old);
                    }

                    if (n.Tokens[0].Type == Token.Macro)
                    {
                        old.Add(new List <LineToken>());
                    }
                    old.Last().Add(n);
                    return(old);
                });

                for (int i = done; i >= 0; i--)
                {
                    lines.RemoveAt(i);
                }


                foreach (List <LineToken> macro in macros)
                {
                    TokenMacroPiece mp = new TokenMacroPiece();

                    allMacros.Add(mp);

                    mp.Lines = new List <LineToken>();

                    TokenEnumerator en = new TokenEnumerator(macro.ToArray());
                    StaticMethods.Assert(en.Current.Type == Token.Macro, "notMacro?");
                    en.MoveNext();
                    List <IToken> mps     = new List <IToken>();
                    int           curLine = 0;

                    if (en.Current.Type == Token.SemiColon)
                    {
                        StaticMethods.Assert(en.Current.Type == Token.SemiColon, "");
                        en.MoveNext();
                        while (en.Current.Type != Token.SemiColon)
                        {
                            mps.Add(en.Current);
                            en.MoveNext();
                        }
                        mp.Macro = mps.ToArray();

                        StaticMethods.Assert(en.Current.Type == Token.SemiColon, "");
                        en.MoveNext();

                        StaticMethods.Assert(en.Current.Type == Token.AnonMethodStart, "");
                        en.MoveNext();

                        StaticMethods.Assert(en.Current.Type == Token.Bar, "");
                        en.MoveNext();
                        StaticMethods.Assert(en.Current.Type == Token.OpenParen, "");
                        en.MoveNext();


                        List <ParamEter> parameters_ = new List <ParamEter>();
                        if (en.Current.Type != Token.CloseParen)
                        {
pback2:
                            bool byRef = false;

                            if (((TokenWord)en.Current).Word.ToLower() == "ref")
                            {
                                byRef = true;
                                en.MoveNext();
                            }
                            parameters_.Add(new ParamEter()
                            {
                                ByRef = byRef, Name = ((TokenWord)en.Current).Word
                            });
                            en.MoveNext();
                            switch (en.Current.Type)
                            {
                            case Token.CloseParen:
                                en.MoveNext();
                                break;

                            case Token.Comma:
                                en.MoveNext();
                                goto pback2;
                                break;

                            default:
                                throw new ArgumentOutOfRangeException();
                            }
                        }
                        mp.Parameters = parameters_.ToArray();

                        curLine = 1;
                    }
                    else if (en.Current.Type == Token.OpenCurly)
                    {
                        en.MoveNext();
                        while (!(en.Current.Type == Token.CloseCurly && en.PeakNext().Type != Token.CloseCurly))
                        {
                            if (en.Current.Type == Token.OpenCurly && en.PeakNext().Type == Token.OpenCurly)
                            {
                                en.MoveNext();
                            }
                            if (en.Current.Type == Token.CloseCurly && en.PeakNext().Type == Token.CloseCurly)
                            {
                                en.MoveNext();
                            }
                            mps.Add(en.Current);
                            en.MoveNext();
                        }
                        en.MoveNext();
                        mp.Macro = mps.ToArray().Trim((a) => a.Type == Token.NewLine, (a) => a.Type == Token.Tab);



                        StaticMethods.Assert(en.Current.Type == Token.Colon, "");
                        en.MoveNext();
                        StaticMethods.Assert(en.Current.Type == Token.OpenParen, "");
                        en.MoveNext();


                        List <ParamEter> parameters_ = new List <ParamEter>();
                        if (en.Current.Type != Token.CloseParen)
                        {
pback2:

                            ParamEter pm;
                            parameters_.Add(pm = new ParamEter()
                            {
                                ByRef = true, Name = ((TokenWord)en.Current).Word
                            });
                            if (!pm.Name.StartsWith("$"))
                            {
                                throw new Exception("Bad macro param");
                            }
                            en.MoveNext();

                            if (en.Current.Type != Token.Equal)
                            {
                                throw new Exception("Bad macro param equals");
                            }
                            en.MoveNext();

                            pm.Type = consumeMacroParamValue(en);


                            switch (en.Current.Type)
                            {
                            case Token.CloseParen:
                                en.MoveNext();
                                break;

                            case Token.Comma:
                                en.MoveNext();
                                goto pback2;
                                break;

                            default:
                                throw new ArgumentOutOfRangeException();
                            }
                        }
                        mp.Parameters = parameters_.ToArray();
                        curLine       = en.LineIndex + 1;
                    }
                    else
                    {
                        throw new Exception("Cannot find macro");
                    }



                    for (int i = curLine; i < macro.Count; i++)
                    {
                        mp.Lines.Add(macro[i]);
                    }

                    if (mp.Lines[0].Tokens.Count > 1 && mp.Lines[0].Tokens[0].Type == Token.Tab && mp.Lines[0].Tokens[1].Type == Token.OpenCurly)
                    {
                        mp.Lines.RemoveAt(0);
                    }
                    if (mp.Lines[mp.Lines.Count - 1].Tokens.Count > 1 && mp.Lines[mp.Lines.Count - 1].Tokens[0].Type == Token.Tab && mp.Lines[mp.Lines.Count - 1].Tokens[1].Type == Token.CloseCurly)
                    {
                        mp.Lines.RemoveAt(mp.Lines.Count - 1);
                    }
                }
            }

            var classes = lines.Aggregate(new List <List <LineToken> >()
            {
            }, (old, n) =>
            {
                if (n.Tokens.Count == 0)
                {
                    return(old);
                }
                if (n.Tokens[0].Type == Token.Class)
                {
                    old.Add(new List <LineToken>());
                }
                old.Last().Add(n);
                return(old);
            });


            List <Class> someClasses = new List <Class>();

            foreach (List <LineToken> @class in classes)
            {
                Class c = new Class();
                someClasses.Add(c);
                c.Name = ((TokenWord)@class[0].Tokens[1]).Word;
                for (int index = 1; index < @class.Count; index++)
                {
                    LineToken v = @class[index];
                    if (v.Tokens[0].Type != Token.Tab)
                    {
                        throw new AbandonedMutexException();
                    }

                    if (v.Tokens[1].Type != Token.Def)
                    {
                        c.Variables.Add(v);
                    }
                    else
                    {
                        var m = new Method();
                        if (v.Tokens[2] is TokenOpenParen)
                        {
                            m.Name = ".ctor";
                        }
                        else
                        {
                            m.Name = ((TokenWord)v.Tokens[2]).Word;
                        }

                        if (v.Tokens.Count != 5 + (v.Tokens[2] is TokenOpenParen ? 0 : 1))//tab def name openP closeP newline
                        {
                            for (int i = 3 + (v.Tokens[2] is TokenOpenParen ? 0 : 1); i < v.Tokens.Count - 2; i++)
                            {
                                m.paramNames.Add(((TokenWord)v.Tokens[i]).Word);
                                i++;
                            }
                        }
                        int tabl = ((TokenTab)v.Tokens[0]).TabIndex + 1;
                        index++;
                        for (; index < @class.Count; index++)
                        {
                            if (((TokenTab)@class[index].Tokens[0]).TabIndex < tabl)
                            {
                                index--;
                                break;
                            }
                            m.Lines.Add(@class[index]);
                        }
                        //index++;
                        c.Methods.Add(m);
                    }
                }
            }

            StringBuilder sb = new StringBuilder();

            foreach (var tokenMacroPiece in allMacros)
            {
                sb.Append(tokenMacroPiece.ToString());
            }

            sb.AppendLine();

            foreach (var someClass in someClasses)
            {
                Method ctor = someClass.Methods.FirstOrDefault(a => a.Name == ".ctor");
                if (ctor == null)
                {
                    someClass.Methods.Add(ctor = new Method());
                    ctor.Name = ".ctor";
                }
                for (int index = 0; index < someClass.Variables.Count; index++)
                {
                    var lineToken = someClass.Variables[index];
                    ((TokenTab)lineToken.Tokens[0]).TabIndex++;
                    someClass.VariableNames.Add(((TokenWord)lineToken.Tokens[1]).Word);
                    ctor.Lines.Insert(index, lineToken);
                }
                someClass.Variables.Clear();

                sb.AppendLine(someClass.ToString());
            }

            File.WriteAllText("C:\\spoke.txt", sb.ToString());
            //Console.WriteLine(sb);
            return(new Tuple <List <Class>, List <TokenMacroPiece> >(someClasses, allMacros));
        }