We currently do a round trip every time a surface is created.
This patch changes it so that instead of doing to for every surface,
we handle the synchronization once all the current tile updates are
done in WebProcess side.
Change-Id: I444d8bfa35e3bbf82bf11b78512eb03d1325b897
EGLWindowSurface::EGLWindowSurface(const IntSize& size, GLPlatformSurface::SurfaceAttributes attributes)
: EGLOffScreenSurface(attributes)
, m_nativeWindow(0)
- , m_bufferAttached(false)
{
if (!m_configSelector)
return;
LOG_ERROR("Failed to SwapBuffers(%d).", eglGetError());
m_surface->deleteFrameCallBack();
}
-
- if (!m_bufferAttached) {
- // FIXME: Need a better way to handle this.
- WaylandDisplay::instance()->syncDisplay();
- m_bufferAttached = true;
- }
}
void EGLWindowSurface::destroy()
private:
struct wl_egl_window* m_nativeWindow;
OwnPtr<WaylandSurface> m_surface;
- bool m_bufferAttached :1;
};
}
, m_registry(0)
, m_wlCompositor(0)
, m_queue(0)
+ , m_pendingEvents(false)
{
}
m_display = 0;
}
-struct wl_display* WaylandDisplay::nativeDisplay()
+struct wl_display* WaylandDisplay::nativeDisplay() const
{
- wl_display* wlDisplay = 0;
- if (m_instance)
- wlDisplay = m_instance->m_display;
-
- return wlDisplay;
+ return m_display;
}
-struct wl_compositor* WaylandDisplay::compositor()
+struct wl_compositor* WaylandDisplay::compositor() const
{
- struct wl_compositor* wlCompositor = 0;
- if (m_instance)
- wlCompositor = m_instance->m_wlCompositor;
-
- return wlCompositor;
+ return m_wlCompositor;
}
-struct wl_registry* WaylandDisplay::registry()
+struct wl_registry* WaylandDisplay::registry() const
{
- struct wl_registry* wlRegistry = 0;
- if (m_instance)
- wlRegistry = m_instance->m_registry;
-
- return wlRegistry;
+ return m_registry;
}
WaylandBuffer* WaylandDisplay::mapBuffer(WaylandSurfaceId sharedBufferId, WaylandBufferListener* listener, bool useLinearFilter)
wl_callback_destroy(callback);
}
+int WaylandDisplay::flush()
+{
+ if (!m_pendingEvents)
+ return 0;
+
+ return syncDisplay();
+}
+
int WaylandDisplay::syncDisplay()
{
if (!m_queue)
return -1;
int done = 0, ret = 0;
+ m_pendingEvents = false;
struct wl_callback* callback = wl_display_sync(m_display);
wl_callback_add_listener(callback, &syncListener, &done);
wl_proxy_set_queue((struct wl_proxy *) callback, m_queue);
static WaylandDisplay* instance();
static void disconnect();
// client apis.
- struct wl_display* nativeDisplay();
- struct wl_compositor* compositor();
- struct wl_registry* registry();
+ struct wl_display* nativeDisplay() const;
+ struct wl_compositor* compositor() const;
+ struct wl_registry* registry() const;
int syncDisplay();
+ int flush();
+
// Ownership is transferred.
PassOwnPtr<WaylandSurface> createSurface();
void lock();
void unlock();
void handlePendingEvents();
+ void addPendingEvent() { m_pendingEvents = true; }
void initialize(wl_display* = 0);
static WaylandDisplay* openStaticConnection();
struct wl_registry* m_registry;
struct wl_compositor* m_wlCompositor;
struct wl_event_queue* m_queue;
+ bool m_pendingEvents :1;
friend class WaylandBuffer;
+ friend class WaylandSurface;
};
}
: m_surface(0)
, m_frameCallBack(0)
, m_queue(0)
+ , m_surfaceAttached(false)
, m_id(0)
{
static WaylandSurfaceId bufferHandleId = 0;
bufferHandleId++;
m_id = bufferHandleId;
- WaylandDisplay::instance()->syncDisplay();
+ WaylandDisplay::instance()->addPendingEvent();
+}
+
+WaylandSurface::~WaylandSurface()
+{
+ m_id = 0;
+ deleteFrameCallBack();
+
+ if (m_surface) {
+ wl_surface_destroy(m_surface);
+ m_surface = 0;
+ }
+
+ if (WaylandDisplay::instance())
+ WaylandDisplay::instance()->addPendingEvent();
}
void WaylandSurface::addFrameCallBack()
if (!m_queue) {
m_queue = wl_display_create_queue(WaylandDisplay::instance()->nativeDisplay());
wl_proxy_set_queue((struct wl_proxy *)WaylandDisplay::instance()->registry(), m_queue);
+ ensureSurfaceMapped();
}
m_frameCallBack = wl_surface_frame(m_surface);
m_frameCallBack = 0;
}
-WaylandSurface::~WaylandSurface()
+void WaylandSurface::ensureSurfaceMapped()
{
- m_id = 0;
- deleteFrameCallBack();
-
- if (m_surface) {
- wl_surface_destroy(m_surface);
- m_surface = 0;
+ if (!m_surfaceAttached) {
+ WaylandDisplay::instance()->addPendingEvent();
+ m_surfaceAttached = true;
}
}
// m_surface->addFrameCallBack();
// Swap buffers.
void addFrameCallBack();
- // Ensure that deleteFrameCallBack is called before
- // destroying any EGL resources associated with the
- // surface.
- // Example usage:
+ // Ensure deleteFrameCallBack(in case a framecallback is requested)
+ // is called before destroying any EGL resources associated with the
+ // surface. Example usage:
// deleteFrameCallBack();
// destroy egl window etc
// m_surface = nullptr; i.e destroy WaylandSurface.
void deleteFrameCallBack();
// see addFrameCallBack.
int ensureFrameCallBackDone();
+ // Synchronizes initial Attach call.
+ void ensureSurfaceMapped();
// callback
static void surfaceFrameCallback(void*, struct wl_callback*, uint32_t);
struct wl_surface* m_surface;
struct wl_callback* m_frameCallBack;
struct wl_event_queue* m_queue;
+ bool m_surfaceAttached :1;
WaylandSurfaceId m_id;
friend class WaylandDisplay;
};
#include "TextureMapperPlatformLayer.h"
#include "TiledBackingStoreRemoteTile.h"
#include "SharedPlatformSurfaceTizen.h"
+#if PLATFORM(WAYLAND)
+#include "WaylandDisplay.h"
+#endif
#include "WebPage.h"
#include <wtf/CurrentTime.h>
#include <wtf/HashMap.h>
void WebGraphicsLayer::tiledBackingStorePaintEnd(const Vector<IntRect>& updatedRects)
{
+#if PLATFORM(WAYLAND)
+ if (WaylandDisplay::instance())
+ WaylandDisplay::instance()->flush();
+#endif
}
bool WebGraphicsLayer::tiledBackingStoreUpdatesAllowed() const