Пример #1
0
        public void AddAnnotation(LuryObject obj)
        {
            if (this.IsFrozen)
            {
                throw new InvalidOperationException();
            }

            this.annotations.Add(obj);
        }
Пример #2
0
        private void InitializeGlobalContext()
        {
            // 一時的なメソッド

            var intrinsic = new LuryObject(IntrinsicIntrinsic.FullName, null, freeze: true);

            this.globalContext[IntrinsicIntrinsic.TypeName] = intrinsic;
            this.globalContext[intrinsic.LuryTypeName]      = intrinsic;

            Action <string, string, IEnumerable <string> > setFunctionMember = (t, n, f) =>
            {
                var type = new LuryObject(t, null);

                foreach (var item in f)
                {
                    type.SetMember(item, new LuryObject(IntrinsicFunction.FullName, t + "." + item, annotations: new[] { intrinsic }, freeze: true));
                }
                type.Freeze();
                this.globalContext[n] = type;
                this.globalContext[type.LuryTypeName] = type;
            };

            setFunctionMember(IntrinsicFunction.FullName, IntrinsicFunction.TypeName, new[] { IntrinsicIntrinsic.OperatorCall });

            var intrinsicTypes = Assembly
                                 .GetExecutingAssembly()
                                 .GetTypes()
                                 .Where(t =>
                                        t.IsClass &&
                                        t.Namespace == "Lury.Engine.Intrinsic" &&
                                        Attribute.GetCustomAttribute(t, typeof(IntrinsicClassAttribute)) != null);

            foreach (var type in intrinsicTypes)
            {
                var attr      = type.GetCustomAttribute <IntrinsicClassAttribute>();
                var methods   = type.GetMethods(BindingFlags.Static | BindingFlags.Public);
                var funcnames = new List <string>();

                for (int j = 0; j < methods.Length; j++)
                {
                    var mattr = methods[j].GetCustomAttributes <IntrinsicAttribute>().Select(a => a.TargetFunction).ToArray();

                    foreach (var funcName in mattr)
                    {
                        funcnames.Add(funcName);
                        this.intrinsicMap.Add(attr.FullName + "." + funcName, methods[j]);
                    }
                }

                if (funcnames.Count > 0)
                {
                    setFunctionMember(attr.FullName, attr.TypeName, funcnames);
                }
            }
        }
Пример #3
0
 private LuryObject Eval(LuryObject self)
 {
     if (self.Annotations.Any(o => o.LuryTypeName == IntrinsicIntrinsic.FullName))
     {
         var intrinsicMethod = this.intrinsicMap[(string)self.Value];
         return((LuryObject)intrinsicMethod.Invoke(null, null));
     }
     else
     {
         throw new NotImplementedException();
     }
 }
Пример #4
0
        public void SetMember(string name, LuryObject obj)
        {
            if (this.IsFrozen)
            {
                throw new InvalidOperationException();
            }

            if (this.members.ContainsKey(name))
            {
                this.members[name] = obj;
            }
            else
            {
                this.members.Add(name, obj);
            }
        }
Пример #5
0
 private LuryObject CallKeyword(LuryObject self, LuryObject kwParam)
 {
     throw new NotImplementedException();
 }
Пример #6
0
 private static void Store(LuryObject obj, Reference toRef, ProgramContext context)
 {
     context[toRef.Name] = obj;
 }
