]> git.sesse.net Git - casparcg/commitdiff
2.0.0.2:
authorronag <ronag@362d55ac-95cf-4e76-9f9a-cbaa9c17b72d>
Tue, 14 Dec 2010 22:44:37 +0000 (22:44 +0000)
committerronag <ronag@362d55ac-95cf-4e76-9f9a-cbaa9c17b72d>
Tue, 14 Dec 2010 22:44:37 +0000 (22:44 +0000)
 - Further improvements to safe_ptr. Added cast functions and implicit conversion to shared_ptr.

git-svn-id: https://casparcg.svn.sourceforge.net/svnroot/casparcg/server/branches/2.0.0.2@293 362d55ac-95cf-4e76-9f9a-cbaa9c17b72d

common/utility/safe_ptr.h
core/StdAfx.h
core/producer/ffmpeg/video/video_transformer.cpp
core/producer/flash/cg_producer.cpp
core/producer/flash/flash_producer.cpp
core/producer/image/image_producer.cpp
core/producer/transition/transition_producer.cpp
core/protocol/amcp/AMCPProtocolStrategy.cpp

index 93cbc6d7737f89ee42eca8d35a8bbe33b50387f6..9eeb923a4a32bace6c1f4cf165e60e18ce9b8457 100644 (file)
@@ -13,69 +13,69 @@ class safe_ptr
 public:\r
        typedef T element_type;\r
        \r
-       safe_ptr() : impl_(std::make_shared<T>()){static_assert(!std::is_abstract<T>::value, "Cannot construct abstract class.");}      \r
+       safe_ptr() : impl_(std::make_shared<T>()){}     \r
        \r
        safe_ptr(const safe_ptr<T>& other) : impl_(other.impl_){}\r
        \r
-       template<typename Y>\r
-       safe_ptr(const safe_ptr<Y>& other, typename std::enable_if<std::is_convertible<Y*, T*>::value, void*>::type = 0) : impl_(other.impl_){}\r
+       template<typename U>\r
+       safe_ptr(const safe_ptr<U>& other, typename std::enable_if<std::is_convertible<U*, T*>::value, void*>::type = 0) : impl_(other.impl_){}\r
                \r
-       template<typename Y>    \r
-       safe_ptr(const Y& impl, typename std::enable_if<std::is_convertible<typename std::add_pointer<Y>::type, typename std::add_pointer<T>::type>::value, void>::type* = 0)\r
-               : impl_(std::make_shared<Y>(impl)) {}\r
+       template<typename U>    \r
+       safe_ptr(const U& impl, typename std::enable_if<std::is_convertible<typename std::add_pointer<U>::type, typename std::add_pointer<T>::type>::value, void>::type* = 0)\r
+               : impl_(std::make_shared<U>(impl)) {}\r
        \r
-       template<typename Y, typename D>                \r
-       safe_ptr(const Y& impl, D dtor, typename std::enable_if<std::is_convertible<typename std::add_pointer<Y>::type, typename std::add_pointer<T>::type>::value, void>::type* = 0)\r
-               : impl_(new Y(impl), dtor) {}\r
+       template<typename U, typename D>                \r
+       safe_ptr(const U& impl, D dtor, typename std::enable_if<std::is_convertible<typename std::add_pointer<U>::type, typename std::add_pointer<T>::type>::value, void>::type* = 0)\r
+               : impl_(new U(impl), dtor) {}\r
 \r
-       template<typename Y>    \r
-       safe_ptr(Y&& impl, typename std::enable_if<std::is_convertible<typename std::add_pointer<Y>::type, typename std::add_pointer<T>::type>::value, void>::type* = 0)\r
-               : impl_(std::make_shared<Y>(std::forward<Y>(impl))) {}\r
+       template<typename U>    \r
+       safe_ptr(U&& impl, typename std::enable_if<std::is_convertible<typename std::add_pointer<U>::type, typename std::add_pointer<T>::type>::value, void>::type* = 0)\r
+               : impl_(std::make_shared<U>(std::forward<U>(impl))) {}\r
 \r
