示例#1
0
        public P5Code ParseFile(Runtime runtime, string program, bool is_main)
        {
            var parser = SafeInstance(runtime);
            P5Array arglist_parse_file =
                new P5Array(parser_runtime,
                            parser,
                            new P5Scalar(parser_runtime, program),
                            new P5Scalar(parser_runtime, 3));

            IP5Any res;
            try
            {
                res = arglist_parse_file.CallMethod(parser_runtime, Opcode.ContextValues.SCALAR, "parse_file");
            }
            catch (System.Reflection.TargetInvocationException te)
            {
                var e = te.InnerException as P5Exception;

                if (e == null)
                    throw te;
                else
                    throw FixupException(e);
            }
            catch (P5Exception e)
            {
                throw FixupException(e);
            }

            return NetGlue.UnwrapValue(res, typeof(P5Code)) as P5Code;
        }
示例#2
0
        public Parser(Runtime runtime)
        {
            parser_runtime = new Runtime();
            parser_runtime.NativeRegex = true;

            // find compiled code
            var parser_assembly = System.Reflection.Assembly.Load("Language.P.Net.Parser");

            parser_runtime.ModuleLoaders.Insert(0, new AssemblyModuleLoader(parser_assembly));

            // load Language::P frontend
            Builtins.RequireFile(parser_runtime,
                                 Opcode.ContextValues.VOID,
                                 new P5Scalar(parser_runtime, "Language/P.pm"));

            // create generator
            generator = new DynamicGenerator(runtime, parser_runtime);

            // instantiate parser
            P5Array arglist_parser =
                new P5Array(parser_runtime,
                            new P5Scalar(parser_runtime, "Language::P::Parser"),
                            GetInit(runtime));
            parser_template = arglist_parser.CallMethod(parser_runtime, Opcode.ContextValues.SCALAR, "new") as P5Scalar;
        }
示例#3
0
        public P5Code ParseString(Runtime runtime, string program, string file, int line)
        {
            var parser = SafeInstance(runtime);
            var reader = new P5Handle(
                parser_runtime, new System.IO.StringReader(program), null);
            P5Array arglist_parse_stream =
                new P5Array(parser_runtime,
                            parser,
                            new P5Scalar(parser_runtime, reader),
                            new P5Scalar(parser_runtime, file),
                            new P5Scalar(parser_runtime, 3),
                            new P5Scalar(parser_runtime));

            IP5Any res;
            try
            {
                res = arglist_parse_stream.CallMethod(parser_runtime, Opcode.ContextValues.SCALAR, "parse_stream");
            }
            catch (System.Reflection.TargetInvocationException te)
            {
                var e = te.InnerException as P5Exception;

                if (e == null)
                    throw te;
                else
                    throw FixupException(e);
            }
            catch (P5Exception e)
            {
                throw FixupException(e);
            }

            return NetGlue.UnwrapValue(res, typeof(P5Code)) as P5Code;
        }
示例#4
0
        private IP5Any SafeInstance(Runtime runtime)
        {
            P5Array arglist_safe_instance =
                new P5Array(parser_runtime,
                            parser_template);
            var parser = arglist_safe_instance.CallMethod(parser_runtime, Opcode.ContextValues.SCALAR, "safe_instance");

            return parser;
        }
示例#5
0
        public void Run(Runtime runtime, string[] args)
        {
            P5Array argv = new P5Array(parser_runtime);

            foreach (var arg in args)
                argv.Push(parser_runtime, new P5Scalar(parser_runtime, arg));

            P5Array arglist_new =
                new P5Array(parser_runtime,
                            new P5Scalar(parser_runtime, "Language::P"),
                            new P5Scalar(parser_runtime, argv),
                            GetInit(runtime));

            try
            {
                var p = arglist_new.CallMethod(parser_runtime, Opcode.ContextValues.SCALAR, "new_from_argv");

                P5Array arglist_run = new P5Array(parser_runtime, p);
                arglist_run.CallMethod(parser_runtime, Opcode.ContextValues.VOID, "run");
            }
            catch (System.Reflection.TargetInvocationException te)
            {
                var e = te.InnerException as P5Exception;

                if (e == null)
                    throw te;
                else
                    throw FixupException(e);
            }
            catch (P5Exception e)
            {
                throw FixupException(e);
            }
        }
