Exemple #1
0
        public override bool TryInvoke(InvokeBinder binder, object[] args, out object result)
        {
            LuaObject[] passingArgs = Array.ConvertAll <object, LuaObject>(args,
                                                                           x => (x is LuaObject ? (LuaObject)x : LuaObject.FromObject(x)));
            LuaArguments ret = this.Call(passingArgs);

            if (ret.Length == 1)
            {
                if (ret[0].IsNil)
                {
                    result = null;
                }
                else
                {
                    result = getObject(ret[0]);
                }
                return(true);
            }
            else
            {
                object[] res = Array.ConvertAll <LuaObject, object>(ret.ToArray(), x => getObject(x));
                result = res;
                return(true);
            }
        }
Exemple #2
0
        static LuaArguments io_output(LuaArguments args)
        {
            var obj = args[0];

            if (isStream(obj))
            {
                currentOutput = obj;
                return(Lua.Return(currentOutput));
            }
            else if (obj.IsString)
            {
#if PORTABLE
                MemoryStream stream = new MemoryStream();
#else
                FileStream stream = new FileStream(obj.ToString(), FileMode.OpenOrCreate);
#endif
                currentOutput = CreateFileObject(stream);
                return(Lua.Return(currentOutput));
            }
            else if (args.Length == 0)
            {
                return(Lua.Return(currentOutput));
            }
            else
            {
                throw new LuaException("Invalid argument");
            }
        }
Exemple #3
0
        static LuaArguments EvalWhile(WhileStat stat, LuaContext Context, out LuaReturnStatus returned)
        {
            returned.returned = false;
            returned.broke    = false;
            LuaObject  cond = EvalExpression(stat.Condition, Context)[0];
            LuaContext ctx  = new LuaContext(Context);

            while (cond.AsBool())
            {
                LuaArguments obj = EvalBlock(stat.Block, ctx, out returned);
                if (returned.broke)
                {
                    break;
                }
                if (returned.returned)
                {
                    return(obj);
                }
                else
                {
                    cond = EvalExpression(stat.Condition, Context)[0];
                }
            }
            return(Lua.Return());
        }
Exemple #4
0
        static LuaArguments EvalRepeat(RepeatStat stat, LuaContext Context, out LuaReturnStatus returned)
        {
            returned.returned = false;
            returned.broke    = false;
            LuaContext ctx = new LuaContext(Context);

            while (true)
            {
                LuaArguments obj = EvalBlock(stat.Block, ctx, out returned);

                if (returned.broke)
                {
                    break;
                }
                if (returned.returned)
                {
                    return(obj);
                }
                LuaObject cond = EvalExpression(stat.Condition, ctx)[0];
                if (cond)
                {
                    break;
                }
            }
            return(Lua.Return());
        }
Exemple #5
0
        static LuaArguments write(LuaArguments args)
        {
            var self = args[0];

            if (isStream(self))
            {
                FileObject fobj = self.luaobj as FileObject;
                foreach (var arg in args)
                {
                    if (arg == self)
                    {
                        continue;
                    }

                    if (!(arg.IsString || arg.IsNumber))
                    {
                        Lua.Return();
                    }

                    if (fobj.stream.CanWrite)
                    {
                        fobj.writer.Write(arg.ToString());
                    }
                    else
                    {
                        Lua.Return();
                    }
                }
                return(Lua.Return(self));
            }
            else
            {
                return(Lua.Return());
            }
        }
Exemple #6
0
        static LuaArguments EvalNumericFor(NumericFor stat, LuaContext Context, out LuaReturnStatus returned)
        {
            returned.broke    = false;
            returned.returned = false;
            var varList   = EvalExpression(stat.Var, Context);
            var limitList = EvalExpression(stat.Limit, Context);
            var stepList  = EvalExpression(stat.Step, Context);
            var var       = LuaEvents.toNumber(varList[0]);
            var limit     = LuaEvents.toNumber(limitList[0]);
            var step      = LuaEvents.toNumber(stepList[0]);

            if (!(var & limit & step).AsBool())
            {
                throw new LuaException("Error in for loop");
            }
            LuaContext ctx = new LuaContext(Context);

            while ((step > 0 & var <= limit) | (step <= 0 & var >= limit))
            {
                ctx.SetLocal(stat.Variable, var);
                LuaArguments obj = EvalBlock(stat.Block, ctx, out returned);
                if (returned.broke)
                {
                    break;
                }
                if (returned.returned)
                {
                    return(obj);
                }
                var = var + step;
            }
            return(Lua.Return());
        }
