public override IElfObject Get(RuntimeContext ctx, string name, IElfObject @this)
        {
            var b = Vault(ctx).GetBranch(name.FromElfIdentifier());
            if (b == null)
            {
                throw new ReferencedBranchDoesNotExistException(Node(ctx), name);
            }
            else
            {
                if (b.IsFov())
                {
                    var eval = Session(ctx).Eval(b);

                    var typeToken = b.GetValue("type").ContentString;
                    var val = typeToken == "percent" ? ((double)eval) * 100 : eval;

                    var obj_t = typeToken.GetTypeFromToken();
                    var obj = (IElfObject)Activator.CreateInstance(obj_t, val);
                    obj.Bind(ctx.VM);
                    return obj;
                }
                else
                {
                    return new ScenarioNode(b);
                }
            }
        }
Ejemplo n.º 2
0
        public NativeCallContext(NativeMethod source, IElfObject @this, params IElfObject[] args) 
        {
            Stack = new Stack<IElfObject>();

            var callScope = new Scope();
            callScope.Add("@this", @this);
            source.FuncDef.Args.Zip(args, callScope.Add);
            Scopes = new Stack<Scope>();
            Scopes.Push(callScope);

            Source = source;
            if (source.FuncDef.Args.Count() != args.Length)
            {
                throw new UnexpectedElfRuntimeException(@this.VM, String.Format(
                   "Fatal error invoking native call '{0}({1})' with args '{2}'. Reason: args count mismatch.",
                   Source.Name, Source.FuncDef.Args.StringJoin(), args.StringJoin()));
            }

            CurrentEvi = 0;
            PrevEvi = -1;
            if (source.Body.IsNullOrEmpty())
            {
                throw new UnexpectedElfRuntimeException(@this.VM, String.Format(
                   "Fatal error invoking native call '{0}'. Reason: empty method body.", Source.Name));
            } 
        }
Ejemplo n.º 3
0
        public override void Set(RuntimeContext ctx, string name, IElfObject value, IElfObject @this)
        {
            var pbag = (PropertyBag)ctx.VM.Context["iactx"];
            if (pbag.ContainsKey(name))
            {
                pbag[name] = @this.VM.Marshaller.Marshal(value);
                return;
            }

            try
            {
                base.Set(ctx, name, value, @this);
            }
            catch (ErroneousScriptRuntimeException e)
            {
                if (e.Type == ElfExceptionType.CannotResolveVariable)
                {
                    pbag.Add(name, @this.VM.Marshaller.Marshal(value));
                }
                else
                {
                    throw;
                }
            }
        }
Ejemplo n.º 4
0
        public override IElfObject Get(RuntimeContext ctx, string name, IElfObject @this)
        {
            var pbag = (PropertyBag)ctx.VM.Context["iactx"];
            if (pbag.ContainsKey(name))
            {
                return @this.VM.Marshaller.Unmarshal(pbag[name]);
            }

            return base.Get(ctx, name, @this);
        }
Ejemplo n.º 5
0
 public override void Declare(RuntimeContext ctx, string name, IElfObject @this)
 {
     if (name.Contains("."))
     {
         throw new ErroneousScriptRuntimeException(ElfExceptionType.DuplicateVariableName, ctx.VM);
     }
     else
     {
         base.Declare(ctx, name, @this);
     }
 }
Ejemplo n.º 6
0
        public override IElfObject Get(RuntimeContext ctx, string name, IElfObject @this)
        {
            var script = (ToyScript)@this.VM.Marshaller.Marshal(@this);
            if (name.Contains("."))
            {
                // release code should feature type check here
                return @this.VM.Marshaller.Unmarshal((double)script[name]);
            }

            return base.Get(ctx, name, @this);
        }
Ejemplo n.º 7
0
        public override void Set(RuntimeContext ctx, string name, IElfObject value, IElfObject @this)
        {
            var script = (ToyScript)@this.VM.Marshaller.Marshal(@this);
            if (script[name] != null)
            {
                // release code should feature type check here
                script[name] = (double)@this.VM.Marshaller.Marshal(value);
                return;
            }

            base.Set(ctx, name, value, @this);
        }