示例#6
0
        private P5Exception FixupException(P5Exception e)
        {
            // TODO required until Language::P::Exception can be derived
            //      from P5Exception
            if (e.Reference != null)
            {
                var stash = e.Reference.BlessedReferenceStash(parser_runtime);
                var l_p_e = parser_runtime.SymbolTable.GetPackage(parser_runtime, "Language::P::Exception", false);

                if (stash.IsDerivedFrom(parser_runtime, l_p_e))
                {
                    P5Array arglist_format_message =
                        new P5Array(parser_runtime,
                                    e.Reference);
                    var msg = arglist_format_message.CallMethod(parser_runtime, Opcode.ContextValues.SCALAR, "format_message");

                    return new P5Exception(parser_runtime, msg.AsString(parser_runtime));
                }
            }

            return e;
        }
示例#7
0
        private P5Scalar _to_ir(string method, P5Scalar trees)
        {
            P5Array arglist_generate =
                new P5Array(parser_runtime,
                            intermediate,
                            trees);
            var segments = arglist_generate.CallMethod(parser_runtime, Opcode.ContextValues.SCALAR, method) as P5Scalar;

            P5Array arglist_transform =
                new P5Array(parser_runtime,
                            transform,
                            segments);
            arglist_transform.CallMethod(parser_runtime, Opcode.ContextValues.VOID, "all_to_tree");

            return segments;
        }
示例#8
0
        private P5Scalar CreateTransform()
        {
            P5Array arglist_transform =
                new P5Array(parser_runtime,
                            new P5Scalar(parser_runtime, "Language::P::Intermediate::Transform"));

            return arglist_transform.CallMethod(parser_runtime, Opcode.ContextValues.SCALAR, "new") as P5Scalar;
        }
示例#9
0
        private P5Scalar CreateIRGenerator()
        {
            P5Array arglist_parser =
                new P5Array(parser_runtime,
                            new P5Scalar(parser_runtime, "Language::P::Intermediate::Generator"),
                            new P5Scalar(parser_runtime, new P5Hash(parser_runtime)));

            return arglist_parser.CallMethod(parser_runtime, Opcode.ContextValues.SCALAR, "new") as P5Scalar;
        }
示例#10
0
        // TODO change it to P5Hash when auto-dereference is implemented,
        //      and maybe use a plain .Net map
        public void start_code_generation(P5Scalar args)
        {
            var argmap = args.DereferenceHash(parser_runtime);

            file_name = argmap.GetItem(parser_runtime, "file_name").AsString(parser_runtime);

            pending = new List<P5Scalar>();

            P5Array arglist_create_main =
                new P5Array(parser_runtime,
                            intermediate,
                            new P5Scalar(parser_runtime),
                            new P5Scalar(parser_runtime, false));
            arglist_create_main.CallMethod(parser_runtime, Opcode.ContextValues.SCALAR, "create_main");
        }
示例#11
0
        public void process(P5Scalar tree)
        {
            var use_stash = parser_runtime.SymbolTable.GetPackage(parser_runtime, "Language::P::ParseTree::Use", false);
            var sub_stash = parser_runtime.SymbolTable.GetPackage(parser_runtime, "Language::P::ParseTree::NamedSubroutine", false);
            var lex_stash = parser_runtime.SymbolTable.GetPackage(parser_runtime, "Language::P::ParseTree::LexicalState", false);

            if (tree.BlessedReferenceStash(parser_runtime).IsDerivedFrom(parser_runtime, use_stash))
            {
                var code = _to_ir("generate_use", tree);
                var subs = NetGlue.UnwrapArray<Subroutine>(parser_runtime, code);

                foreach (var sub in subs)
                    mod_generator.Generate(sub);

                return;
            }

            if (tree.BlessedReferenceStash(parser_runtime).IsDerivedFrom(parser_runtime, sub_stash))
            {
                var code = _to_ir("generate_subroutine", tree);
                var subs = NetGlue.UnwrapArray<Subroutine>(parser_runtime, code);

                foreach (var sub in subs)
                    mod_generator.Generate(sub);

                return;
            }

            if (tree.BlessedReferenceStash(parser_runtime).IsDerivedFrom(parser_runtime, lex_stash))
            {
                P5Array arglist_changed =
                    new P5Array(parser_runtime, tree);
                int changed = arglist_changed.CallMethod(parser_runtime, Opcode.ContextValues.SCALAR, "changed").AsInteger(parser_runtime);

                if ((changed & Opcode.CHANGED_PACKAGE) != 0)
                {
                    P5Array arglist_package =
                        new P5Array(parser_runtime, tree);
                    string pack = arglist_package.CallMethod(parser_runtime, Opcode.ContextValues.SCALAR, "package").AsString(parser_runtime);

                    runtime.SymbolTable.GetPackage(runtime, pack, true);
                }
            }

            pending.Add(tree.Clone(parser_runtime, 0) as P5Scalar);
        }