Exemple #7
0
        LuaArguments type(LuaArguments args)
        {
            switch (args[0].Type)
            {
            case LuaType.boolean:
                return(Return("boolean"));

            case LuaType.function:
                return(Return("function"));

            case LuaType.nil:
                return(Return("nil"));

            case LuaType.number:
                return(Return("number"));

            case LuaType.@string:
                return(Return("string"));

            case LuaType.table:
                return(Return("table"));

            case LuaType.thread:
                return(Return("thread"));

            case LuaType.userdata:
                return(Return("userdata"));
            }
            return(Return());
        }
Exemple #8
0
        LuaArguments tonumber(LuaArguments args)
        {
            LuaObject obj = args[0];

            if (args.Length == 1)
            {
                double d = 0;
                if (obj.IsString)
                {
                    if (double.TryParse(obj.AsString(), out d))
                    {
                        return(Return(d));
                    }
                    else
                    {
                        return(Return());
                    }
                }
                else if (obj.IsNumber)
                {
                    return(Return(obj.AsNumber()));
                }
                else
                {
                    return(Return());
                }
            }
            else
            {
                //TODO: Implement tonumber for bases different from 10
                throw new NotImplementedException();
            }
        }
Exemple #9
0
        static LuaArguments io_temp(LuaArguments args)
        {
            string path = Path.GetTempFileName();
            Stream s    = new FileStream(path, FileMode.Append, FileAccess.Write, FileShare.Write, Int16.MaxValue, FileOptions.DeleteOnClose);

            return(Lua.Return(CreateFileObject(s)));
        }
Exemple #10
0
        LuaArguments ipairs(LuaArguments args)
        {
            LuaObject handler = LuaEvents.getMetamethod(args[0], "__ipairs");

            if (!handler.IsNil)
            {
                return(handler.Call(args));
            }
            else
            {
                if (args[0].IsTable)
                {
                    LuaFunction f = delegate(LuaArguments x)
                    {
                        var s   = x[0];
                        var var = x[1].AsNumber() + 1;

                        var val = s[var];
                        if (val == LuaObject.Nil)
                        {
                            return(Return(LuaObject.Nil));
                        }
                        else
                        {
                            return(Return(var, val));
                        }
                    };
                    return(Return(f, args[0], 0));
                }
                else
                {
                    throw new LuaException("t must be a table");
                }
            }
        }
Exemple #11
0
        LuaArguments next(LuaArguments args)
        {
            var table = args[0];
            var index = args[1];

            if (!table.IsTable)
            {
                throw new LuaException("t must be a table");
            }
            List <LuaObject> keys = new List <LuaObject>(table.AsTable().Keys);

            if (index.IsNil)
            {
                if (keys.Count == 0)
                {
                    return(Return());
                }
                return(Return(keys[0], table[keys[0]]));
            }
            else
            {
                int pos = keys.IndexOf(index);
                if (pos == keys.Count - 1)
                {
                    return(Return());
                }
                else
                {
                    return(Return(keys[pos + 1], table[keys[pos + 1]]));
                }
            }
        }
Exemple #12
0
        static LuaArguments math_max(LuaArguments args)
        {
            var max = args[0];

            foreach (LuaObject o in args)
            {
                max = Math.Max(max, o);
            }
            return(Lua.Return(max));
        }
Exemple #13
0
        static LuaArguments math_min(LuaArguments args)
        {
            var min = args[0];

            foreach (LuaObject o in args)
            {
                min = Math.Min(min, o);
            }
            return(Lua.Return(min));
        }
Exemple #14
0
        static LuaArguments flush(LuaArguments args)
        {
            var obj = args[0];

            if (isStream(obj))
            {
                FileObject fobj = obj.luaobj as FileObject;
                fobj.writer.Flush();
            }
            return(Lua.Return());
        }
Exemple #15
0
        static LuaArguments close(LuaArguments args)
        {
            var obj = args[0];

            if (isStream(obj))
            {
                FileObject fobj = obj.luaobj as FileObject;
                fobj.stream.Close();
            }
            return(Lua.Return());
        }
Exemple #16
0
        /// <summary>
        /// Calls the object passing the instance as first argument. Uses the metafield __call
        /// </summary>
        /// <param name="instance">The object to be passed as first argument</param>
        /// <param name="args">Arguments to be passed after the object</param>
        public LuaArguments MethodCall(LuaObject instance, LuaArguments args)
        {
            LuaObject[] objs = new LuaObject[args.Length + 1];
            objs[0] = instance;
            for (int i = 0; i < args.Length; i++)
            {
                objs[i + 1] = args[i];
            }

            return(this.Call(objs));
        }