Ejemplo n.º 8
0
 public override void Declare(RuntimeContext ctx, string name, IElfObject @this)
 {
     var pbag = (PropertyBag)ctx.VM.Context["iactx"];
     if (pbag.ContainsKey(name))
     {
         throw new ErroneousScriptRuntimeException(ElfExceptionType.DuplicateVariableName, ctx.VM);
     }
     else
     {
         base.Declare(ctx, name, @this);
     }
 }
Ejemplo n.º 9
0
        public virtual IElfObject Get(RuntimeContext ctx, string name, IElfObject @this)
        {
            var current = ctx.CallStack.Peek();
            foreach(var scope in current.Scopes)
            {
                if (scope.ContainsKey(name))
                {
                    return scope[name];
                }
            }

            throw new ErroneousScriptRuntimeException(ElfExceptionType.CannotResolveVariable, @this.VM);
        }
Ejemplo n.º 10
0
        public virtual void Declare(RuntimeContext ctx, string name, IElfObject @this)
        {
            var current = ctx.CallStack.Peek();
            foreach(var scope in current.Scopes)
            {
                if (scope.ContainsKey(name))
                {
                    throw new ErroneousScriptRuntimeException(ElfExceptionType.DuplicateVariableName, @this.VM);
                }
            }

            current.Scopes.Peek().Add(name, new ElfVoid());
        }
Ejemplo n.º 11
0
        public override IElfObject Get(RuntimeContext ctx, string name, IElfObject @this)
        {
            var node = (ColaNode)ctx.VM.Context["cc_node"];
            var qualifiedName = name.Contains(".") ? name : node.TPath + "." + name;

            var pbag = (ParametersValues)ctx.VM.Context["cc_values"];
            if (pbag.ContainsKey(qualifiedName))
            {
                return @this.VM.Marshaller.Unmarshal(pbag[qualifiedName]);
            }

            return base.Get(ctx, name, @this);
        }
Ejemplo n.º 12
0
 public object Marshal(IElfObject elf)
 {
     if (elf == null)
     {
         return null;
     }
     else
     {
         if (elf is ElfVoid)
         {
             return new ElfVoid();
         }
         else if (elf is ElfScriptDefinedClassInstance)
         {
             return ((ElfScriptDefinedClassInstance)elf).ClrObject;
         }
         else
         {
             var cast = ImplicitCasts.Where(
                 mi => mi.GetParameters()[0].ParameterType.IsAssignableFrom(elf.GetType())).SingleOrDefault();
             if (cast != null)
             {
                 return cast.Invoke(null, new object[] { elf });
             }
             else
             {
                 var valprop = elf.GetType().GetProperty("Val", BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance);
                 if (valprop != null && valprop.CanRead)
                 {
                     return valprop.GetValue(elf, null);
                 }
                 else
                 {
                     throw new NotSupportedException(String.Format(
                         "Elf object '{0}' of type '{1}' is not supported.",
                         elf, elf.GetType()));
                 }
             }
         }
     }
 }
Ejemplo n.º 13
0
        public override void Set(RuntimeContext ctx, string name, IElfObject value, IElfObject @this)
        {
            var node = (ColaNode)ctx.VM.Context["cc_node"];
            var qualifiedName = name.Contains(".") ? name : node.TPath + "." + name;

            var pbag = (ParametersValues)ctx.VM.Context["cc_values"];
            if (pbag.ContainsKey(qualifiedName))
            {
                pbag[qualifiedName] = @this.VM.Marshaller.Marshal(value);
                return;
            }

            try
            {
                base.Set(ctx, name, value, @this);
            }
            catch (ErroneousScriptRuntimeException)
            {
                pbag.Add(new Parameter(qualifiedName), @this.VM.Marshaller.Marshal(value));
                return;
            }
        }
Ejemplo n.º 14
0
        public override void Declare(RuntimeContext ctx, string name, IElfObject @this)
        {
            if (name.Contains("."))
            {
                // todo. is this behavior really unacceptable?
                throw new ErroneousScriptRuntimeException(ElfExceptionType.BadVariableName, ctx.VM);
            }
            else
            {
                var node = (ColaNode)ctx.VM.Context["cc_node"];
                var qualifiedName = name.Contains(".") ? name : node.TPath + "." + name;

                var pbag = (ParametersValues)ctx.VM.Context["cc_values"];
                if (pbag.ContainsKey(qualifiedName))
                {
                    throw new ErroneousScriptRuntimeException(ElfExceptionType.DuplicateVariableName, ctx.VM);
                }
                else
                {
                    base.Declare(ctx, name, @this);
                }
            }
        }