-       template<typename Y, typename D>        \r
-       safe_ptr(Y&& impl, D dtor, typename std::enable_if<std::is_convertible<typename std::add_pointer<Y>::type, typename std::add_pointer<T>::type>::value, void>::type* = 0)\r
-               : impl_(new Y(std::forward<Y>(impl)), dtor) {}\r
+       template<typename U, typename D>        \r
+       safe_ptr(U&& impl, D dtor, typename std::enable_if<std::is_convertible<typename std::add_pointer<U>::type, typename std::add_pointer<T>::type>::value, void>::type* = 0)\r
+               : impl_(new U(std::forward<U>(impl)), dtor) {}\r
                        \r
-       template<typename Y>    \r
-       explicit safe_ptr(const std::shared_ptr<Y>& impl, typename std::enable_if<std::is_convertible<Y*, T*>::value, void*>::type = 0) : impl_(impl)\r
+       template<typename U>    \r
+       explicit safe_ptr(const std::shared_ptr<U>& impl, typename std::enable_if<std::is_convertible<U*, T*>::value, void*>::type = 0) : impl_(impl)\r
        {\r
                if(!impl_)\r
                        throw std::invalid_argument("impl");\r
        }\r
        \r
-       template<typename Y>    \r
-       explicit safe_ptr(std::shared_ptr<Y>&& impl, typename std::enable_if<std::is_convertible<Y*, T*>::value, void*>::type = 0) : impl_(std::move(impl))\r
+       template<typename U>    \r
+       explicit safe_ptr(std::shared_ptr<U>&& impl, typename std::enable_if<std::is_convertible<U*, T*>::value, void*>::type = 0) : impl_(std::move(impl))\r
        {\r
                if(!impl_)\r
                        throw std::invalid_argument("impl");\r
        }\r
 \r
-       template<typename Y>    \r
-       explicit safe_ptr(Y* impl, typename std::enable_if<std::is_convertible<Y*, T*>::value, void*>::type = 0) : impl_(impl)\r
+       template<typename U>    \r
+       explicit safe_ptr(U* impl, typename std::enable_if<std::is_convertible<U*, T*>::value, void*>::type = 0) : impl_(impl)\r
        {\r
                if(!impl_)\r
                        throw std::invalid_argument("impl");\r
        }\r
 \r
-       template<typename Y, typename D>        \r
-       explicit safe_ptr(Y* impl, D dtor, typename std::enable_if<std::is_convertible<Y*, T*>::value, void*>::type = 0) : impl_(impl, dtor)\r
+       template<typename U, typename D>        \r
+       explicit safe_ptr(U* impl, D dtor, typename std::enable_if<std::is_convertible<U*, T*>::value, void*>::type = 0) : impl_(impl, dtor)\r
        {\r
                if(!impl_)\r
                        throw std::invalid_argument("impl");\r
        }\r
 \r
-       template<typename Y>\r
-       typename std::enable_if<std::is_convertible<Y*, T*>::value, safe_ptr<T>&>::type\r
-       operator=(const safe_ptr<Y>& other)\r
+       template<typename U>\r
+       typename std::enable_if<std::is_convertible<U*, T*>::value, safe_ptr<T>&>::type\r
+       operator=(const safe_ptr<U>& other)\r
        {\r
                safe_ptr<T> temp(other);\r
                temp.swap(*this);\r
                return *this;\r
        }\r
 \r
-       template <typename Y>\r
-       typename std::enable_if<std::is_convertible<typename std::add_pointer<Y>::type, typename std::add_pointer<T>::type>::value, safe_ptr<T>&>::type\r
-       operator=(Y&& impl)\r
+       template <typename U>\r
+       typename std::enable_if<std::is_convertible<typename std::add_pointer<U>::type, typename std::add_pointer<T>::type>::value, safe_ptr<T>&>::type\r
+       operator=(U&& impl)\r
        {\r
                safe_ptr<T> temp(std::forward<T>(impl));\r
                temp.swap(*this);\r
@@ -94,66 +94,129 @@ public:
                                \r
        void swap(safe_ptr& other) { impl_.swap(other.impl_); } \r
        \r
-       std::shared_ptr<T> get_shared() const { return impl_; }\r
+       operator std::shared_ptr<T>() const { return impl_;}\r
+\r
+       template<class U>\r
+       bool owner_before(const safe_ptr<T>& ptr){ return impl_.owner_before(ptr.impl_); }\r
+\r
+       template<class U>\r
+       bool owner_before(const std::shared_ptr<U>& ptr){ return impl_.owner_before(ptr); }\r
+       \r
+       template<class D, class U> \r
+       D* get_deleter(safe_ptr<U> const& ptr) { return impl_.get_deleter(); }\r
        \r
 private:       \r
        std::shared_ptr<T> impl_;\r
 };\r
 \r
 template<class T, class U>\r
