Changeset 699a97d


Ignore:
Timestamp:
Apr 20, 2023, 3:21:09 PM (12 months ago)
Author:
Andrew Beach <ajbeach@…>
Branches:
ADT, ast-experimental, master
Children:
04c78215, b110bcc
Parents:
45e753c
Message:

Added IndexIterator?, which absorbs some functionality of some MemberIterator? types for CurrentObject?.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/ResolvExpr/CurrentObject.cc

    r45e753c r699a97d  
    671671        };
    672672
    673         /// Iterates array types
    674         class ArrayIterator final : public MemberIterator {
     673        /// Iterates over an indexed type:
     674        class IndexIterator : public MemberIterator {
     675        protected:
    675676                CodeLocation location;
    676                 const ArrayType * array = nullptr;
    677                 const Type * base = nullptr;
    678677                size_t index = 0;
    679678                size_t size = 0;
    680                 std::unique_ptr< MemberIterator > memberIter;
    681 
    682                 void setSize( const Expr * expr ) {
    683                         auto res = eval( expr );
    684                         if ( ! res.second ) {
    685                                 SemanticError( location, toString( "Array designator must be a constant expression: ", expr ) );
    686                         }
    687                         size = res.first;
    688                 }
    689 
    690         public:
    691                 ArrayIterator( const CodeLocation & loc, const ArrayType * at ) : location( loc ), array( at ), base( at->base ) {
    692                         PRINT( std::cerr << "Creating array iterator: " << at << std::endl; )
    693                         memberIter.reset( createMemberIterator( loc, base ) );
    694                         if ( at->isVarLen ) {
    695                                 SemanticError( location, at, "VLA initialization does not support @=: " );
    696                         }
    697                         setSize( at->dimension );
    698                 }
     679                std::unique_ptr<MemberIterator> memberIter;
     680        public:
     681                IndexIterator( const CodeLocation & loc, size_t size ) :
     682                        location( loc ), size( size )
     683                {}
    699684
    700685                void setPosition( const Expr * expr ) {
     
    705690                        auto arg = eval( expr );
    706691                        index = arg.first;
    707                         return;
    708692
    709693                        // if ( auto constExpr = dynamic_cast< const ConstantExpr * >( expr ) ) {
     
    735719
    736720                operator bool() const override { return index < size; }
     721        };
     722
     723        /// Iterates over the members of array types:
     724        class ArrayIterator final : public IndexIterator {
     725                const ArrayType * array = nullptr;
     726                const Type * base = nullptr;
     727
     728                size_t getSize( const Expr * expr ) {
     729                        auto res = eval( expr );
     730                        if ( !res.second ) {
     731                                SemanticError( location, toString( "Array designator must be a constant expression: ", expr ) );
     732                        }
     733                        return res.first;
     734                }
     735
     736        public:
     737                ArrayIterator( const CodeLocation & loc, const ArrayType * at ) :
     738                                IndexIterator( loc, getSize( at->dimension) ),
     739                                array( at ), base( at->base ) {
     740                        PRINT( std::cerr << "Creating array iterator: " << at << std::endl; )
     741                        memberIter.reset( createMemberIterator( loc, base ) );
     742                        if ( at->isVarLen ) {
     743                                SemanticError( location, at, "VLA initialization does not support @=: " );
     744                        }
     745                }
    737746
    738747                ArrayIterator & bigStep() override {
     
    873882
    874883                const Type * getNext() final {
    875                         return ( memberIter && *memberIter ) ? memberIter->getType() : nullptr;
     884                        bool hasMember = memberIter && *memberIter;
     885                        return hasMember ? memberIter->getType() : nullptr;
    876886                }
    877887
     
    938948
    939949        /// Iterates across the positions in a tuple:
    940         class TupleIterator final : public MemberIterator {
    941                 CodeLocation location;
     950        class TupleIterator final : public IndexIterator {
    942951                ast::TupleType const * const tuple;
    943                 size_t index = 0;
    944                 size_t size = 0;
    945                 std::unique_ptr<MemberIterator> sub_iter;
    946952
    947953                const ast::Type * typeAtIndex() const {
     
    952958        public:
    953959                TupleIterator( const CodeLocation & loc, const TupleType * type )
    954                 : location( loc ), tuple( type ), size( type->size() ) {
     960                : IndexIterator( loc, type->size() ), tuple( type ) {
    955961                        PRINT( std::cerr << "Creating tuple iterator: " << type << std::endl; )
    956                         sub_iter.reset( createMemberIterator( loc, typeAtIndex() ) );
    957                 }
    958 
    959                 void setPosition( const ast::Expr * expr ) {
    960                         auto arg = eval( expr );
    961                         index = arg.first;
    962                 }
    963 
    964                 void setPosition(
    965                                 std::deque< ptr< Expr > >::const_iterator begin,
    966                                 std::deque< ptr< Expr > >::const_iterator end ) {
    967                         if ( begin == end ) return;
    968 
    969                         setPosition( *begin );
    970                         sub_iter->setPosition( ++begin, end );
    971                 }
    972 
    973                 std::deque< InitAlternative > operator*() const override {
    974                         return first();
    975                 }
    976 
    977                 operator bool() const override {
    978                         return index < size;
     962                        memberIter.reset( createMemberIterator( loc, typeAtIndex() ) );
    979963                }
    980964
    981965                TupleIterator & bigStep() override {
    982966                        ++index;
    983                         sub_iter.reset( index < size ?
     967                        memberIter.reset( index < size ?
    984968                                createMemberIterator( location, typeAtIndex() ) : nullptr );
    985969                        return *this;
     
    987971
    988972                TupleIterator & smallStep() override {
    989                         if ( sub_iter ) {
    990                                 PRINT( std::cerr << "has member iter: " << *sub_iter << std::endl; )
    991                                 sub_iter->smallStep();
    992                                 if ( !sub_iter ) {
     973                        if ( memberIter ) {
     974                                PRINT( std::cerr << "has member iter: " << *memberIter << std::endl; )
     975                                memberIter->smallStep();
     976                                if ( !memberIter ) {
    993977                                        PRINT( std::cerr << "has valid member iter" << std::endl; )
    994978                                        return *this;
     
    1003987
    1004988                const ast::Type * getNext() override {
    1005                         return ( sub_iter && *sub_iter ) ? sub_iter->getType() : nullptr;
     989                        bool hasMember = memberIter && *memberIter;
     990                        return hasMember ? memberIter->getType() : nullptr;
    1006991                }
    1007992
    1008993                std::deque< InitAlternative > first() const override {
    1009994                        PRINT( std::cerr << "first in TupleIterator (" << index << "/" << size << ")" << std::endl; )
    1010                         if ( sub_iter && *sub_iter ) {
    1011                                 std::deque< InitAlternative > ret = sub_iter->first();
     995                        if ( memberIter && *memberIter ) {
     996                                std::deque< InitAlternative > ret = memberIter->first();
    1012997                                for ( InitAlternative & alt : ret ) {
    1013998                                        alt.designation.get_and_mutate()->designators.emplace_front(
Note: See TracChangeset for help on using the changeset viewer.