Ejemplo n.º 15
0
        private void ProcessCurrentEvi(NativeCallContext currentFrame, ElfVmInstruction currentEvi)
        {
            // perverted solution, but I really cba to introduce an enum for evis
            // neither I like solution with introduction of visitor
            var @this = Ctx.CallStack.Peek().Scopes.Last()["@this"];
            var scopeResolver = (IScopeResolver)Activator.CreateInstance(@this.Type.ScopeResolver);
            var invocationResolver = (IInvocationResolver)Activator.CreateInstance(@this.Type.InvocationResolver);

            switch (currentEvi.GetType().Name.ToLower())
            {
                case "decl":
                    var decl = (Decl)currentEvi;
                    scopeResolver.Declare(Ctx, decl.Name, @this);
                    ++currentFrame.CurrentEvi;
                    break;

                case "dup":
                    currentFrame.Stack.Push(currentFrame.Stack.Peek());
                    ++currentFrame.CurrentEvi;
                    break;

                case "enter":
                    scopeResolver.EnterScope(Ctx, @this);
                    ++currentFrame.CurrentEvi;
                    break;

                case "invoke":
                    var invoke = (Invoke)currentEvi;
                    var args = new IElfObject[invoke.Argc];
                    for (var i = invoke.Argc - 1; i >= 0; --i)
                        args[i] = currentFrame.Stack.Pop();

                    try {invocationResolver.PrepareCallContext(Ctx, invoke.Name, @this, args);}
                    catch (Exception e)
                    {
                        // that's pretty awful, tho logically correct
                        if (e is ErroneousScriptRuntimeException) throw;
                        throw new UnexpectedRtimplRuntimeException(VM, String.Format(
                            "Fatal runtime error in an Elf thread. VM dump:{0}{1}",
                            Environment.NewLine, VM.DumpAll()), e);
                    }

                    if (Ctx.PendingClrCall != null) ProcessClrCall(Ctx.PendingClrCall);
                    ++currentFrame.CurrentEvi;
                    break;

                case "jf":
                case "jt":
                    var test = currentFrame.Stack.Pop();
                    if (!(test is ElfBoolean))
                    {
                        throw new ErroneousScriptRuntimeException(ElfExceptionType.ConditionNotBoolean, VM);
                    }
                    else
                    {
                        var jf = currentEvi as Jf;
                        var jt = currentEvi as Jt;
                        var jlabel = jf != null ? jf.Label : jt.Label;

                        if ((((ElfBoolean)test).Val) ^ jf != null)
                        {
                            var target = currentFrame.Source.Body
                                .OfType<Label>().Single(b => b.Name == jlabel);
                            currentFrame.CurrentEvi =
                                Array.IndexOf(currentFrame.Source.Body, target);
                        }
                        else
                        {
                            ++currentFrame.CurrentEvi;
                        }
                    }
                    break;

                case "label":
                    ++currentFrame.CurrentEvi;
                    break;

                case "leave":
                    scopeResolver.LeaveScope(Ctx, @this);
                    ++currentFrame.CurrentEvi;
                    break;

                case "pop":
                    currentFrame.Stack.Pop();
                    ++currentFrame.CurrentEvi;
                    break;

                case "popall":
                    currentFrame.Stack.Clear();
                    ++currentFrame.CurrentEvi;
                    break;

                case "popref":
                    var value = currentFrame.Stack.Pop();
                    var popRef = (PopRef)currentEvi;

                    try {scopeResolver.Set(Ctx, popRef.Ref, value, @this);}
                    catch (Exception e)
                    {
                        // that's pretty awful, tho logically correct
                        if (e is ErroneousScriptRuntimeException) throw;
                        throw new UnexpectedRtimplRuntimeException(VM, String.Format(
                            "Fatal runtime error in an Elf thread. VM dump:{0}{1}",
                            Environment.NewLine, VM.DumpAll()), e);
                    }

                    ++currentFrame.CurrentEvi;
                    break;

                case "pushref":
                    var pushRef = (PushRef)currentEvi;

                    IElfObject value2;
                    try { value2 = scopeResolver.Get(Ctx, pushRef.Ref, @this); }
                    catch(Exception e)
                    {
                        // that's pretty awful, tho logically correct
                        if (e is ErroneousScriptRuntimeException) throw;
                        throw new UnexpectedRtimplRuntimeException(VM, String.Format(
                            "Fatal runtime error in an Elf thread. VM dump:{0}{1}",
                            Environment.NewLine, VM.DumpAll()), e);
                    }

                    currentFrame.Stack.Push(value2);
                    ++currentFrame.CurrentEvi;
                    break;

                case "pushval":
                    var pushVal = (PushVal)currentEvi;
                    var value3 = VM.Marshaller.Unmarshal(pushVal.Val);
                    currentFrame.Stack.Push(value3);
                    ++currentFrame.CurrentEvi;
                    break;

                case "ret":
                    var retval = currentFrame.Stack.SingleOrDefault() ?? new ElfVoid();
                    Ctx.CallStack.Pop();
                    if (Ctx.CallStack.Count > 0)
                    {
                        Ctx.CallStack.Peek().Stack.Push(retval);
                    }
                    else
                    {
                        ExecutionResult = retval;
                    }
                    break;

                default:
                    throw new UnexpectedElfRuntimeException(VM, String.Format(
                        "Fatal error executing evi '{0}'. Reason: evi type '{1}' not supported.",
                        currentEvi, currentEvi.GetType()));
            }
        }
 public override void Set(RuntimeContext ctx, string name, IElfObject value, IElfObject @this)
 {
     // todo. temporarily not implemented
 }