-bool operator==(safe_ptr<T> const & a, safe_ptr<U> const & b)\r
+bool operator==(const safe_ptr<T>& a, const safe_ptr<U>& b)\r
 {\r
        return a.get() == b.get();\r
 }\r
 \r
 template<class T, class U>\r
-bool operator!=(safe_ptr<T> const & a, safe_ptr<U> const & b)\r
+bool operator!=(const safe_ptr<T>& a, const safe_ptr<U>& b)\r
 {\r
        return a.get() != b.get();\r
 }\r
 \r
 template<class T, class U>\r
-bool operator<(safe_ptr<T> const & a, safe_ptr<U> const & b)\r
+bool operator<(const safe_ptr<T>& a, const safe_ptr<U>& b)\r
 {\r
        return a.get() < b.get();\r
 }\r
 \r
-template<class T> void swap(safe_ptr<T> & a, safe_ptr<T> & b)\r
+template<class T, class U>\r
+bool operator>(const safe_ptr<T>& a, const safe_ptr<U>& b)\r
+{\r
+       return a.get() > b.get();\r
+}\r
+\r
+template<class T, class U>\r
+bool operator>=(const safe_ptr<T>& a, const safe_ptr<U>& b)\r
+{\r
+       return a.get() >= b.get();\r
+}\r
+\r
+template<class T, class U>\r
+bool operator<=(const safe_ptr<T>& a, const safe_ptr<U>& b)\r
+{\r
+       return a.get() <= b.get();\r
+}\r
+\r
+template<class E, class T, class U>\r
+std::basic_ostream<E, T>& operator<<(std::basic_ostream<E, T>& out,    const safe_ptr<U>& p)\r
+{\r
+       return out << p.get();\r
+}\r
+\r
+template<class T> \r
+void swap(safe_ptr<T>& a, safe_ptr<T>& b)\r
 {\r
        a.swap(b);\r
 }\r
 \r
-template<class T> T* get_pointer(safe_ptr<T> const & p)\r
+template<class T> \r
+T* get_pointer(safe_ptr<T> const& p)\r
 {\r
        return p.get();\r
 }\r
 \r
+template <class T, class U>\r
+safe_ptr<T> static_pointer_cast(const safe_ptr<U>& p)\r
+{\r
+       return safe_ptr<T>(std::static_pointer_cast<T>(std::shared_ptr<U>(p)));\r
+}\r
+\r
+template <class T, class U>\r
+safe_ptr<T> const_pointer_cast(const safe_ptr<U>& p)\r
+{\r
+       return safe_ptr<T>(std::const_pointer_cast<T>(std::shared_ptr<U>(p)));\r
+}\r
+\r
+template <class T, class U>\r
+safe_ptr<T> dynamic_pointer_cast(const safe_ptr<U>& p)\r
+{\r
+       auto temp = std::dynamic_pointer_cast<T>(std::shared_ptr<U>(p));\r
+       if(!temp)\r
+               throw std::bad_cast();\r
+       return safe_ptr<T>(temp);\r
+}\r
+\r
 template<typename T>\r
 safe_ptr<T> make_safe()\r
 {\r
-       static_assert(!std::is_abstract<T>::value, "Cannot construct abstract class.");\r
        return safe_ptr<T>();\r
 }\r
 \r
 template<typename T, typename P0>\r
 safe_ptr<T> make_safe(P0&& p0)\r
 {\r
-       static_assert(!std::is_abstract<T>::value, "Cannot construct abstract class.");\r
        return safe_ptr<T>(std::make_shared<T>(std::forward<P0>(p0)));\r
 }\r
 \r
 template<typename T, typename P0, typename P1>\r
 safe_ptr<T> make_safe(P0&& p0, P1&& p1)\r
 {\r
-       static_assert(!std::is_abstract<T>::value, "Cannot construct abstract class.");\r
        return safe_ptr<T>(std::make_shared<T>(std::forward<P0>(p0), std::forward<P1>(p1)));\r
 }\r
 \r
 template<typename T, typename P0, typename P1, typename P2>\r
 safe_ptr<T> make_safe(P0&& p0, P1&& p1, P2&& p2)\r
 {\r
-       static_assert(!std::is_abstract<T>::value, "Cannot construct abstract class.");\r
        return safe_ptr<T>(std::make_shared<T>(std::forward<P0>(p0), std::forward<P1>(p1), std::forward<P2>(p2)));\r
 }\r
 \r