Exemple #17
0
        static LuaArguments read(LuaArguments args)
        {
            var self = args[0];

            if (isStream(self))
            {
                var fobj = self.luaobj as FileObject;
                if (args.Length == 1)
                {
                    var line = fobj.reader.ReadLine();

                    return(Lua.Return(line));
                }
                else
                {
                    List <LuaObject> ret = new List <LuaObject>();
                    foreach (var arg in args)
                    {
                        if (arg == self)
                        {
                            continue;
                        }
                        if (arg.IsNumber)
                        {
                            StringBuilder bld = new StringBuilder();
                            for (int i = 0; i < arg; i++)
                            {
                                bld.Append((char)fobj.reader.Read());
                            }
                            ret.Add(bld.ToString());
                        }
                        else if (arg == "*a")
                        {
                            ret.Add(fobj.reader.ReadToEnd());
                        }
                        else if (arg == "*l")
                        {
                            ret.Add(fobj.reader.ReadLine());
                        }
                        else if (arg == "*n")
                        {
                            //TODO: Implement io.read("*n")
                            throw new NotImplementedException();
                        }
                    }
                    return(Lua.Return(ret.ToArray()));
                }
            }
            else
            {
                return(Lua.Return());
            }
        }
Exemple #18
0
        LuaArguments pairs(LuaArguments args)
        {
            LuaObject handler = LuaEvents.getMetamethod(args[0], "__pairs");

            if (!handler.IsNil)
            {
                return(handler.Call(args));
            }
            else
            {
                return(Return((LuaFunction)next, args[0], LuaObject.Nil));
            }
        }
Exemple #19
0
        static LuaArguments io_write(LuaArguments args)
        {
            var obj = args[0];

            if (!obj.IsNil)
            {
                return(currentOutput["write"].MethodCall(currentOutput, args));
            }
            else
            {
                return(Lua.Return());
            }
        }
Exemple #20
0
        static LuaArguments io_close(LuaArguments args)
        {
            var obj = args[0];

            if (obj.IsNil)
            {
                return(currentOutput["close"].MethodCall(currentOutput, args));
            }
            else
            {
                return(obj["close"].MethodCall(obj, args));
            }
        }
Exemple #21
0
        static LuaArguments EvalFunctionCall(FunctionCall Expression, LuaContext Context)
        {
            LuaObject func = EvalExpression(Expression.Function, Context)[0];

            LuaArguments args = null;

            if (Expression.Arguments != null || Expression.Arguments.Count != 0)
            {
                List <LuaObject> values = new List <LuaObject>();
                foreach (IExpression expr in Expression.Arguments)
                {
                    values.AddRange(EvalExpression(expr, Context));
                }
                args = values.ToArray();
            }
            return(func.Call(args));
        }
Exemple #22
0
        static LuaArguments EvalGenericFor(GenericFor stat, LuaContext Context, out LuaReturnStatus returned)
        {
            returned.broke    = false;
            returned.returned = false;

            LuaArguments args = null;

            foreach (IExpression expr in stat.Expressions)
            {
                if (args == null)
                {
                    args = EvalExpression(expr, Context);
                }
                else
                {
                    args.Concat(EvalExpression(expr, Context));
                }
            }
            LuaObject  f = args[0], s = args[1], var = args[2];
            LuaContext ctx = new LuaContext(Context);

            while (true)
            {
                LuaArguments res = f.Call(s, var);
                for (int i = 0; i < stat.Variables.Count; i++)
                {
                    ctx.SetLocal(stat.Variables[i], res[i]);
                }
                if (res[0].IsNil)
                {
                    break;
                }
                var = res[0];
                LuaArguments obj = EvalBlock(stat.Block, ctx, out returned);
                if (returned.broke)
                {
                    break;
                }
                if (returned.returned)
                {
                    return(obj);
                }
            }

            return(Lua.Return());
        }
Exemple #23
0
        LuaArguments rawlen(LuaArguments args)
        {
            LuaObject obj = args[0];

            if (obj.IsString)
            {
                return(Return(obj.AsString().Length));
            }
            else if (obj.IsTable)
            {
                return(Return(obj.AsTable().Count));
            }
            else
            {
                throw new LuaException("invalid argument");
            }
        }
