Changeset 235b41f for src/SymTab


Ignore:
Timestamp:
Sep 5, 2017, 3:41:04 PM (9 years ago)
Author:
Thierry Delisle <tdelisle@…>
Branches:
ADT, aaron-thesis, arm-eh, ast-experimental, cleanup-dtors, deferred_resn, demangler, enum, forall-pointer-decay, jacob/cs343-translation, jenkins-sandbox, master, new-ast, new-ast-unique-expr, new-env, no_list, persistent-indexer, pthread-emulation, qualifiedEnum, resolv-new, stuck-waitfor-destruct, with_gc
Children:
416cc86
Parents:
800d275 (diff), 3f8dd01 (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the (diff) links above to see all the changes relative to each parent.
Message:

Merge branch 'master' of plg.uwaterloo.ca:software/cfa/cfa-cc

Location:
src/SymTab
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • src/SymTab/Indexer.cc

    r800d275 r235b41f  
    398398        void Indexer::visit( LabelAddressExpr *labAddressExpr ) {
    399399                acceptNewScope( labAddressExpr->get_result(), *this );
    400                 maybeAccept( labAddressExpr->get_arg(), *this );
    401400        }
    402401
     
    554553
    555554
    556         void Indexer::visit( TraitInstType *contextInst ) {
    557                 acceptAll( contextInst->get_parameters(), *this );
    558                 acceptAll( contextInst->get_members(), *this );
     555        void Indexer::visit( TraitInstType *traitInst ) {
     556                acceptAll( traitInst->get_parameters(), *this );
    559557        }
    560558
  • src/SymTab/Validate.cc

    r800d275 r235b41f  
    127127          public:
    128128                LinkReferenceToTypes( bool doDebug, const Indexer *indexer );
    129                 using Parent::visit;
     129                using Parent::visit;
     130                void visit( TypeInstType *typeInst ) final;
     131
    130132                void visit( EnumInstType *enumInst ) final;
    131133                void visit( StructInstType *structInst ) final;
    132134                void visit( UnionInstType *unionInst ) final;
    133                 void visit( TraitInstType *contextInst ) final;
     135                void visit( TraitInstType *traitInst ) final;
     136
    134137                void visit( EnumDecl *enumDecl ) final;
    135138                void visit( StructDecl *structDecl ) final;
    136139                void visit( UnionDecl *unionDecl ) final;
    137                 void visit( TypeInstType *typeInst ) final;
     140                void visit( TraitDecl * traitDecl ) final;
     141
    138142          private:
    139143                const Indexer *indexer;
     
    240244        };
    241245
     246        struct LabelAddressFixer final : public WithGuards {
     247                std::set< Label > labels;
     248
     249                void premutate( FunctionDecl * funcDecl );
     250                Expression * postmutate( AddressExpr * addrExpr );
     251        };
    242252
    243253        FunctionDecl * dereferenceOperator = nullptr;
     
    253263                PassVisitor<ValidateGenericParameters> genericParams;
    254264                PassVisitor<FindSpecialDeclarations> finder;
     265                PassVisitor<LabelAddressFixer> labelAddrFixer;
    255266
    256267                EliminateTypedef::eliminateTypedef( translationUnit );
     
    270281                ArrayLength::computeLength( translationUnit );
    271282                acceptAll( translationUnit, finder );
     283                mutateAll( translationUnit, labelAddrFixer );
    272284        }
    273285
     
    287299
    288300        HoistStruct::HoistStruct() : inStruct( false ) {
    289         }
    290 
    291         void filter( std::list< Declaration * > &declList, bool (*pred)( Declaration * ), bool doDelete ) {
    292                 std::list< Declaration * >::iterator i = declList.begin();
    293                 while ( i != declList.end() ) {
    294                         std::list< Declaration * >::iterator next = i;
    295                         ++next;
    296                         if ( pred( *i ) ) {
    297                                 if ( doDelete ) {
    298                                         delete *i;
    299                                 } // if
    300                                 declList.erase( i );
    301                         } // if
    302                         i = next;
    303                 } // while
    304301        }
    305302
     
    453450        }
    454451
    455         void LinkReferenceToTypes::visit( TraitInstType *traitInst ) {
     452        template< typename Decl >
     453        void normalizeAssertions( std::list< Decl * > & assertions ) {
     454                // ensure no duplicate trait members after the clone
     455                auto pred = [](Decl * d1, Decl * d2) {
     456                        // only care if they're equal
     457                        DeclarationWithType * dwt1 = dynamic_cast<DeclarationWithType *>( d1 );
     458                        DeclarationWithType * dwt2 = dynamic_cast<DeclarationWithType *>( d2 );
     459                        if ( dwt1 && dwt2 ) {
     460                                if ( dwt1->get_name() == dwt2->get_name() && ResolvExpr::typesCompatible( dwt1->get_type(), dwt2->get_type(), SymTab::Indexer() ) ) {
     461                                        // std::cerr << "=========== equal:" << std::endl;
     462                                        // std::cerr << "d1: " << d1 << std::endl;
     463                                        // std::cerr << "d2: " << d2 << std::endl;
     464                                        return false;
     465                                }
     466                        }
     467                        return d1 < d2;
     468                };
     469                std::set<Decl *, decltype(pred)> unique_members( assertions.begin(), assertions.end(), pred );
     470                // if ( unique_members.size() != assertions.size() ) {
     471                //      std::cerr << "============different" << std::endl;
     472                //      std::cerr << unique_members.size() << " " << assertions.size() << std::endl;
     473                // }
     474
     475                std::list< Decl * > order;
     476                order.splice( order.end(), assertions );
     477                std::copy_if( order.begin(), order.end(), back_inserter( assertions ), [&]( Decl * decl ) {
     478                        return unique_members.count( decl );
     479                });
     480        }
     481
     482        // expand assertions from trait instance, performing the appropriate type variable substitutions
     483        template< typename Iterator >
     484        void expandAssertions( TraitInstType * inst, Iterator out ) {
     485                assertf( inst->baseTrait, "Trait instance not linked to base trait: %s", toString( inst ).c_str() );
     486                std::list< DeclarationWithType * > asserts;
     487                for ( Declaration * decl : inst->baseTrait->members ) {
     488                        asserts.push_back( safe_dynamic_cast<DeclarationWithType *>( decl->clone() ) );
     489                }
     490                // substitute trait decl parameters for instance parameters
     491                applySubstitution( inst->baseTrait->parameters.begin(), inst->baseTrait->parameters.end(), inst->parameters.begin(), asserts.begin(), asserts.end(), out );
     492        }
     493
     494        void LinkReferenceToTypes::visit( TraitDecl * traitDecl ) {
     495                Parent::visit( traitDecl );
     496
     497                if ( traitDecl->name == "sized" ) {
     498                        // "sized" is a special trait - flick the sized status on for the type variable
     499                        assertf( traitDecl->parameters.size() == 1, "Built-in trait 'sized' has incorrect number of parameters: %zd", traitDecl->parameters.size() );
     500                        TypeDecl * td = traitDecl->parameters.front();
     501                        td->set_sized( true );
     502                }
     503
     504                // move assertions from type parameters into the body of the trait
     505                for ( TypeDecl * td : traitDecl->parameters ) {
     506                        for ( DeclarationWithType * assert : td->assertions ) {
     507                                if ( TraitInstType * inst = dynamic_cast< TraitInstType * >( assert->get_type() ) ) {
     508                                        expandAssertions( inst, back_inserter( traitDecl->members ) );
     509                                } else {
     510                                        traitDecl->members.push_back( assert->clone() );
     511                                }
     512                        }
     513                        deleteAll( td->assertions );
     514                        td->assertions.clear();
     515                } // for
     516        }
     517
     518        void LinkReferenceToTypes::visit( TraitInstType * traitInst ) {
    456519                Parent::visit( traitInst );
    457                 if ( traitInst->get_name() == "sized" ) {
    458                         // "sized" is a special trait with no members - just flick the sized status on for the type variable
    459                         if ( traitInst->get_parameters().size() != 1 ) {
    460                                 throw SemanticError( "incorrect number of trait parameters: ", traitInst );
    461                         }
    462                         TypeExpr * param = safe_dynamic_cast< TypeExpr * > ( traitInst->get_parameters().front() );
    463                         TypeInstType * inst = safe_dynamic_cast< TypeInstType * > ( param->get_type() );
    464                         TypeDecl * decl = inst->get_baseType();
    465                         decl->set_sized( true );
    466                         // since "sized" is special, the next few steps don't apply
    467                         return;
    468                 }
    469 
    470520                // handle other traits
    471                 TraitDecl *traitDecl = indexer->lookupTrait( traitInst->get_name() );
     521                TraitDecl *traitDecl = indexer->lookupTrait( traitInst->name );
    472522                if ( ! traitDecl ) {
    473                         throw SemanticError( "use of undeclared trait " + traitInst->get_name() );
     523                        throw SemanticError( "use of undeclared trait " + traitInst->name );
    474524                } // if
    475525                if ( traitDecl->get_parameters().size() != traitInst->get_parameters().size() ) {
    476526                        throw SemanticError( "incorrect number of trait parameters: ", traitInst );
    477527                } // if
    478 
    479                 for ( TypeDecl * td : traitDecl->get_parameters() ) {
    480                         for ( DeclarationWithType * assert : td->get_assertions() ) {
    481                                 traitInst->get_members().push_back( assert->clone() );
    482                         } // for
    483                 } // for
    484 
    485                 // need to clone members of the trait for ownership purposes
    486                 std::list< Declaration * > members;
    487                 std::transform( traitDecl->get_members().begin(), traitDecl->get_members().end(), back_inserter( members ), [](Declaration * dwt) { return dwt->clone(); } );
    488 
    489                 applySubstitution( traitDecl->get_parameters().begin(), traitDecl->get_parameters().end(), traitInst->get_parameters().begin(), members.begin(), members.end(), back_inserter( traitInst->get_members() ) );
     528                traitInst->baseTrait = traitDecl;
    490529
    491530                // need to carry over the 'sized' status of each decl in the instance
     
    498537                        }
    499538                }
     539                // normalizeAssertions( traitInst->members );
    500540        }
    501541
     
    561601        void forallFixer( Type * func ) {
    562602                for ( TypeDecl * type : func->get_forall() ) {
    563                         std::list< DeclarationWithType * > toBeDone, nextRound;
    564                         toBeDone.splice( toBeDone.end(), type->get_assertions() );
    565                         while ( ! toBeDone.empty() ) {
    566                                 for ( DeclarationWithType * assertion : toBeDone ) {
    567                                         if ( TraitInstType *traitInst = dynamic_cast< TraitInstType * >( assertion->get_type() ) ) {
    568                                                 // expand trait instance into all of its members
    569                                                 for ( Declaration * member : traitInst->get_members() ) {
    570                                                         DeclarationWithType *dwt = safe_dynamic_cast< DeclarationWithType * >( member );
    571                                                         nextRound.push_back( dwt->clone() );
    572                                                 }
    573                                                 delete traitInst;
    574                                         } else {
    575                                                 // pass assertion through
    576                                                 FixFunction fixer;
    577                                                 assertion = assertion->acceptMutator( fixer );
    578                                                 if ( fixer.get_isVoid() ) {
    579                                                         throw SemanticError( "invalid type void in assertion of function ", func );
    580                                                 }
    581                                                 type->get_assertions().push_back( assertion );
    582                                         } // if
    583                                 } // for
    584                                 toBeDone.clear();
    585                                 toBeDone.splice( toBeDone.end(), nextRound );
    586                         } // while
     603                        std::list< DeclarationWithType * > asserts;
     604                        asserts.splice( asserts.end(), type->assertions );
     605                        // expand trait instances into their members
     606                        for ( DeclarationWithType * assertion : asserts ) {
     607                                if ( TraitInstType *traitInst = dynamic_cast< TraitInstType * >( assertion->get_type() ) ) {
     608                                        // expand trait instance into all of its members
     609                                        expandAssertions( traitInst, back_inserter( type->assertions ) );
     610                                        delete traitInst;
     611                                } else {
     612                                        // pass other assertions through
     613                                        type->assertions.push_back( assertion );
     614                                } // if
     615                        } // for
     616                        // apply FixFunction to every assertion to check for invalid void type
     617                        for ( DeclarationWithType *& assertion : type->assertions ) {
     618                                FixFunction fixer;
     619                                assertion = assertion->acceptMutator( fixer );
     620                                if ( fixer.get_isVoid() ) {
     621                                        throw SemanticError( "invalid type void in assertion of function ", func );
     622                                } // if
     623                        } // for
     624                        // normalizeAssertions( type->assertions );
    587625                } // for
    588626        }
     
    752790                CompoundStmt *ret = Mutator::mutate( compoundStmt );
    753791                scopeLevel -= 1;
    754                 std::list< Statement * >::iterator i = compoundStmt->get_kids().begin();
    755                 while ( i != compoundStmt->get_kids().end() ) {
    756                         std::list< Statement * >::iterator next = i+1;
    757                         if ( DeclStmt *declStmt = dynamic_cast< DeclStmt * >( *i ) ) {
     792                // remove and delete decl stmts
     793                filter( compoundStmt->kids, [](Statement * stmt) {
     794                        if ( DeclStmt *declStmt = dynamic_cast< DeclStmt * >( stmt ) ) {
    758795                                if ( dynamic_cast< TypedefDecl * >( declStmt->get_decl() ) ) {
    759                                         delete *i;
    760                                         compoundStmt->get_kids().erase( i );
     796                                        return true;
    761797                                } // if
    762798                        } // if
    763                         i = next;
    764                 } // while
     799                        return false;
     800                }, true);
    765801                typedefNames.endScope();
    766802                return ret;
     
    771807        template<typename AggDecl>
    772808        AggDecl *EliminateTypedef::handleAggregate( AggDecl * aggDecl ) {
    773                 std::list<Declaration *>::iterator it = aggDecl->get_members().begin();
    774                 for ( ; it != aggDecl->get_members().end(); ) {
    775                         std::list< Declaration * >::iterator next = it+1;
    776                         if ( dynamic_cast< TypedefDecl * >( *it ) ) {
    777                                 delete *it;
    778                                 aggDecl->get_members().erase( it );
    779                         } // if
    780                         it = next;
    781                 }
     809                filter( aggDecl->members, isTypedef, true );
    782810                return aggDecl;
    783811        }
     
    957985        }
    958986
     987        struct LabelFinder {
     988                std::set< Label > & labels;
     989                LabelFinder( std::set< Label > & labels ) : labels( labels ) {}
     990                void previsit( Statement * stmt ) {
     991                        for ( Label & l : stmt->labels ) {
     992                                labels.insert( l );
     993                        }
     994                }
     995        };
     996
     997        void LabelAddressFixer::premutate( FunctionDecl * funcDecl ) {
     998                GuardValue( labels );
     999                PassVisitor<LabelFinder> finder( labels );
     1000                funcDecl->accept( finder );
     1001        }
     1002
     1003        Expression * LabelAddressFixer::postmutate( AddressExpr * addrExpr ) {
     1004                // convert &&label into label address
     1005                if ( AddressExpr * inner = dynamic_cast< AddressExpr * >( addrExpr->arg ) ) {
     1006                        if ( NameExpr * nameExpr = dynamic_cast< NameExpr * >( inner->arg ) ) {
     1007                                if ( labels.count( nameExpr->name ) ) {
     1008                                        Label name = nameExpr->name;
     1009                                        delete addrExpr;
     1010                                        return new LabelAddressExpr( name );
     1011                                }
     1012                        }
     1013                }
     1014                return addrExpr;
     1015        }
     1016
    9591017        void FindSpecialDeclarations::previsit( FunctionDecl * funcDecl ) {
    9601018                if ( ! dereferenceOperator ) {
Note: See TracChangeset for help on using the changeset viewer.