]> git.sesse.net Git - casparcg/blobdiff - core/mixer/gpu/ogl_device.h
2.0. Fixed rendering stalls caused by ogl frame allocation delays.
[casparcg] / core / mixer / gpu / ogl_device.h
index 7812165539c103a068df84754ed8f5454376eadb..872046c0b3b46072f26ef5cd782750622af8c3f2 100644 (file)
 #include <tbb/concurrent_unordered_map.h>\r
 #include <tbb/concurrent_queue.h>\r
 \r
+#include <boost/noncopyable.hpp>\r
 #include <boost/thread/future.hpp>\r
 \r
 #include <array>\r
+#include <unordered_map>\r
+\r
+#include <gl/glew.h>\r
 \r
 #include "../../dependencies\SFML-1.6\include\SFML/Window/Context.hpp"\r
 \r
 namespace caspar { namespace core {\r
 \r
-class ogl_device\r
+class shader;\r
+\r
+template<typename T>\r
+struct buffer_pool\r
+{\r
+       tbb::atomic<int> usage_count;\r
+       tbb::atomic<int> flush_count;\r
+       tbb::concurrent_bounded_queue<std::shared_ptr<T>> items;\r
+\r
+       buffer_pool()\r
+       {\r
+               usage_count = 0;\r
+               flush_count = 0;\r
+       }\r
+};\r
+\r
+class ogl_device : boost::noncopyable\r
 {      \r
+       std::unordered_map<GLenum, bool> caps_;\r
+       std::array<size_t, 4>                    viewport_;\r
+       std::array<size_t, 4>                    scissor_;\r
+       const GLubyte*                                   pattern_;\r
+       GLint                                                    attached_texture_;\r
+       GLint                                                    active_shader_;\r
+       std::array<GLint, 16>                    binded_textures_;\r
+       std::array<GLint, 4>                     blend_func_;\r
+\r
        std::unique_ptr<sf::Context> context_;\r
        \r
-       std::array<tbb::concurrent_unordered_map<size_t, tbb::concurrent_bounded_queue<std::shared_ptr<device_buffer>>>, 4> device_pools_;\r
-       std::array<tbb::concurrent_unordered_map<size_t, tbb::concurrent_bounded_queue<std::shared_ptr<host_buffer>>>, 2> host_pools_;\r
+       std::array<tbb::concurrent_unordered_map<size_t, safe_ptr<buffer_pool<device_buffer>>>, 4> device_pools_;\r
+       std::array<tbb::concurrent_unordered_map<size_t, safe_ptr<buffer_pool<host_buffer>>>, 2> host_pools_;\r
        \r
        unsigned int fbo_;\r
 \r
        executor executor_;\r
-\r
+                               \r
+public:                \r
        ogl_device();\r
        ~ogl_device();\r
 \r
-       static ogl_device& get_instance()\r
-       {\r
-               static ogl_device device;\r
-               return device;\r
-       }\r
+       // Not thread-safe, must be called inside of context\r
+       void enable(GLenum cap);\r
+       void disable(GLenum cap);\r
+       void viewport(size_t x, size_t y, size_t width, size_t height);\r
+       void scissor(size_t x, size_t y, size_t width, size_t height);\r
+       void stipple_pattern(const GLubyte* pattern);\r
+\r
+       void attach(device_buffer& texture);\r
+       void clear(device_buffer& texture);\r
+\r
+       void begin_read(host_buffer& dest, device_buffer& source);\r
+       void begin_read(device_buffer& dest, host_buffer& source);\r
+\r
+       void blend_func(int c1, int c2, int a1, int a2);\r
+       void blend_func(int c1, int c2);\r
        \r
+       void use(shader& shader);\r
+\r
+       void flush();\r
+\r
+       // thread-afe\r
        template<typename Func>\r
-       auto do_begin_invoke(Func&& func) -> boost::unique_future<decltype(func())> // noexcept\r
+       auto begin_invoke(Func&& func, task_priority priority = normal_priority) -> boost::unique_future<decltype(func())> // noexcept\r
        {                       \r
-               return executor_.begin_invoke(std::forward<Func>(func));\r
+               return executor_.begin_invoke(std::forward<Func>(func), priority);\r
        }\r
        \r
        template<typename Func>\r
-       auto do_invoke(Func&& func) -> decltype(func())\r
+       auto invoke(Func&& func, task_priority priority = normal_priority) -> decltype(func())\r
        {\r
-               return executor_.invoke(std::forward<Func>(func));\r
+               return executor_.invoke(std::forward<Func>(func), priority);\r
        }\r
                \r
-       safe_ptr<device_buffer> do_create_device_buffer(size_t width, size_t height, size_t stride);\r
-       safe_ptr<host_buffer> do_create_host_buffer(size_t size, host_buffer::usage_t usage);\r
-public:                \r
+       safe_ptr<device_buffer> create_device_buffer(size_t width, size_t height, size_t stride);\r
+       safe_ptr<host_buffer> create_host_buffer(size_t size, host_buffer::usage_t usage);\r
        \r
-       template<typename Func>\r
-       static auto begin_invoke(Func&& func) -> boost::unique_future<decltype(func())> // noexcept\r
-       {                       \r
-               return get_instance().do_begin_invoke(std::forward<Func>(func));\r
-       }\r
-       \r
-       template<typename Func>\r
-       static auto invoke(Func&& func) -> decltype(func())\r
-       {\r
-               return get_instance().do_invoke(std::forward<Func>(func));\r
-       }\r
-               \r
-       static safe_ptr<device_buffer> create_device_buffer(size_t width, size_t height, size_t stride)\r
-       {\r
-               return get_instance().do_create_device_buffer(width, height, stride);\r
-       }\r
-\r
-       static safe_ptr<host_buffer> create_host_buffer(size_t size, host_buffer::usage_t usage)\r
-       {\r
-               return get_instance().do_create_host_buffer(size, usage);\r
-       }\r
-\r
-       static void yield()\r
-       {\r
-               get_instance().executor_.yield();\r
-       }\r
+       void yield();\r
+       boost::unique_future<void> gc();\r
 \r
        static std::wstring get_version();\r
+\r
+private:\r
+       safe_ptr<device_buffer> allocate_device_buffer(size_t width, size_t height, size_t stride);\r
+       safe_ptr<host_buffer> allocate_host_buffer(size_t size, host_buffer::usage_t usage);\r
 };\r
 \r
 }}
\ No newline at end of file