+template<typename T, typename P0, typename P1, typename P2, typename P3>\r
+safe_ptr<T> make_safe(P0&& p0, P1&& p1, P2&& p2, P3&& p3)\r
+{\r
+       return safe_ptr<T>(std::make_shared<T>(std::forward<P0>(p0), std::forward<P1>(p1), std::forward<P2>(p2), std::forward<P3>(p3)));\r
+}\r
+\r
+template<typename T, typename P0, typename P1, typename P2, typename P3, typename P4>\r
+safe_ptr<T> make_safe(P0&& p0, P1&& p1, P2&& p2, P3&& p3, P4&&)\r
+{\r
+       return safe_ptr<T>(std::make_shared<T>(std::forward<P0>(p0), std::forward<P1>(p1), std::forward<P2>(p2), std::forward<P3>(p3), std::forward<P3>(p4)));\r
+}\r
 }
\ No newline at end of file
index a7dd5106b1c80b72b3838c54e09c69951f18734e..78566bcfabdc86cd4289a84a90188354f34e730a 100644 (file)
@@ -66,6 +66,7 @@
 #include <SFML/Audio.hpp>\r
 \r
 #include "../common/utility/string_convert.h"\r
+#include "../common/utility/safe_ptr.h"\r
 \r
 #include "../common/log/Log.h"\r
 #include "../common/exception/exceptions.h"\r
index cc2f7422f13bd4a4f06d9aea23f357353ea72806..4a0f9b233e6f1d531bf3d1dc56938c04573a2460 100644 (file)
@@ -143,7 +143,7 @@ struct video_transformer::implementation : boost::noncopyable
 \r
        void initialize(const safe_ptr<frame_processor_device>& frame_processor)\r
        {\r
-               frame_processor_ = frame_processor.get_shared();\r
+               frame_processor_ = frame_processor;\r
        }\r
        \r
        std::shared_ptr<frame_processor_device> frame_processor_;\r
index 909e9c54a5412ace9aec9b820db8f5d229160d9e..161d67c5d36343a9b9825d402bfae935487337f6 100644 (file)
@@ -30,10 +30,7 @@ struct cg_producer::implementation : boost::noncopyable
 {\r
 public:\r
 \r
-       implementation() : ver_(template_version::invalid), flash_producer_(create_flash())\r
-       {\r
-       \r
-       }\r
+       implementation() : ver_(template_version::invalid), flash_producer_(create_flash()){}\r
 \r
        safe_ptr<flash_producer> create_flash()\r
        {               \r
@@ -144,7 +141,7 @@ public:
                \r
        void initialize(const safe_ptr<frame_processor_device>& frame_processor)\r
        {\r
-               frame_processor_ = frame_processor.get_shared();\r
+               frame_processor_ = frame_processor;\r
                flash_producer_->initialize(frame_processor);\r
        }\r
 \r
@@ -160,14 +157,16 @@ public:
        \r
 safe_ptr<cg_producer> get_default_cg_producer(const safe_ptr<channel>& channel, int render_layer)\r
 {      \r
-       auto producer = std::dynamic_pointer_cast<cg_producer>(channel->foreground(render_layer).get().get_shared());\r
-       if(producer == nullptr)\r
+       try\r
        {\r
-               producer = std::make_shared<cg_producer>();             \r
-               channel->load(render_layer, safe_ptr<frame_producer>(producer), load_option::auto_play); \r
+               return dynamic_pointer_cast<cg_producer>(channel->foreground(render_layer).get());\r
+       }\r
+       catch(std::bad_cast&)\r
+       {\r
+               auto producer = make_safe<cg_producer>();               \r
+               channel->load(render_layer, producer, load_option::auto_play); \r
+               return producer;\r
        }\r
-       \r
-       return safe_ptr<cg_producer>(producer);\r
 }\r
 \r
 cg_producer::cg_producer() : impl_(new implementation()){}\r
index 31f1fbfd502debb90d2c8fd60210969a45aa3d58..ca777dff21ca1ee730c12f592a71903ab672f3db 100644 (file)
@@ -182,7 +182,7 @@ struct flash_producer::implementation
                                stop();\r
 \r
                                frame_buffer_.clear();\r
-                               frame_buffer_.try_push(draw_frame::eof().get_shared()); // EOF\r
+                               frame_buffer_.try_push(draw_frame::eof()); // EOF\r
                \r
                                current_frame_ = nullptr;\r
                        });\r
