On 30.11.2005 07:24, "Maciej Stachowiak" <[EMAIL PROTECTED]> wrote:

> I plan to integrate this soon. Any thoughts?

  Does gcc support C++0x move semantics? With CodeWarrior, it gave me
measurably better performance than PassRefPtr.

- WBR, Alexey Proskuryakov

Attachment: reftest3.cpp
Description: application/applefile

// -*- mode: c++; c-basic-offset: 4 -*-

#pragma rvalue_refs on  // must turn language feature on
#include <stdio.h>
#include <memory>

struct RefCounter {
    RefCounter() : m_refcount(0) {}
    void ref() { ++m_refcount; }
    void deref() { if (!--m_refcount) delete this; }
    int m_refcount;
};

template <class T> class PassRefPtr;
template <class T> class PassRefPtr_ref;

template <class T> class SharedPtr
{
public:
    SharedPtr() : m_ptr(0) {}
    SharedPtr(T *ptr) : m_ptr(ptr) { if (ptr) ptr->ref(); }
    SharedPtr(const SharedPtr& o) : m_ptr(o.get()) { if (m_ptr) m_ptr->ref(); }
    SharedPtr(SharedPtr&& o) : m_ptr(o.get()) { o.m_ptr = 0; }
    SharedPtr(PassRefPtr<T>& o) : m_ptr(o.release()) {}
    ~SharedPtr() { if (m_ptr) m_ptr->deref(); }
    
    template <class U> SharedPtr(const SharedPtr<U> &o) : m_ptr(o.get()) { if 
(T *ptr = m_ptr) ptr->ref(); }
    template <class U> SharedPtr(PassRefPtr<U> &o) : m_ptr(o.release()) { }
        
    // FIXME: Deprecate in favor of operators below, then remove?
    bool isNull() const { return m_ptr == 0; }
    bool notNull() const { return m_ptr != 0; }
    
    // FIXME: Deprecate in favor of operator=, then remove?
    void reset() { if (T *ptr = m_ptr) ptr->deref(); m_ptr = NULL; }
        void reset(T *o) { if (o) o->ref(); if (T *ptr = m_ptr) ptr->deref(); 
m_ptr = o; }
    
    T *get() const { return m_ptr; }
    
    T &operator*() const { return *m_ptr; }
    T *operator->() const { return m_ptr; }
    
    bool operator!() const { return m_ptr == 0; }
    operator bool() const { return m_ptr != 0; }
    
    SharedPtr &operator=(const SharedPtr &);
    SharedPtr &operator=(T *);
    SharedPtr &operator=(SharedPtr&& o) { std::swap(m_ptr, o.m_ptr); return 
*this; }

    SharedPtr<T> &operator=(PassRefPtr<T> &o);
    
    SharedPtr(PassRefPtr_ref<T> ref)
        : m_ptr(ref.m_ptr) { }
      
    SharedPtr& operator=(PassRefPtr_ref<T> ref)
    {
        if (m_ptr)
            m_ptr->deref();
        m_ptr = ref.m_ptr;
        return *this;
    }
      
private:
    T *m_ptr;
    
    operator int() const; // deliberately not implemented; helps prevent 
operator bool from converting to int accidentally
};

template <class T> inline SharedPtr<T> &SharedPtr<T>::operator=(const 
SharedPtr<T> &o) 
{
    T *optr = o.m_ptr;
    if (optr)
        optr->ref();
    if (T *ptr = m_ptr)
        ptr->deref();
    m_ptr = optr;
    return *this;
}

template <class T> inline SharedPtr<T> &SharedPtr<T>::operator=(PassRefPtr<T> 
&o) 
{
    T *optr = o.release();
    if (optr)
        optr->ref();
    if (T *ptr = m_ptr)
        ptr->deref();
    m_ptr = optr;
    return *this;
}

template <class T> inline SharedPtr<T> &SharedPtr<T>::operator=(T *optr)
{
    if (optr)
        optr->ref();
    if (T *ptr = m_ptr)
        ptr->deref();
    m_ptr = optr;
    return *this;
}

template <class T> inline bool operator==(const SharedPtr<T> &a, const 
SharedPtr<T> &b) 
{ 
    return a.get() == b.get(); 
}

template <class T> inline bool operator==(const SharedPtr<T> &a, const T *b) 
{ 
    return a.get() == b; 
}

template <class T> inline bool operator==(const T *a, const SharedPtr<T> &b) 
{
    return a == b.get(); 
}

template <class T> inline bool operator!=(const SharedPtr<T> &a, const 
SharedPtr<T> &b) 
{ 
    return a.get() != b.get(); 
}

