Пример #1
0
        // Stack unwinding due to error.

        internal string UnwindStackTrace()
        {
            StringBuilder s = new StringBuilder();

            foreach (Frame frame in UnwoundFrames)
            {
                LuaValue function = Stack[frame.FrameBase];
                if (function is LuaFunction)
                {
                    LuaPrototype prototype = ((LuaFunction)function).Prototype;
                    SourceSpan   location  = prototype.DebugInstructionSourceSpans[frame.InstructionPointer - 1];
                    s.AppendFormat("   at <unknown> in {0}:line {1}\n", location.Start.SourceName, location.Start.Line);
                }
                else
                {
                    s.AppendFormat("   Frame: {0} {1} {2} {3}\n", frame.FrameBase, frame.ResultCount, frame.FramePointer, frame.InstructionPointer);
                }

                StackWatermark(frame.FrameBase);
            }

            UnwoundFrames.Clear();

            return(s.ToString());
        }
Пример #2
0
        public LuaFunction(LuaPrototype p, LuaTable environment)
        {
            upVals    = new UpVal[p.UpValCount];
            prototype = p;

            if (environment != null)
            {
                Environment = environment;
            }
            else
            {
                Environment = LuaThread.CurrentThread.Environment;
            }
        }
Пример #3
0
        public static LuaPrototype Load(BinaryReader r)
        {
            // Header.
            CheckSByte(r, 0x1B);        // <esc>
            CheckSByte(r, 0x4C);        // 'L'
            CheckSByte(r, 0x75);        // 'u'
            CheckSByte(r, 0x61);        // 'a'
            CheckSByte(r, 0x51);        // Version 5.1
            CheckSByte(r, 0x00);        // Format 0
            CheckSByte(r, 0x01);        // Little-endian
            CheckSByte(r, 0x04);        // sizeof( int )
            CheckSByte(r, 0x04);        // sizeof( size_t )
            CheckSByte(r, 0x04);        // sizeof( Instruction )
            CheckSByte(r, 0x08);        // sizeof( lua_Number )
            CheckSByte(r, 0x00);        // Floating-point


            // Function.
            LuaPrototype result = new LuaPrototype();

            result.LoadPrototype(r);
            return(result);
        }
Пример #4
0
        void LoadPrototype(BinaryReader r)
        {
            // Function information.
            DebugName       = ReadString(r);
            DebugSourceSpan = new SourceSpan(DebugName, r.ReadInt32(), 0, r.ReadInt32(), 0);
            UpValCount      = r.ReadByte();
            ParameterCount  = r.ReadByte();
            IsVararg        = r.ReadByte() != 0;
            StackSize       = r.ReadByte();


            // Instructions.
            int instructionsLength = r.ReadInt32();

            Instructions = new Instruction[instructionsLength];
            for (int instruction = 0; instruction < instructionsLength; ++instruction)
            {
                Instructions[instruction] = Instruction.FromUInt32(r.ReadUInt32());
            }


            // Constants.
            int constantsLength = r.ReadInt32();

            Constants = new LuaValue[constantsLength];
            for (int constant = 0; constant < constantsLength; ++constant)
            {
                switch (r.ReadSByte())
                {
                case LUA_TNIL:
                    Constants[constant] = null;
                    break;

                case LUA_TBOOLEAN:
                    Constants[constant] = r.ReadSByte() != 0;
                    break;

                case LUA_TNUMBER:
                    double d = r.ReadDouble();
                    int    i = (int)d;
                    if ((double)i == d)
                    {
                        Constants[constant] = i;
                    }
                    else
                    {
                        Constants[constant] = d;
                    }
                    break;

                case LUA_TSTRING:
                    Constants[constant] = ReadString(r);
                    break;

                default:
                    throw new FileLoadException();
                }
            }



            // Prototypes.
            int prototypesLength = r.ReadInt32();

            Prototypes = new LuaPrototype[prototypesLength];
            for (int prototype = 0; prototype < prototypesLength; ++prototype)
            {
                Prototypes[prototype] = new LuaPrototype();
                Prototypes[prototype].LoadPrototype(r);
            }


            // Debug information.
            int debugInstructionSourceSpansLength = r.ReadInt32();

            DebugInstructionSourceSpans = new SourceSpan[debugInstructionSourceSpansLength];
            for (int debugInstructionSourceSpan = 0; debugInstructionSourceSpan < debugInstructionSourceSpansLength; ++debugInstructionSourceSpan)
            {
                int line = r.ReadInt32();
                DebugInstructionSourceSpans[debugInstructionSourceSpan] = new SourceSpan(DebugName, line, 0, line, 0);
            }

            int debugLocalsLength = r.ReadInt32();

            DebugLocals = new Symbol[debugLocalsLength];
            for (int debugLocal = 0; debugLocal < debugLocalsLength; ++debugLocal)
            {
                DebugLocals[debugLocal] = new Symbol(ReadString(r), r.ReadInt32(), r.ReadInt32());
            }

            int debugUpValNamesLength = r.ReadInt32();

            DebugUpValNames = new string[debugUpValNamesLength];
            for (int debugUpValName = 0; debugUpValName < debugUpValNamesLength; ++debugUpValName)
            {
                DebugUpValNames[debugUpValName] = ReadString(r);
            }
        }
