Пример #1
0
 private static int firstChoice(Choice ch)
 {
     if (Options.getForceLaCheck()) {
         return 0;
     }
     for (int i = 0; i < ch.Choices.Count; i++) {
         if (!explicitLA((Expansion) ch.Choices[i])) {
             return i;
         }
     }
     return ch.Choices.Count;
 }
Пример #2
0
        public static IList <MatchInfo> genFirstSet(IList <MatchInfo> partialMatches, Expansion exp)
        {
            if (exp is RegularExpression)
            {
                IList <MatchInfo> retval = new List <MatchInfo>();
                for (int i = 0; i < partialMatches.Count; i++)
                {
                    MatchInfo m    = (MatchInfo)partialMatches[i];
                    MatchInfo mnew = new MatchInfo();
                    for (int j = 0; j < m.firstFreeLoc; j++)
                    {
                        mnew.match[j] = m.match[j];
                    }
                    mnew.firstFreeLoc = m.firstFreeLoc;
                    mnew.match[mnew.firstFreeLoc++] = ((RegularExpression)exp).Ordinal;
                    if (mnew.firstFreeLoc == MatchInfo.laLimit)
                    {
                        sizeLimitedMatches.Add(mnew);
                    }
                    else
                    {
                        retval.Add(mnew);
                    }
                }
                return(retval);
            }
            else if (exp is NonTerminal)
            {
                NormalProduction prod = ((NonTerminal)exp).Production;
                if (prod is CodeProduction)
                {
                    return(new List <MatchInfo>());
                }
                else
                {
                    return(genFirstSet(partialMatches, prod.Expansion));
                }
            }
            else if (exp is Choice)
            {
                IList <MatchInfo> retval = new List <MatchInfo>();
                Choice            ch     = (Choice)exp;
                foreach (Expansion e in ch.Choices)
                {
                    IList <MatchInfo> v = genFirstSet(partialMatches, e);
                    listAppend(retval, v);
                }
                return(retval);
            }
            else if (exp is Sequence)
            {
                IList <MatchInfo> v   = partialMatches;
                Sequence          seq = (Sequence)exp;
                foreach (Expansion unit in seq.Units)
                {
                    v = genFirstSet(v, unit);
                    if (v.Count == 0)
                    {
                        break;
                    }
                }
                return(v);
            }
            else if (exp is OneOrMore)
            {
                IList <MatchInfo> retval = new List <MatchInfo>();
                IList <MatchInfo> v      = partialMatches;
                OneOrMore         om     = (OneOrMore)exp;
                while (true)
                {
                    v = genFirstSet(v, om.Expansion);
                    if (v.Count == 0)
                    {
                        break;
                    }

                    listAppend(retval, v);
                }
                return(retval);
            }
            else if (exp is ZeroOrMore)
            {
                IList <MatchInfo> retval = new List <MatchInfo>();
                listAppend(retval, partialMatches);
                IList <MatchInfo> v  = partialMatches;
                ZeroOrMore        zm = (ZeroOrMore)exp;
                while (true)
                {
                    v = genFirstSet(v, zm.Expansion);
                    if (v.Count == 0)
                    {
                        break;
                    }

                    listAppend(retval, v);
                }
                return(retval);
            }
            else if (exp is ZeroOrOne)
            {
                IList <MatchInfo> retval = new List <MatchInfo>();
                listAppend(retval, partialMatches);
                listAppend(retval, genFirstSet(partialMatches, ((ZeroOrOne)exp).Expansion));
                return(retval);
            }
            else if (exp is TryBlock)
            {
                return(genFirstSet(partialMatches, ((TryBlock)exp).Expansion));
            }
            else if (considerSemanticLA &&
                     exp is Lookahead &&
                     ((Lookahead)exp).ActionTokens.Count != 0
                     )
            {
                return(new List <MatchInfo>());
            }
            else
            {
                IList <MatchInfo> retval = new List <MatchInfo>();
                listAppend(retval, partialMatches);
                return(retval);
            }
        }
