Changeset 58fe85a for src/AST/Node.hpp


Ignore:
Timestamp:
Jan 7, 2021, 3:27:00 PM (5 years ago)
Author:
Thierry Delisle <tdelisle@…>
Branches:
ADT, arm-eh, ast-experimental, enum, forall-pointer-decay, jacob/cs343-translation, master, new-ast-unique-expr, pthread-emulation, qualifiedEnum
Children:
2b4daf2, 64aeca0
Parents:
3c64c668 (diff), eef8dfb (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' into park_unpark

File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/AST/Node.hpp

    r3c64c668 r58fe85a  
    1010// Created On       : Wed May 8 10:27:04 2019
    1111// Last Modified By : Andrew Beach
    12 // Last Modified On : Mon Jun  3 13:26:00 2019
    13 // Update Count     : 5
     12// Last Modified On : Fri Jun 5 9:47:00 2020
     13// Update Count     : 6
    1414//
    1515
     
    3838        Node& operator= (const Node&) = delete;
    3939        Node& operator= (Node&&) = delete;
    40         virtual ~Node() = default;
     40        virtual ~Node() {}
    4141
    4242        virtual const Node * accept( Visitor & v ) const = 0;
     
    4949
    5050        bool unique() const { return strong_count == 1; }
     51        bool isManaged() const {return strong_count > 0; }
    5152
    5253private:
     
    5758        template<typename node_t>
    5859        friend node_t * mutate(const node_t * node);
     60        template<typename node_t>
     61        friend node_t * shallowCopy(const node_t * node);
    5962
    6063        mutable size_t strong_count = 0;
     
    6972        }
    7073
    71         void decrement(ast::Node::ref_type ref) const {
     74        void decrement(ast::Node::ref_type ref, bool do_delete = true) const {
    7275                switch (ref) {
    7376                        case ref_type::strong: strong_count--; break;
     
    7578                }
    7679
    77                 if(!strong_count && !weak_count) {
     80                if( do_delete && !strong_count && !weak_count) {
    7881                        delete this;
    7982                }
     
    9497        assertf(
    9598                node->weak_count == 0,
    96                 "Error: mutating node with weak references to it will invalided some references"
     99                "Error: mutating node with weak references to it will invalidate some references"
    97100        );
    98101        return node->clone();
     
    104107        // skip mutate if equivalent
    105108        if ( node->*field == val ) return node;
    106        
     109
    107110        // mutate and return
    108111        node_t * ret = mutate( node );
     
    123126        (ret->*field)[i] = std::forward< field_t >( val );
    124127        return ret;
     128}
     129
     130/// Mutate an entire indexed collection by cloning to accepted value
     131template<typename node_t, typename parent_t, typename coll_t>
     132const node_t * mutate_each( const node_t * node, coll_t parent_t::* field, Visitor & v ) {
     133        for ( unsigned i = 0; i < (node->*field).size(); ++i ) {
     134                node = mutate_field_index( node, field, i, (node->*field)[i]->accept( v ) );
     135        }
     136        return node;
    125137}
    126138
     
    217229        const node_t & operator* () const { _check(); return *node; }
    218230        explicit operator bool() const { _check(); return node; }
    219         operator const node_t * () const { _check(); return node; }
     231        operator const node_t * () const & { _check(); return node; }
     232        operator const node_t * () && = delete;
     233
     234        const node_t * release() {
     235                const node_t * ret = node;
     236                if ( node ) {
     237                        _dec(node, false);
     238                        node = nullptr;
     239                }
     240                return ret;
     241        }
    220242
    221243        /// wrapper for convenient access to dynamic_cast
     
    223245        const o_node_t * as() const { _check(); return dynamic_cast<const o_node_t *>(node); }
    224246
    225         /// wrapper for convenient access to strict_dynamic_cast
     247        /// Wrapper that makes sure dynamic_cast returns non-null.
    226248        template<typename o_node_t>
    227         const o_node_t * strict_as() const { _check(); return strict_dynamic_cast<const o_node_t *>(node); }
     249        const o_node_t * strict_as() const {
     250                if (const o_node_t * ret = as<o_node_t>()) return ret;
     251                _strict_fail();
     252        }
     253
     254        /// Wrapper that makes sure dynamic_cast does not fail.
     255        template<typename o_node_t, decltype(nullptr) null>
     256        const o_node_t * strict_as() const { return node ? strict_as<o_node_t>() : nullptr; }
    228257
    229258        /// Returns a mutable version of the pointer in this node.
     
    244273
    245274        void _inc( const node_t * other );
    246         void _dec( const node_t * other );
     275        void _dec( const node_t * other, bool do_delete = true );
    247276        void _check() const;
     277        void _strict_fail() const __attribute__((noreturn));
    248278
    249279        const node_t * node;
Note: See TracChangeset for help on using the changeset viewer.