示例#1
0
 /// <summary>
 /// Creates a new CheckManual instance
 /// </summary>
 public CheckerManual()
 {
     lib = Vnvd.Library;
 }
示例#2
0
        private UserMethod DefineMethod(UserType type, String name, List <string> modifiers, String _return, String[] parTypes, String[] parNames)
        {
            bool overrid = modifiers.Remove("override");

            if (overrid)
            {
                modifiers.Add("virtual");
            }
            if (!type.IsAbstract && modifiers.Contains("abstract"))
            {
                throw new CheckerException("Cannot declare abstract method " + name + " in a non-abstract class: " + type.Name);
            }
            if (modifiers.Contains("abstract"))
            {
                modifiers.Add("virtual");
            }
            MethodAttributes attr = MethodAttributes.HideBySig;

            foreach (String s in modifiers)
            {
                attr |= (MethodAttributes)Enum.Parse(typeof(MethodAttributes), s, true);
            }

            IdEntry[] pars = new IdEntry[parTypes.Length];
            for (int i = 0; i < parTypes.Length; i++)
            {
                pars[i] = this.GetTypeIdEntry(parTypes[i]);
            }
            IdEntry ret = KeywordToType(_return) != null ? new IdEntry()
            {
                ReflectionObject = KeywordToType(_return)
            } : this.GetTypeIdEntry(_return);

            if (overrid)
            {
                MethodInfo m = type.BaseType.GetMethod(name, BindingFlags.FlattenHierarchy | BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, LibraryChecker.ToArray <Type>(pars), null);
                if (m == null || m.ReturnType != ret.ReflectionObject)
                {
                    throw new CheckerException("No suitable method found to override: " + name);
                }
                if (!m.IsVirtual)
                {
                    throw new CheckerException("Cannot override a non-virtual method: " + m.Name);
                }
            }
            else
            {
                MethodInfo m = type.GetMethod(name, BindingFlags.FlattenHierarchy | BindingFlags.ExactBinding | BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, LibraryChecker.ToArray <Type>(pars), null);
                if (m != null)
                {
                    throw new CheckerException("Method already exists: " + m.Name);
                }
                if (type.GetInterfaceMethod(name, LibraryChecker.ToArray <Type>(pars)) != null)
                {
                    attr |= MethodAttributes.NewSlot | MethodAttributes.Virtual;
                }
            }
            UserMethod metb = type.DefineMethod(name, attr, ret, pars, parNames);

            return(metb);
        }
