示例#1
0
文件: AstTry.cs 项目: kayateia/climoo
        /// <summary>
        /// Throws an exception.
        /// </summary>
        /// <param name="thrown">
        /// The object to throw. It's recommended that this be a dictionary with a
        /// "name" parameter at the least.
        /// </param>
        public void throwException( State state, object thrown )
        {
            // We want to have stack traces, so this is necessary... but we also want to
            // throw data objects and not C# objects. So we have to convert back and forth.
            if( !(thrown is CoralException) )
            thrown = new CoralException( thrown );
            var cex = (CoralException)thrown;
            if( cex.trace == null )
            cex.setStackTrace( state );
            thrown = cex.data;

            state.pushAction( new Step( this, st =>
            {
                // We'll want to hold on to the finally runner if there is one. This will
                // let us properly handle nested exceptions.
                Step finallyStep = null;
                st.unwindActions( step => IsTryMarker( step ), this.finallyBlock != null );
                if( this.finallyBlock != null )
                    finallyStep = st.popAction();

                // The except block may have a parameter.
                if( this.exceptIdentifer != null )
                {
                    IScope exceptScope = new ParameterScope( st.scope, new string[] { this.exceptIdentifer } );
                    exceptScope.set( this.exceptIdentifer, thrown );
                    state.pushActionAndScope( new Step( this, a => {}, "except: scope" ), exceptScope );
                }
                this.exceptBlock.run( st );

                if( finallyStep != null )
                {
                    finallyStep.description = "finally block";
                    st.pushAction( finallyStep );
                }
            },
            "throw" )
            );
        }
示例#2
0
文件: AstFor.cs 项目: kayateia/climoo
        public override void run( State state )
        {
            // We execute by first evaluating the loopOver and then pushing one iteration of
            // the loop onto the action stack. Each iteration, if it completes successfully,
            // will push the next on. The array and current index are curried. We also push
            // a for loop marker on so that break works.
            state.pushAction( new Step( this, st =>
            {
            object over = LValue.Deref( st );
            IEnumerable<object> overTyped;
            if( over is List<object> )
                overTyped = (IEnumerable<object>)over;
            else if( over is Dictionary<object,object> )
                overTyped = ((Dictionary<object,object>)over).Keys;
            else
                throw CoralException.GetArg( "Value is not enumerable" );

            IScope forScope = new ParameterScope( st.scope, new string[] { this.loopVariable } );
            state.pushActionAndScope( new Step( this, a => {}, ScopeMarker ), forScope );
            state.scope.set( this.loopVariable, null );

            oneIteration( st, overTyped, 0 );
            } ) );
            this.loopOver.run( state );
        }