sharedptr.h
iostream
AssociationBase.h
sharedptr.h
iostream
AssociationBase.h
Association.h
Dialog_Preferences.h
bakery.h
sharedptr.h
Client.h
Bakery::sharedptr
Bakery

    /*
    *Copyright2004MurrayCumming
    *
    *Thislibraryisfreesoftware;youcanredistributeitand/or
    *modifyitunderthetermsoftheGNULibraryGeneralPublic
    *LicenseaspublishedbytheFreeSoftwareFoundation;either
    *version2oftheLicense,or(atyouroption)anylaterversion.
    *
    *Thislibraryisdistributedinthehopethatitwillbeuseful,
    *butWITHOUTANYWARRANTY;withouteventheimpliedwarrantyof
    *MERCHANTABILITYorFITNESSFORAPARTICULARPURPOSE.SeetheGNU
    *LibraryGeneralPublicLicenseformoredetails.
    *
    *YoushouldhavereceivedacopyoftheGNULibraryGeneralPublic
    *Licensealongwiththislibrary;ifnot,writetotheFree
    *SoftwareFoundation,Inc.,675MassAve,Cambridge,MA02139,USA.
    */

    #ifndefBAKERY_UTILITIES_SHAREDPTR_H
    #defineBAKERY_UTILITIES_SHAREDPTR_H

    #include<iostream>//Justfordebugging.

    namespaceBakery
    {

    template<typenameT_obj>
    classsharedptr
    {
    public:
    typedefsize_tsize_type;

    sharedptr();

    explicitsharedptr(T_obj*pobj);

    sharedptr(constsharedptr&src);

    sharedptr&operator=(constsharedptr&src);

    virtual~sharedptr();

    inlineT_obj&operator*();

    inlineconstT_obj&operator*()const;

    inlineT_obj*operator->()const;

    inlineoperator bool()const;

    inlineT_obj*obj();

    inlineconstT_obj*obj()const;

    protected:
    inlinevoidref();
    inlinevoidunref();

    size_type*m_pRefCount;//Sharedbetweeninstances,bycopying.
    T_obj*m_pobj;//Theunderlyinginstance.
    };

    template<typenameT_obj>
    sharedptr<T_obj>::sharedptr()
    :m_pRefCount(0),m_pobj(0)
    {

    }

    template<typenameT_obj>
    sharedptr<T_obj>::sharedptr(T_obj*pobj)
    :m_pRefCount(0),m_pobj(pobj)
    {
    //Startrefcounting:
    ref();
    }

    template<typenameT_obj>
    sharedptr<T_obj>::sharedptr(constsharedptr<T_obj>&src)
    :m_pRefCount(src.m_pRefCount),m_pobj(src.m_pobj)
    {
    ref();
    }

    template<typenameT_obj>
    sharedptr<T_obj>&sharedptr<T_obj>::operator=(constsharedptr<T_obj>&src)
    {
    //std::cout<<"sharedptr&operator=(constsharedptr&src)"<<std::endl;
    if(&src!=this)
    {
    //Unrefanyexistingstuff.
    //operator=canneverrunbeforeaconstructor,sothesevalueswillbeinitializedalready.
    if(m_pobj)//Theif()mightnotberequired.
    {
    unref();//Couldcauseadeallocation.
    }

    //Copy:
    m_pobj=src.m_pobj;

    m_pRefCount=src.m_pRefCount;
    ref();
    }

    return*this;
    }

    template<typenameT_obj>
    sharedptr<T_obj>::~sharedptr()
    {
    unref();
    }

    /*
    template<typenameT_obj>
    voidsharedptr<T_obj>::clear_without_deallocating()
    {
    m_pobj=0;
    }
    */

    template<typenameT_obj>
    inline
    T_obj*sharedptr<T_obj>::obj()
    {
    returnm_pobj;
    }

    template<typenameT_obj>
    inline
    constT_obj*sharedptr<T_obj>::obj()const
    {
    returnm_pobj;
    }

    template<typenameT_obj>
    inline
    T_obj&sharedptr<T_obj>::operator*()
    {
    return*m_pobj;
    }

    template<typenameT_obj>
    inline
    constT_obj&sharedptr<T_obj>::operator*()const
    {
    return*m_pobj;
    }

    template<typenameT_obj>
    inline
    T_obj*sharedptr<T_obj>::operator->()const
    {
    returnm_pobj;
    }

    template<classT_obj>
    inline
    sharedptr<T_obj>::operator bool()const
    {
    return(m_pobj!=0);
    }

    template<classT_obj>
    inline
    voidsharedptr<T_obj>::ref()
    {
    if(m_pobj)//Don'twastetimeoninvalidinstances.Thesewouldbeveryrareanyway,andintentionallycreatedwith(0,0)construction.
    {
    if(m_pRefCount==0)
    {
    //std::cout<<"sharedptr::ref():firstref"<<std::endl;
    //Firstref,soallocatethesharedcount:
    m_pRefCount=newsize_type();
    *m_pRefCount=1;
    }
    else
    {
    //std::cout<<"sharedptr::ref():startingat"<<*m_pRefCount<<std::endl;
    (*m_pRefCount)++;
    }
    }
    }

    template<classT_obj>
    inline
    voidsharedptr<T_obj>::unref()
    {
    if(m_pRefCount)
    {
    //std::cout<<"sharedptr::unref():startingat"<<*m_pRefCount<<std::endl;

    if((*m_pRefCount)>0)
    (*m_pRefCount)--;

    //Unallocifthisisthelastuseroftheobj:
    if(*m_pRefCount==0)
    {
    if(m_pobj)
    {
    //try
    //{
    //std::cout<<"sharedptr::unref():deallocating"<<*m_pRefCount<<std::endl;
    deletem_pobj;
    m_pobj=0;
    //}
    /*
    catch(ex_base&)
    {
    //std::cout<<"sharedptr::unref():exceptionthrownduringdeallocation."<<std::endl;
    //Ignoreit.Can'tthrowanexpectionuptothedestructor.
    }
    */

    m_pobj=0;
    }

    //Clearrefcount:
    deletem_pRefCount;
    m_pRefCount=0;
    }
    }
    else
    {
    //std::cout<<"sharedptr::unref():refnotsetup."<<std::endl;
    }

    }

    }//namespace

    #endif//BAKERY_UTILITIES_SHAREDPTR_H