// // Cforall Version 1.0.0 Copyright (C) 2015 University of Waterloo // // The contents of this file are covered under the licence agreement in the // file "LICENCE" distributed with Cforall. // // FindOpenVars.cc -- // // Author : Richard C. Bilson // Created On : Sun May 17 09:42:48 2015 // Last Modified By : Peter A. Buhr // Last Modified On : Sun May 17 09:45:25 2015 // Update Count : 3 // #include "FindOpenVars.h" #include // for _List_const_iterator, list<>::const... #include // for map<>::mapped_type #include "AST/Pass.hpp" #include "AST/Type.hpp" #include "Common/PassVisitor.h" #include "SynTree/Declaration.h" // for TypeDecl, DeclarationWithType (ptr ... #include "SynTree/Type.h" // for Type, Type::ForallList, ArrayType namespace ResolvExpr { struct FindOpenVars_old : public WithGuards { FindOpenVars_old( OpenVarSet &openVars, OpenVarSet &closedVars, AssertionSet &needAssertions, AssertionSet &haveAssertions, bool firstIsOpen ); void previsit( PointerType * pointerType ); void previsit( ArrayType * arrayType ); void previsit( FunctionType * functionType ); void previsit( TupleType * tupleType ); void common_action( Type *type ); OpenVarSet &openVars, &closedVars; AssertionSet &needAssertions, &haveAssertions; bool nextIsOpen; }; void findOpenVars( Type *type, OpenVarSet &openVars, OpenVarSet &closedVars, AssertionSet &needAssertions, AssertionSet &haveAssertions, bool firstIsOpen ) { PassVisitor finder( openVars, closedVars, needAssertions, haveAssertions, firstIsOpen ); type->accept( finder ); } FindOpenVars_old::FindOpenVars_old( OpenVarSet &openVars, OpenVarSet &closedVars, AssertionSet &needAssertions, AssertionSet &haveAssertions, bool firstIsOpen ) : openVars( openVars ), closedVars( closedVars ), needAssertions( needAssertions ), haveAssertions( haveAssertions ), nextIsOpen( firstIsOpen ) { } void FindOpenVars_old::common_action( Type *type ) { if ( nextIsOpen ) { for ( Type::ForallList::const_iterator i = type->get_forall().begin(); i != type->get_forall().end(); ++i ) { openVars[ (*i)->get_name() ] = TypeDecl::Data{ (*i) }; for ( std::list< DeclarationWithType* >::const_iterator assert = (*i)->get_assertions().begin(); assert != (*i)->get_assertions().end(); ++assert ) { needAssertions[ *assert ].isUsed = false; } /// cloneAll( (*i)->get_assertions(), needAssertions ); /// needAssertions.insert( needAssertions.end(), (*i)->get_assertions().begin(), (*i)->get_assertions().end() ); } } else { for ( Type::ForallList::const_iterator i = type->get_forall().begin(); i != type->get_forall().end(); ++i ) { closedVars[ (*i)->get_name() ] = TypeDecl::Data{ (*i) }; for ( std::list< DeclarationWithType* >::const_iterator assert = (*i)->get_assertions().begin(); assert != (*i)->get_assertions().end(); ++assert ) { haveAssertions[ *assert ].isUsed = false; } /// cloneAll( (*i)->get_assertions(), haveAssertions ); /// haveAssertions.insert( haveAssertions.end(), (*i)->get_assertions().begin(), (*i)->get_assertions().end() ); } // for } // if /// std::cerr << "type is "; /// type->print( std::cerr ); /// std::cerr << std::endl << "need is" << std::endl; /// printAssertionSet( needAssertions, std::cerr ); /// std::cerr << std::endl << "have is" << std::endl; /// printAssertionSet( haveAssertions, std::cerr ); } void FindOpenVars_old::previsit(PointerType *pointerType) { common_action( pointerType ); } void FindOpenVars_old::previsit(ArrayType *arrayType) { common_action( arrayType ); } void FindOpenVars_old::previsit(FunctionType *functionType) { common_action( functionType ); nextIsOpen = ! nextIsOpen; GuardAction( [this](){ nextIsOpen = ! nextIsOpen; } ); } void FindOpenVars_old::previsit(TupleType *tupleType) { common_action( tupleType ); } namespace { struct FindOpenVars_new final : public ast::WithGuards { ast::OpenVarSet & open; ast::OpenVarSet & closed; ast::AssertionSet & need; ast::AssertionSet & have; bool nextIsOpen; FindOpenVars_new( ast::OpenVarSet & o, ast::OpenVarSet & c, ast::AssertionSet & n, ast::AssertionSet & h, FirstMode firstIsOpen ) : open( o ), closed( c ), need( n ), have( h ), nextIsOpen( firstIsOpen ) {} void previsit( const ast::FunctionType * type ) { // mark open/closed variables if ( nextIsOpen ) { for ( const ast::TypeDecl * decl : type->forall ) { open[ decl->name ] = ast::TypeDecl::Data{ decl }; for ( const ast::DeclWithType * assert : decl->assertions ) { need[ assert ].isUsed = false; } } } else { for ( const ast::TypeDecl * decl : type->forall ) { closed[ decl->name ] = ast::TypeDecl::Data{ decl }; for ( const ast::DeclWithType * assert : decl->assertions ) { have[ assert ].isUsed = false; } } } // flip open variables for contained function types nextIsOpen = ! nextIsOpen; GuardAction( [this](){ nextIsOpen = ! nextIsOpen; } ); } }; } void findOpenVars( const ast::Type * type, ast::OpenVarSet & open, ast::OpenVarSet & closed, ast::AssertionSet & need, ast::AssertionSet & have, FirstMode firstIsOpen ) { ast::Pass< FindOpenVars_new > finder{ open, closed, need, have, firstIsOpen }; type->accept( finder ); } } // namespace ResolvExpr // Local Variables: // // tab-width: 4 // // mode: c++ // // compile-command: "make install" // // End: //