@@ -227,9 +227,9 @@ struct flash_producer::implementation
 \r
                        std::shared_ptr<draw_frame> frame;\r
                        if(is_progressive)\r
-                               frame = do_receive().get_shared();\r
+                               frame = do_receive();\r
                        else\r
-                               frame = composite_frame::interlace(do_receive(), do_receive(), format_desc.mode).get_shared();\r
+                               frame = std::shared_ptr<composite_frame>(composite_frame::interlace(do_receive(), do_receive(), format_desc.mode));\r
                        \r
                        frame_buffer_.push(frame);\r
                        is_empty_ = flashax_container_->IsEmpty();\r
@@ -261,7 +261,7 @@ struct flash_producer::implementation
 \r
        void initialize(const safe_ptr<frame_processor_device>& frame_processor)\r
        {\r
-               frame_processor_ = frame_processor.get_shared();\r
+               frame_processor_ = frame_processor;\r
                auto format_desc = frame_processor_->get_video_format_desc();\r
                bmp_frame_ = std::make_shared<bitmap>(format_desc.width, format_desc.height);\r
                start(false);\r
index e4cec3ba3dcc3e305cff7ebaaee5af9ba58cdcf7..92fefc7f5d5199986f850e789e3431b56a18b005 100644 (file)
@@ -25,7 +25,7 @@ struct image_producer : public frame_producer
 \r
        void initialize(const safe_ptr<frame_processor_device>& frame_processor)\r
        {\r
-               frame_processor_ = frame_processor.get_shared();\r
+               frame_processor_ = frame_processor;\r
                auto bitmap = load_image(filename_);\r
                FreeImage_FlipVertical(bitmap.get());\r
                auto frame = frame_processor->create_frame(FreeImage_GetWidth(bitmap.get()), FreeImage_GetHeight(bitmap.get()));\r
index 61790a309dfb8c7d6163e0a29128f388c42e0797..9dbcf87eb47910b1e6614999790b69d4d26cfbc3 100644 (file)
@@ -143,7 +143,7 @@ struct transition_producer::implementation : boost::noncopyable
        void initialize(const safe_ptr<frame_processor_device>& frame_processor)\r
        {\r
                dest_producer_->initialize(frame_processor);\r
-               frame_processor_ = frame_processor.get_shared();\r
+               frame_processor_ = frame_processor;\r
        }\r
 \r
        std::wstring print() const\r
index 8eacc63e70080c9b6dc92077a801609932b804f2..78b4a46fd152334b7691679a1b1412d29eb0a43b 100644 (file)
@@ -48,7 +48,7 @@ const std::wstring AMCPProtocolStrategy::MessageDelimiter = TEXT("\r\n");
 \r
 inline std::shared_ptr<channel> GetChannelSafe(unsigned int index, const std::vector<safe_ptr<channel>>& channels)\r
 {\r
-       return index < channels.size() ? channels[index].get_shared() : nullptr;\r
+       return index < channels.size() ? std::shared_ptr<channel>(channels[index]) : nullptr;\r
 }\r
 \r
 AMCPProtocolStrategy::AMCPProtocolStrategy(const std::vector<safe_ptr<channel>>& channels) : channels_(channels) {\r