Exemple #24
0
        static LuaArguments io_type(LuaArguments args)
        {
            var obj = args[0];

            if (isStream(obj))
            {
                FileObject fobj = obj.luaobj as FileObject;
                if (!fobj.stream.CanWrite && !fobj.stream.CanRead)
                {
                    return(Lua.Return("closed file"));
                }
                else
                {
                    return(Lua.Return("file"));
                }
            }
            return(Lua.Return());
        }
Exemple #25
0
 LuaArguments assert(LuaArguments args)
 {
     if (args.Length > 0)
     {
         if (args[0].AsBool() == false)
         {
             if (args.Length == 1)
             {
                 throw new LuaException("Assertion failed");
             }
             else
             {
                 throw new LuaException(args[1].ToString());
             }
         }
     }
     return(Return());
 }
Exemple #26
0
        static LuaObject EvalTableConstructor(TableConstructor tctor, LuaContext Context)
        {
            Dictionary <LuaObject, LuaObject> table = new Dictionary <LuaObject, LuaObject>();
            int i = 0;

            foreach (KeyValuePair <IExpression, IExpression> pair in tctor.Values)
            {
                if (i == tctor.Values.Count - 1 && (pair.Value is FunctionCall || pair.Value is VarargsLiteral))
                // This is the last element, and this is a function call or varargs, thus we will add
                // every return value to the table
                {
                    LuaObject key = EvalExpression(pair.Key, Context)[0];
                    if (key.IsNumber)
                    {
                        LuaArguments values = EvalExpression(pair.Value, Context);

                        double k = key;
                        foreach (LuaObject v in values)
                        {
                            table.Add(k, v);
                            k++;
                        }
                    }
                    else
                    {
                        LuaObject value = EvalExpression(pair.Value, Context)[0];

                        table.Add(key, value);
                    }
                }
                else
                {
                    LuaObject key   = EvalExpression(pair.Key, Context)[0];
                    LuaObject value = EvalExpression(pair.Value, Context)[0];

                    table.Add(key, value);
                }
                i++;
            }
            return(LuaObject.FromTable(table));
        }
Exemple #27
0
 internal static LuaArguments call_event(LuaObject func, LuaArguments args)
 {
     if (func.IsFunction)
     {
         return(func.AsFunction()(args));
     }
     else
     {
         var handler = getMetamethod(func, "__call");
         if (handler.IsFunction)
         {
             var argslist = new List <LuaObject>();
             argslist.Add(func); argslist.AddRange(args);
             return(handler.AsFunction()(argslist.ToArray()));
         }
         else
         {
             throw new LuaException("Cannot call nonfunction");
         }
     }
 }
Exemple #28
0
        static LuaArguments io_open(LuaArguments args)
        {
            var file = args[0];
            var mode = args[1];

            if (file.IsString)
            {
                FileMode   fmode   = FileMode.Open;
                FileAccess faccess = FileAccess.Read;
                if (mode.IsString)
                {
                    switch (mode.ToString())
                    {
                    case "r":
                        faccess = FileAccess.Read; break;

                    case "w":
                        fmode = FileMode.Create; faccess = FileAccess.ReadWrite; break;

                    case "a":
                        fmode = FileMode.Append; faccess = FileAccess.Write; break;

                    case "r+":
                    case "w+":
                    case "a+":
                        // TODO: Implement rwa+
                        throw new NotImplementedException();
                    }
                }
                FileStream stream = new FileStream(file.ToString(), fmode, faccess);

                return(Lua.Return(CreateFileObject(stream)));
            }
            else
            {
                return(Lua.Return());
            }
        }
Exemple #29
0
        static LuaArguments io_input(LuaArguments args)
        {
            var obj = args[0];

            if (isStream(obj))
            {
                currentInput = obj;
                return(Lua.Return(currentInput));
            }
            else if (obj.IsString)
            {
                currentInput = io_open(args)[0];
                return(Lua.Return(currentInput));
            }
            else if (args.Length == 0)
            {
                return(Lua.Return(currentInput));
            }
            else
            {
                throw new LuaException("Invalid argument");
            }
        }
Exemple #30
0
        static LuaArguments seek(LuaArguments args)
        {
            var obj    = args[0];
            var whence = args[1] | "cur";
            var offset = args[2] | 0;

            if (isStream(obj))
            {
                var fobj = obj.luaobj as FileObject;
                switch (whence.ToString())
                {
                case "cur":
                    fobj.stream.Position += (long)offset; break;

                case "set":
                    fobj.stream.Position = (long)offset; break;

                case "end":
                    fobj.stream.Position = fobj.stream.Length + (long)offset; break;
                }
                return(Lua.Return(fobj.stream.Position));
            }
            return(Lua.Return());
        }