Ejemplo n.º 17
0
 public ClrCallContext(ClrMethod source, IElfObject @this, params IElfObject[] args) 
 {
     Source = source;
     This = @this;
     Args = args;
 }
Ejemplo n.º 18
0
 public virtual void LeaveScope(RuntimeContext ctx, IElfObject @this)
 {
     ctx.CallStack.Peek().Scopes.Pop();
 }
Ejemplo n.º 19
0
 public DefaultEntryPoint(NativeMethod codePoint, IElfObject @this, IElfObject[] args)
 {
     CodePoint = codePoint;
     This = @this;
     Args = args;
 }
Ejemplo n.º 20
0
 public virtual void EnterScope(RuntimeContext ctx, IElfObject @this)
 {
     ctx.CallStack.Peek().Scopes.Push(new Scope());
 }
Ejemplo n.º 21
0
 public virtual void PrepareCallContext(RuntimeContext ctx, string name, IElfObject @this, params IElfObject[] args)
 {
     var resolved = Resolve(@this.VM, name, @this.Type, args.Select(arg => arg.Type).ToArray());
     if (resolved == null)
     {
         throw new ErroneousScriptRuntimeException(ElfExceptionType.CannotResolveInvocation, ctx.VM);
     }
     else
     {
         if (resolved is NativeMethod)
         {
             // this class, elf method
             if (resolved.Argc == args.Length)
             {
                 ctx.CallStack.Push(new NativeCallContext(
                     (NativeMethod)resolved, @this, args));
             }
             // other class, elf method as well
             else
             {
                 ctx.CallStack.Push(new NativeCallContext(
                     (NativeMethod)resolved, args[0], args.Skip(1).ToArray()));
             }
         }
         else
         {
             var mi = ((ClrMethod)resolved).Rtimpl;
             if (mi.DeclaringType != @this.Type.ClrType)
             {
                 if (mi.IsConstructor)
                 {
                     // other class, clr ctor
                     ctx.PendingClrCall = new ClrCallContext(
                          (ClrMethod)resolved, null, args);
                 }
                 else if (mi.IsStatic)
                 {
                     // other class, static clr method
                     ctx.PendingClrCall = new ClrCallContext(
                          (ClrMethod)resolved, args[0], args);
                 }
                 else
                 {
                     // other class, instance clr method
                     ctx.PendingClrCall = new ClrCallContext(
                         (ClrMethod)resolved, args[0], args.Skip(1).ToArray());
                 }
             }
             else
             {
                 if (mi.IsStatic)
                 {
                     // this class, static clr method
                     ctx.PendingClrCall = new ClrCallContext(
                          (ClrMethod)resolved, @this, @this.AsArray().Concat(args).ToArray());
                 }
                 else
                 {
                     // this class, instance clr method
                     ctx.PendingClrCall = new ClrCallContext(
                         (ClrMethod)resolved, @this, args);
                 }
             }
         }
     }
 }