Пример #7
0
        private LuryObject CallRoutine(ProgramContext parentContext, Routine routine)
        {
            LuryObject[]   register       = new LuryObject[routine.RegisterCount];
            ProgramContext currentContext = new ProgramContext(parentContext);

            for (int i = 0; i < routine.RegisterCount; i++)
            {
                register[i] = LuryObject.Nil;
            }

            int instCount = routine.Instructions.Count;

            for (int i = 0; i < instCount; i++)
            {
                Instruction instruction     = routine.Instructions[i];
                LuryObject  temporaryObject = null;

                LuryObject x; //, y, op, f;

                switch (instruction.Operation)
                {
                case Operation.Nop:
                    break;

                case Operation.Load:
                    if (instruction.Parameters[0].Type == ParameterType.Label)
                    {
                        throw new InvalidOperationException();
                    }

                    if (instruction.Destination < 0)
                    {
                        throw new InvalidOperationException();
                    }

                    temporaryObject = this.Load(register, instruction.Parameters[0], currentContext);
                    break;

                case Operation.Store:
                    if (instruction.Parameters[0].Type != ParameterType.Register)
                    {
                        throw new InvalidOperationException();
                    }

                    if (instruction.Parameters[1].Type != ParameterType.Reference)
                    {
                        throw new InvalidOperationException();
                    }

                    x = this.Load(register, instruction.Parameters[0], currentContext);
                    Store(x, (Reference)instruction.Parameters[1].Value, currentContext);
                    break;

                case Operation.Scope:
                    currentContext = new ProgramContext(currentContext);
                    break;

                case Operation.Break:
                    if (currentContext.Parent == null)
                    {
                        throw new InvalidOperationException();
                    }

                    currentContext = currentContext.Parent;
                    break;

                case Operation.Inc:
                    if (instruction.Parameters[0].Type != ParameterType.Register)
                    {
                        throw new InvalidOperationException();
                    }

                    temporaryObject = this.CallUnaryOperator(OperatorInc, register, instruction.Parameters[0], currentContext);
                    break;

                case Operation.Dec:
                    if (instruction.Parameters[0].Type != ParameterType.Register)
                    {
                        throw new InvalidOperationException();
                    }

                    temporaryObject = this.CallUnaryOperator(OperatorDec, register, instruction.Parameters[0], currentContext);
                    break;

                case Operation.Pos:
                    temporaryObject = this.CallUnaryOperator(OperatorPos, register, instruction.Parameters[0], currentContext);
                    break;

                case Operation.Neg:
                    temporaryObject = this.CallUnaryOperator(OperatorNeg, register, instruction.Parameters[0], currentContext);
                    break;

                case Operation.Inv:
                    temporaryObject = this.CallUnaryOperator(OperatorInv, register, instruction.Parameters[0], currentContext);
                    break;

                case Operation.Pow:
                    temporaryObject = this.CallBinaryOperator(OperatorPow, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Mul:
                    temporaryObject = this.CallBinaryOperator(OperatorMul, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Div:
                    temporaryObject = this.CallBinaryOperator(OperatorDiv, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Idiv:
                    temporaryObject = this.CallBinaryOperator(OperatorIDiv, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Mod:
                    temporaryObject = this.CallBinaryOperator(OperatorMod, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Add:
                    temporaryObject = this.CallBinaryOperator(OperatorAdd, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Sub:
                    temporaryObject = this.CallBinaryOperator(OperatorSub, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Con:
                    temporaryObject = this.CallBinaryOperator(OperatorCon, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Shl:
                    temporaryObject = this.CallBinaryOperator(OperatorLShift, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Shr:
                    temporaryObject = this.CallBinaryOperator(OperatorRShift, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.And:
                    temporaryObject = this.CallBinaryOperator(OperatorAnd, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Xor:
                    temporaryObject = this.CallBinaryOperator(OperatorXor, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Or:
                    temporaryObject = this.CallBinaryOperator(OperatorOr, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Lt:
                    temporaryObject = this.CallBinaryOperator(OperatorLt, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Gt:
                    temporaryObject = this.CallBinaryOperator(OperatorGt, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Ltq:
                    temporaryObject = this.CallBinaryOperator(OperatorLtq, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Gtq:
                    temporaryObject = this.CallBinaryOperator(OperatorGtq, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Eq:
                    temporaryObject = this.CallBinaryOperator(OperatorEq, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Neq:
                    temporaryObject = this.CallBinaryOperator(OperatorNe, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Is:
                    throw new NotImplementedException();

                case Operation.Isn:
                    throw new NotImplementedException();

                case Operation.In:
                    temporaryObject = this.CallBinaryOperator(OperatorIn, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.NotIn:
                    temporaryObject = this.CallBinaryOperator(OperatorNotIn, register, instruction.Parameters[0], instruction.Parameters[1], currentContext);
                    break;

                case Operation.Not:
                    temporaryObject = this.CallUnaryOperator(OperatorNot, register, instruction.Parameters[0], currentContext);
                    break;

                case Operation.Ret:
                    if (instruction.Parameters.Count == 0)
                    {
                        return(LuryObject.Nil);
                    }
                    else
                    {
                        return(this.Load(register, instruction.Parameters[0], currentContext));
                    }

                case Operation.Yield:
                    throw new NotImplementedException();

                case Operation.Throw:
                    throw new NotImplementedException();

                case Operation.Call:
                    throw new NotImplementedException();

                case Operation.Eval:
                    throw new NotImplementedException();

                case Operation.Jmp:
                    i = routine.JumpLabels[(string)instruction.Parameters[0].Value] - 1;
                    break;

                case Operation.Jmpt:
                    if (this.Load(register, instruction.Parameters[0], currentContext) == IntrinsicBoolean.True)
                    {
                        i = routine.JumpLabels[(string)instruction.Parameters[1].Value] - 1;
                    }
                    break;

                case Operation.Jmpf:
                    if (this.Load(register, instruction.Parameters[0], currentContext) == IntrinsicBoolean.False)
                    {
                        i = routine.JumpLabels[(string)instruction.Parameters[1].Value] - 1;
                    }
                    break;

                case Operation.Jmpn:
                    if (this.Load(register, instruction.Parameters[0], currentContext) == LuryObject.Nil)
                    {
                        i = routine.JumpLabels[(string)instruction.Parameters[1].Value] - 1;
                    }
                    break;

                case Operation.Catch:
                    throw new NotImplementedException();

                case Operation.Ovlok:
                    throw new NotImplementedException();

                case Operation.Func:
                    throw new NotImplementedException();

                case Operation.Class:
                    throw new NotImplementedException();

                case Operation.Annot:
                    throw new NotImplementedException();

                default:
                    throw new ArgumentException();
                }

                if (instruction.Destination >= 0)
                {
                    if (temporaryObject == null)
                    {
                        throw new ArgumentException();
                    }

                    register[instruction.Destination] = temporaryObject;
                }
            }

            return(LuryObject.Nil);
        }