template <class T> inline bool operator!=(const SharedPtr<T> &a, const T *b)
{
    return a.get() != b; 
}

template <class T> inline bool operator!=(const T *a, const SharedPtr<T> &b) 
{ 
    return a != b.get(); 
}

template <class T, class U> inline SharedPtr<T> static_pointer_cast(const 
SharedPtr<U> &p) 
{ 
    return SharedPtr<T>(static_cast<T *>(p.get())); 
}

template <class T, class U> inline SharedPtr<T> const_pointer_cast(const 
SharedPtr<U> &p) 
{ 
    return SharedPtr<T>(const_cast<T *>(p.get())); 
}

template<class T>
struct PassRefPtr_ref
{
    T* m_ptr;
    
    explicit PassRefPtr_ref(T* p) : m_ptr(p) {}
};


template <class T> class PassRefPtr
{
public:
    PassRefPtr() : m_ptr(0) {}
    PassRefPtr(T *ptr) : m_ptr(ptr) { if (ptr) ptr->ref(); }
    PassRefPtr(const SharedPtr<T> &o) : m_ptr(o.get()) { if (T *ptr = m_ptr) 
ptr->ref(); }

    ~PassRefPtr() { if (T *ptr = m_ptr) ptr->deref(); }
    
    template <class U> PassRefPtr(const SharedPtr<U> &o) : m_ptr(o.get()) { if 
(T *ptr = m_ptr) ptr->ref(); }
    template <class U> PassRefPtr(PassRefPtr<U> &o) : m_ptr(o.release()) { }
        
    // FIXME: Deprecate in favor of operator=, then remove?
    void reset() { if (T *ptr = m_ptr) ptr->deref(); m_ptr = NULL; }
    void reset(T *o) { if (o) o->ref(); if (T *ptr = m_ptr) ptr->deref(); m_ptr 
= o; }
    
    T *get() const { return m_ptr; }

    T *release() { T *tmp = m_ptr; m_ptr = 0; return tmp; }
    
    T &operator*() const { return *m_ptr; }
    T *operator->() const { return m_ptr; }
    
    bool operator!() const { return m_ptr == NULL; }
    operator bool() const { return m_ptr != NULL; }
    
    PassRefPtr &operator=(const SharedPtr<T> &);
    PassRefPtr &operator=(PassRefPtr &);
    PassRefPtr &operator=(T *);

    PassRefPtr(PassRefPtr_ref<T> ref)
        : m_ptr(ref.m_ptr) { }
      
    PassRefPtr& operator=(PassRefPtr_ref<T> ref)
    {
        if (m_ptr)
            m_ptr->deref();
        m_ptr = ref.m_ptr;
        return *this;
    }
      
    template<typename U>
    operator PassRefPtr_ref<U>()
    { 
        return PassRefPtr_ref<U>(release()); 
    }

    template<typename U>
    operator PassRefPtr<U>()
    { 
        return PassRefPtr<U>(this->release()); 
    }
    
private:
    T *m_ptr;
    
    operator int() const; // deliberately not implemented; helps prevent 
operator bool from converting to int accidentally
};

template <class T> inline PassRefPtr<T> &PassRefPtr<T>::operator=(const 
SharedPtr<T> &o) 
{
    T *optr = o.get();
    if (optr)
        optr->ref();
    if (T *ptr = m_ptr)
        ptr->deref();
    m_ptr = optr;
    return *this;
}

template <class T> inline PassRefPtr<T> &PassRefPtr<T>::operator=(PassRefPtr<T> 
&o) 
{
    T *optr = o.release();
    if (T *ptr = m_ptr)
        ptr->deref();
    m_ptr = optr;
    return *this;
}

template <class T> inline PassRefPtr<T> &PassRefPtr<T>::operator=(T *optr)
{
    if (optr)
        optr->ref();
    if (T *ptr = m_ptr)
        ptr->deref();
    m_ptr = optr;
    return *this;
}

class Acceptor {
public:
    Acceptor(SharedPtr<RefCounter> &&s) : m_s(std::move(s)){}
    SharedPtr<RefCounter> m_s;
};

SharedPtr<RefCounter> getRefCounter();

inline SharedPtr<RefCounter> getRefCounter()
{
    return SharedPtr<RefCounter>(new RefCounter);
}

int main()
{
    for (int i = 0; i < 10000000; i++) {
        Acceptor a(getRefCounter());
    }
}

_______________________________________________
webkit-dev mailing list
[email protected]
http://www.opendarwin.org/mailman/listinfo/webkit-dev

Reply via email to