Пример #3
0
 public static void choiceCalc(Choice choice)
 {
     int first = firstChoice(choice);
     // dbl[i] and dbr[i] are lists of size limited matches for choice i
     // of choice.  dbl ignores matches with semantic lookaheads (when force_la_check
     // is false), while dbr ignores semantic lookahead.
     IList<MatchInfo>[] dbl = new IList<MatchInfo>[choice.Choices.Count];
     IList<MatchInfo>[] dbr = new IList<MatchInfo>[choice.Choices.Count];
     int[] minLA = new int[choice.Choices.Count - 1];
     MatchInfo[] overlapInfo = new MatchInfo[choice.Choices.Count - 1];
     int[] other = new int[choice.Choices.Count - 1];
     MatchInfo m;
     IList<MatchInfo> v;
     bool overlapDetected;
     for (int la = 1; la <= Options.getChoiceAmbiguityCheck(); la++) {
         MatchInfo.laLimit = la;
         LookaheadWalk.considerSemanticLA = !Options.getForceLaCheck();
         for (int i = first; i < choice.Choices.Count - 1; i++) {
             LookaheadWalk.sizeLimitedMatches = new List<MatchInfo>();
             m = new MatchInfo();
             m.firstFreeLoc = 0;
             v = new List<MatchInfo>();
             v.Add(m);
             LookaheadWalk.genFirstSet(v, (Expansion) choice.Choices[i]);
             dbl[i] = LookaheadWalk.sizeLimitedMatches;
         }
         LookaheadWalk.considerSemanticLA = false;
         for (int i = first + 1; i < choice.Choices.Count; i++) {
             LookaheadWalk.sizeLimitedMatches = new List<MatchInfo>();
             m = new MatchInfo();
             m.firstFreeLoc = 0;
             v = new List<MatchInfo>();
             v.Add(m);
             LookaheadWalk.genFirstSet(v, (Expansion) choice.Choices[i]);
             dbr[i] = LookaheadWalk.sizeLimitedMatches;
         }
         if (la == 1) {
             for (int i = first; i < choice.Choices.Count - 1; i++) {
                 Expansion exp = (Expansion) choice.Choices[i];
                 if (Semanticize.EmptyExpansionExists(exp)) {
                     CSharpCCErrors.Warning(exp,
                         "This choice can expand to the empty token sequence " +
                         "and will therefore always be taken in favor of the choices appearing later.");
                     break;
                 } else if (CodeCheck(dbl[i])) {
                     CSharpCCErrors.Warning(exp,
                         "CSHARPCODE non-terminal will force this choice to be taken " +
                         "in favor of the choices appearing later.");
                     break;
                 }
             }
         }
         overlapDetected = false;
         for (int i = first; i < choice.Choices.Count - 1; i++) {
             for (int j = i + 1; j < choice.Choices.Count; j++) {
                 if ((m = overlap(dbl[i], dbr[j])) != null) {
                     minLA[i] = la + 1;
                     overlapInfo[i] = m;
                     other[i] = j;
                     overlapDetected = true;
                     break;
                 }
             }
         }
         if (!overlapDetected) {
             break;
         }
     }
     for (int i = first; i < choice.Choices.Count - 1; i++) {
         if (explicitLA((Expansion) choice.Choices[i]) && !Options.getForceLaCheck()) {
             continue;
         }
         if (minLA[i] > Options.getChoiceAmbiguityCheck()) {
             CSharpCCErrors.Warning("Choice conflict involving two expansions at");
             Console.Error.Write("         line " + ((Expansion) choice.Choices[i]).Line);
             Console.Error.Write(", column " + ((Expansion) choice.Choices[i]).Column);
             Console.Error.Write(" and line " + ((Expansion) choice.Choices[other[i]]).Line);
             Console.Error.Write(", column " + ((Expansion) choice.Choices[other[i]]).Column);
             Console.Error.WriteLine(" respectively.");
             Console.Error.WriteLine("         A common prefix is: " + image(overlapInfo[i]));
             Console.Error.WriteLine("         Consider using a lookahead of " + minLA[i] + " or more for earlier expansion.");
         } else if (minLA[i] > 1) {
             CSharpCCErrors.Warning("Choice conflict involving two expansions at");
             Console.Error.Write("         line " + ((Expansion) choice.Choices[i]).Line);
             Console.Error.Write(", column " + ((Expansion) choice.Choices[i]).Column);
             Console.Error.Write(" and line " + ((Expansion) choice.Choices[other[i]]).Line);
             Console.Error.Write(", column " + ((Expansion) choice.Choices[other[i]]).Column);
             Console.Error.WriteLine(" respectively.");
             Console.Error.WriteLine("         A common prefix is: " + image(overlapInfo[i]));
             Console.Error.WriteLine("         Consider using a lookahead of " + minLA[i] + " for earlier expansion.");
         }
     }
 }
Пример #4
0
            public void Action(Expansion e)
            {
                if (e is Sequence) {
                    if (e.Parent is Choice || e.Parent is ZeroOrMore ||
                        e.Parent is OneOrMore || e.Parent is ZeroOrOne)
                        return;
                    Sequence seq = (Sequence) e;
                    Lookahead la = (Lookahead) (seq.Units[0]);
                    if (!la.IsExplicit)
                        return;

                    // Create a singleton choice with an empty action.
                    Choice ch = new Choice();
                    ch.Line = la.Line;
                    ch.Column = la.Column;
                    ch.Parent = seq;
                    Sequence seq1 = new Sequence();
                    seq1.Line = la.Line;
                    seq1.Column = la.Column;
                    seq1.Parent = ch;
                    seq1.Units.Add(la);
                    la.Parent = seq1;
                    Action act = new Action();
                    act.Line = la.Line;
                    act.Column = la.Column;
                    act.Parent = seq1;
                    seq1.Units.Add(act);
                    ch.Choices.Add(seq1);
                    if (la.Amount != 0) {
                        if (la.ActionTokens.Count != 0) {
                            CSharpCCErrors.Warning(la,
                                "Encountered LOOKAHEAD(...) at a non-choice location.  " +
                                "Only semantic lookahead will be considered here.");
                        } else
                            CSharpCCErrors.Warning(la, "Encountered LOOKAHEAD(...) at a non-choice location.  This will be ignored.");
                    }
                    // Now we have moved the lookahead into the singleton choice.  Now create
                    // a new dummy lookahead node to replace this one at its original location.
                    Lookahead la1 = new Lookahead();
                    la1.IsExplicit = false;
                    la1.Line = la.Line;
                    la1.Column = la.Column;
                    la1.Parent = seq;
                    // Now set the la_expansion field of la and la1 with a dummy expansion (we use EOF).
                    la.Expansion = new REndOfFile();
                    la1.Expansion = new REndOfFile();
                    seq.Units[0] = la1;
                    seq.Units[1] = ch;
                }
            }