Пример #5
0
        public void Disassemble(TextWriter o)
        {
            // Function signature.

            o.Write("function ");
            if (DebugName != null && DebugName != String.Empty)
            {
                o.Write(DebugName);
            }
            else
            {
                o.Write("x");
                o.Write(GetHashCode().ToString("X"));
            }
            o.Write("(");
            if (ParameterCount > 0 || IsVararg)
            {
                o.Write(" ");
                bool bFirst = true;
                for (int i = 0; i < ParameterCount; ++i)
                {
                    if (!bFirst)
                    {
                        o.Write(", ");
                    }
                    bFirst = false;
                    o.Write(DebugLocals[i].Name);
                }
                if (IsVararg)
                {
                    if (!bFirst)
                    {
                        o.Write(", ");
                    }
                    bFirst = false;
                    o.Write("...");
                }
                o.Write(" ");
            }
            o.WriteLine(")");


            // Information.

            o.WriteLine(" -- {0} registers, {1} constants", StackSize, Constants.Length);


            // Upvals.

            if (UpValCount > 0)
            {
                o.Write("  -- upval ");
                bool bFirst = true;
                for (int i = 0; i < UpValCount; ++i)
                {
                    if (!bFirst)
                    {
                        o.Write(", ");
                    }
                    bFirst = false;
                    o.Write(DebugUpValNames[i]);
                }
                o.WriteLine();
            }


            // Locals.

            if (DebugLocals.Length > ParameterCount)
            {
                o.Write("  -- local ");
                bool bFirst = true;
                for (int i = ParameterCount; i < DebugLocals.Length; ++i)
                {
                    if (!bFirst)
                    {
                        o.Write(", ");
                    }
                    bFirst = false;
                    o.Write(DebugLocals[i].Name);
                }
                o.WriteLine();
            }


            // Instructions.

            for (int ip = 0; ip < Instructions.Length; ++ip)
            {
                ip = WriteInstruction(o, ip);
                if (Instructions[ip].Opcode == Opcode.Closure)
                {
                    LuaPrototype closure = Prototypes[Instructions[ip].Bx];
                    for (int upval = 0; upval < closure.UpValCount; ++upval)
                    {
                        Instruction i = Instructions[ip + 1 + upval];
                        if (i.Opcode == Opcode.Move)
                        {
                            o.WriteLine("              local   {0} {1}", upval,
                                        OperandString(Mode.R, i.B, ip));
                        }
                        else if (i.Opcode == Opcode.GetUpVal)
                        {
                            o.WriteLine("              upval   {0} {1}", upval,
                                        OperandString(Mode.U, i.B, ip));
                        }
                    }
                    ip += closure.UpValCount;
                }
            }


            // Final.

            o.WriteLine("end");
            o.WriteLine();


            // Other functions.

            for (int i = 0; i < Prototypes.Length; ++i)
            {
                Prototypes[i].Disassemble(o);
            }
        }
Пример #6
0
 public LuaFunction(LuaPrototype p)
     :       this(p, null)
 {
 }