示例#3
0
文件: Vnvd.cs 项目: fvannee/vnvd
        /// <summary>
        /// The main function of Vnvd. This runs the compiler.
        /// </summary>
        /// <param name="args">The command line arguments given to Vnvd.</param>
        public static void Main(String[] args)
        {
            Console.Out.WriteLine("Vnvd Compiler v" + Assembly.GetExecutingAssembly().GetName().Version);
            Console.Out.WriteLine("======================");
            Console.Out.WriteLine();
            ParseOptions(args);
            try
            {
                lib = new LibraryChecker(refs.ToArray());
            }
            catch (ArgumentException ex)
            {
                Console.WriteLine(ex.Message);
                Environment.Exit(1);
            }
            List <TreeNode> trees = new List <TreeNode>();
            bool            error = false;

            foreach (String filename in filenames)
            {
                VnvdLexer lexer = new VnvdLexer(new ANTLRFileStream(filename));

                CommonTokenStream tokens = new CommonTokenStream(lexer);
                VnvdParser        parser = new VnvdParser(tokens);
                parser.TreeAdaptor = new TreeNodeAdaptor();

                VnvdParser.program_return result = parser.program();
                TreeNode tree = (TreeNode)result.Tree;
                trees.Add(tree);

                if (parser.NumberOfSyntaxErrors > 0)
                {
                    error = true;
                }
            }

            if (!error)
            {
                VnvdTreeWalker checker = null;
                if (!opt_nochecker)
                {
                    // check the AST
                    CheckerManual manual = new CheckerManual();
                    try
                    {
                        foreach (TreeNode tree in trees)
                        {
                            manual.WalkClasses(tree);
                        }
                        manual.WalkClassExtendation();
                        manual.WalkClassMembers();

                        for (int i = 0; i < trees.Count; i++)
                        {
                            TreeNode        tree   = trees[i];
                            ITreeNodeStream nodes  = new CommonTreeNodeStream(tree);
                            CheckerHelper   helper = new CheckerHelper();
                            checker             = new VnvdTreeWalker(helper, nodes);
                            checker.Filename    = filenames[i];
                            checker.TreeAdaptor = new TreeNodeAdaptor();
                            helper.Walker       = checker;

                            checker.program();
                            if (checker.SemanticErrorCount > 0 || checker.NumberOfSyntaxErrors > 0)
                            {
                                error = true;
                            }
                        }
                    }
                    catch (CheckerException ex)
                    {
                        Console.WriteLine(ex.ToString());
                        error = true;
                    }
                }

                if (!error)
                {
                    if (!opt_nogenerator)
                    {
                        AssemblyName aName = new AssemblyName();
                        aName.Name = Vnvd.OutputFile.Substring(0, Vnvd.OutputFile.LastIndexOf('.'));

                        AssemblyBuilder ab =
                            AppDomain.CurrentDomain.DefineDynamicAssembly(
                                aName,
                                AssemblyBuilderAccess.Save);

                        // For a single-module assembly, the module name is usually
                        // the assembly name plus an extension.
                        mb =
                            ab.DefineDynamicModule(aName.Name, Vnvd.OutputFile);
                        GeneratorManual manualWalker = new GeneratorManual(mb, ab);

                        foreach (TreeNode tree in trees)
                        {
                            manualWalker.WalkTypes(tree);
                        }
                        manualWalker.WalkTypeMembers();

                        foreach (TreeNode tree in trees)
                        {
                            ITreeNodeStream nodes     = new CommonTreeNodeStream(tree);
                            VnvdTreeWalker  generator = new VnvdTreeWalker(new GeneratorHelper(), nodes);
                            generator.program();
                        }

                        foreach (TypeBuilder t in manualWalker.AllTypes)
                        {
                            t.CreateType();
                        }

                        try
                        {
                            ab.Save(OutputFile);
                        }
                        catch (IOException)
                        {
                            Console.WriteLine("Error while saving the assembly. The output file is in use.");
                        }
                    }
                }

                if (opt_ast)
                {
                    // print the AST as string
                    StringBuilder sb = new StringBuilder();

                    foreach (TreeNode tree in trees)
                    {
                        String s      = tree.ToStringTree();
                        int    indent = 0;
                        foreach (char c in s)
                        {
                            if (c == '(')
                            {
                                sb.Append('\n');
                                indent += 3;
                                for (int i = 0; i < indent; i++)
                                {
                                    sb.Append(' ');
                                }
                            }
                            else if (c == ')')
                            {
                                indent -= 3;
                            }
                            sb.Append(c);
                        }

                        sb.AppendLine();
                        sb.AppendLine();
                    }


                    //Console.WriteLine(sb.ToString());
                    Console.WriteLine("AST was written to ast.txt");
                    StreamWriter sw = new StreamWriter("ast.txt");
                    sw.Write(sb.ToString());
                    sw.Close();
                }
                else if (opt_dot)
                {
                    // print the AST as DOT specification
                    DOTTreeGenerator gen = new DOTTreeGenerator();

                    Console.WriteLine("Graphviz AST graph (only first tree) was written to ast.dot");
                    StringTemplate st = gen.ToDOT(trees[0]);
                    StreamWriter   sw = new StreamWriter("ast.dot");
                    sw.Write(st.ToString());
                    sw.Close();
                }
            }

            if (wait)
            {
                Console.Read();
            }
        }