Goose  Artifact [1383ab1ba7]

Artifact 1383ab1ba725907c58977fb7c3a31392d53265e349b5e219df640b0a5d26f54e:

  • File bs/builtins/statements/continue.cpp — part of check-in [c2b2425c0c] at 2019-08-26 00:18:30 on branch trunk — Implemented local variable destruction (through the DestroyValue() extension point), and setup proper visibility and lifetime rules for variables declared inside of statements. (user: achavasse size: 1526)

#include "builtins/builtins.h"
#include "parse/parse.h"
#include "precedence.h"
#include "builtins/helpers.h"

using namespace empathy;
using namespace empathy::ir;
using namespace empathy::parse;

namespace empathy::builtins
{
    void SetupContinueStmt( Env& e )
    {
        auto handleContinue = []( Parser& p, uint32_t locationId, uint32_t prec )
        {
            auto& dm = DiagnosticsManager::GetInstance();

            if( p.isInParenExpr() || !p.cfg() || !p.continuableScopeLevels() )
            {
                dm.emitSyntaxErrorMessage( locationId, "the continue statement is not allowed here.", 0 );
                return false;
            }

            if( !p.cfg()->currentBB() || p.cfg()->currentBB()->terminator() )
            {
                DiagnosticsManager::GetInstance().emitSyntaxErrorMessage(
                    locationId, "unreachable code.", 0 );
                p.cfg()->poison();
                return true;
            }

            // Emit cleanups for all live variables in the scopes that we are continuing through.
            p.destroyAllLiveValuesFromContinueScope( p.continuableScopeLevels() );

            p.cfg()->currentBB()->setTerminator( llr::Continue( p.continuableScopeLevels() ) );
            return true;
        };

        Rule r( handleContinue );
        auto ruleVal = ToValue( move( r ) );
        auto ruleTerm = ValueToIRExpr( ruleVal );
        e.storeValue( AppendToVectorTerm( RootIdentity(), TSID( continue ) ), ANYTERM( _ ), ruleTerm );
    }
}