diff --git a/gl_compositor.cpp b/gl_compositor.cpp
index 38f1e03..0605c04 100644
--- a/gl_compositor.cpp
+++ b/gl_compositor.cpp
@@ -17,50 +17,23 @@
 #define ATRACE_TAG ATRACE_TAG_GRAPHICS
 #define LOG_TAG "GLCompositor"
 
-#include <sstream>
-#include <string>
 #include <vector>
 
 #include <cutils/log.h>
 
-#define EGL_EGLEXT_PROTOTYPES
-#define GL_GLEXT_PROTOTYPES
-
-#include <EGL/egl.h>
-#include <EGL/eglext.h>
-#include <GLES2/gl2.h>
-#include <GLES2/gl2ext.h>
-
-#include <hardware/hardware.h>
-#include <hardware/hwcomposer.h>
-
 #include <ui/GraphicBuffer.h>
-#include <ui/PixelFormat.h>
 #include <utils/Trace.h>
 
-#include <cutils/properties.h>
 #include <sync/sync.h>
 #include <sw_sync.h>
 
 #include "drm_hwcomposer.h"
 
 #include "gl_compositor.h"
-#include "seperate_rects.h"
-
-// TODO(zachr): use hwc_drm_bo to turn buffer handles into textures
-#ifndef EGL_NATIVE_HANDLE_ANDROID_NVX
-#define EGL_NATIVE_HANDLE_ANDROID_NVX 0x322A
-#endif
-
-#define MAX_OVERLAPPING_LAYERS 64
+#include "glworker.h"
 
 namespace android {
 
-struct GLCompositor::texture_from_handle {
-  EGLImageKHR image;
-  GLuint texture;
-};
-
 static const char *get_gl_error(void);
 static const char *get_egl_error(void);
 static bool has_extension(const char *extension, const char *extensions);
@@ -89,58 +62,31 @@
 
 struct GLTarget {
   sp<GraphicBuffer> fb;
-  EGLImageKHR egl_fb_image;
-  GLuint gl_fb;
-  GLuint gl_fb_tex;
   bool forgotten;
   unsigned composition_count;
 
-  GLTarget()
-      : egl_fb_image(EGL_NO_IMAGE_KHR),
-        gl_fb(0),
-        gl_fb_tex(0),
-        forgotten(true),
-        composition_count(0) {
+  GLTarget() : forgotten(true), composition_count(0) {
   }
 
   void Reset() {
     fb.clear();
-    egl_fb_image = EGL_NO_IMAGE_KHR;
-    gl_fb = 0;
-    gl_fb_tex = 0;
     forgotten = true;
     composition_count = 0;
   }
 
   bool is_some() const {
-    return egl_fb_image != EGL_NO_IMAGE_KHR;
+    return fb != NULL;
   }
 };
 
 struct GLCompositor::priv_data {
-  EGLDisplay egl_display;
-  EGLContext egl_ctx;
-
-  EGLDisplay saved_egl_display;
-  EGLContext saved_egl_ctx;
-  EGLSurface saved_egl_read;
-  EGLSurface saved_egl_draw;
-
   int current_target;
   std::vector<GLTarget> targets;
   std::vector<GLComposition *> compositions;
 
-  std::vector<GLint> blend_programs;
-  GLuint vertex_buffer;
+  GLWorker worker;
 
-  priv_data()
-      : egl_display(EGL_NO_DISPLAY),
-        egl_ctx(EGL_NO_CONTEXT),
-        saved_egl_display(EGL_NO_DISPLAY),
-        saved_egl_ctx(EGL_NO_CONTEXT),
-        saved_egl_read(EGL_NO_SURFACE),
-        saved_egl_draw(EGL_NO_SURFACE),
-        current_target(-1) {
+  priv_data() : current_target(-1) {
   }
 };
 
@@ -152,10 +98,18 @@
   };
 
   GLComposition(GLCompositor *owner, Importer *imp)
-      : compositor(owner), importer(imp), target_handle(-1) {
+      : compositor(owner), importer(imp), target_handle(-1), timeline_fd(-1) {
+    int ret = sw_sync_timeline_create();
+    if (ret < 0) {
+      ALOGE("Failed to create sw sync timeline %d", ret);
+    }
+    timeline_fd = ret;
   }
 
   virtual ~GLComposition() {
+    if (timeline_fd >= 0)
+      close(timeline_fd);
+
     if (compositor == NULL) {
       return;
     }
@@ -186,10 +140,10 @@
       return 1;
     }
 
-    layer_data.push_back(LayerData());
-    LayerData &layer_datum = layer_data.back();
-    layer_datum.layer = *layer;
-    layer_datum.bo = *bo;
+    layer->releaseFenceFd = sw_sync_fence_create(
+        timeline_fd, "GLComposition release fence", layers.size() + 1);
+
+    layers.push_back(*layer);
 
     return importer->ReleaseBuffer(bo);
   }
@@ -202,114 +156,15 @@
   GLCompositor *compositor;
   Importer *importer;
   int target_handle;
-  std::vector<LayerData> layer_data;
+  int timeline_fd;
+  std::vector<hwc_layer_1> layers;
 };
 
-struct RenderingCommand {
-  struct TextureSource {
-    unsigned texture_index;
-    float crop_bounds[4];
-    float alpha;
-  };
-
-  float bounds[4];
-  unsigned texture_count;
-  TextureSource textures[MAX_OVERLAPPING_LAYERS];
-
-  RenderingCommand() : texture_count(0) {
-  }
-};
-
-static void ConstructCommands(const GLComposition &composition,
-                              std::vector<RenderingCommand> *commands) {
-  std::vector<seperate_rects::Rect<float> > in_rects;
-  std::vector<seperate_rects::RectSet<uint64_t, float> > out_rects;
-  int i;
-
-  for (unsigned rect_index = 0; rect_index < composition.layer_data.size();
-       rect_index++) {
-    const struct hwc_layer_1 &layer = composition.layer_data[rect_index].layer;
-    seperate_rects::Rect<float> rect;
-    in_rects.push_back(seperate_rects::Rect<float>(
-        layer.displayFrame.left, layer.displayFrame.top,
-        layer.displayFrame.right, layer.displayFrame.bottom));
-  }
-
-  seperate_frects_64(in_rects, &out_rects);
-
-  for (unsigned rect_index = 0; rect_index < out_rects.size(); rect_index++) {
-    const seperate_rects::RectSet<uint64_t, float> &out_rect =
-        out_rects[rect_index];
-    commands->push_back(RenderingCommand());
-    RenderingCommand &cmd = commands->back();
-
-    memcpy(cmd.bounds, out_rect.rect.bounds, sizeof(cmd.bounds));
-
-    uint64_t tex_set = out_rect.id_set.getBits();
-    for (unsigned i = composition.layer_data.size() - 1; tex_set != 0x0; i--) {
-      if (tex_set & (0x1 << i)) {
-        tex_set &= ~(0x1 << i);
-
-        const struct hwc_layer_1 &layer = composition.layer_data[i].layer;
-
-        seperate_rects::Rect<float> display_rect(
-            layer.displayFrame.left, layer.displayFrame.top,
-            layer.displayFrame.right, layer.displayFrame.bottom);
-        float display_size[2] = {
-            display_rect.bounds[2] - display_rect.bounds[0],
-            display_rect.bounds[3] - display_rect.bounds[1]};
-
-        seperate_rects::Rect<float> crop_rect(
-            layer.sourceCropf.left, layer.sourceCropf.top,
-            layer.sourceCropf.right, layer.sourceCropf.bottom);
-        float crop_size[2] = {crop_rect.bounds[2] - crop_rect.bounds[0],
-                              crop_rect.bounds[3] - crop_rect.bounds[1]};
-
-        RenderingCommand::TextureSource &src = cmd.textures[cmd.texture_count];
-        cmd.texture_count++;
-        src.texture_index = i;
-
-        for (int b = 0; b < 4; b++) {
-          float bound_percent = (cmd.bounds[b] - display_rect.bounds[b % 2]) /
-                                display_size[b % 2];
-          src.crop_bounds[b] =
-              crop_rect.bounds[b % 2] + bound_percent * crop_size[b % 2];
-        }
-
-        if (layer.blending == HWC_BLENDING_NONE) {
-          src.alpha = 1.0f;
-          // This layer is opaque. There is no point in using layers below this
-          // one.
-          break;
-        }
-
-        src.alpha = layer.planeAlpha / 255.0f;
-      }
-    }
-  }
-}
-
 GLCompositor::GLCompositor() {
   priv_ = new priv_data;
 }
 
 GLCompositor::~GLCompositor() {
-  if (BeginContext()) {
-    goto destroy_ctx;
-  }
-
-  glBindFramebuffer(GL_FRAMEBUFFER, 0);
-  glBindTexture(GL_TEXTURE_2D, 0);
-
-  for (std::vector<GLTarget>::iterator it = priv_->targets.end();
-       it != priv_->targets.begin(); it = priv_->targets.end()) {
-    --it;
-    glDeleteFramebuffers(1, &it->gl_fb);
-    glDeleteTextures(1, &it->gl_fb_tex);
-    eglDestroyImageKHR(priv_->egl_display, it->egl_fb_image);
-    priv_->targets.erase(it);
-  }
-
   for (std::vector<GLComposition *>::iterator it = priv_->compositions.end();
        it != priv_->compositions.begin(); it = priv_->compositions.end()) {
     --it;
@@ -320,111 +175,11 @@
     priv_->compositions.erase(it);
   }
 
-destroy_ctx:
-  eglMakeCurrent(priv_->egl_display,
-                 EGL_NO_SURFACE /* No default draw surface */,
-                 EGL_NO_SURFACE /* No default draw read */, EGL_NO_CONTEXT);
-  eglDestroyContext(priv_->egl_display, priv_->egl_ctx);
-
-  EndContext();
   delete priv_;
 }
 
 int GLCompositor::Init() {
-  int ret = 0;
-  const char *egl_extensions;
-  const char *gl_extensions;
-  EGLint num_configs;
-  EGLint attribs[] = {EGL_WIDTH, 1, EGL_HEIGHT, 1, EGL_NONE, EGL_NONE};
-  EGLConfig egl_config;
-
-  // clang-format off
-  const GLfloat verts[] = {
-    0.0f,  0.0f,    0.0f, 0.0f,
-    0.0f,  1.0f,    0.0f, 1.0f,
-    1.0f,  0.0f,    1.0f, 0.0f,
-    1.0f,  1.0f,    1.0f, 1.0f
-  };
-  // clang-format on
-
-  const EGLint config_attribs[] = {EGL_RENDERABLE_TYPE,
-                                   EGL_OPENGL_ES2_BIT,
-                                   EGL_RED_SIZE,
-                                   8,
-                                   EGL_GREEN_SIZE,
-                                   8,
-                                   EGL_BLUE_SIZE,
-                                   8,
-                                   EGL_NONE};
-
-  const EGLint context_attribs[] = {EGL_CONTEXT_CLIENT_VERSION, 3, EGL_NONE};
-
-  priv_->egl_display = eglGetDisplay(EGL_DEFAULT_DISPLAY);
-  if (priv_->egl_display == EGL_NO_DISPLAY) {
-    ALOGE("Failed to get egl display");
-    ret = 1;
-    goto out;
-  }
-
-  if (!eglInitialize(priv_->egl_display, NULL, NULL)) {
-    ALOGE("Failed to initialize egl: %s", get_egl_error());
-    ret = 1;
-    goto out;
-  }
-
-  egl_extensions = eglQueryString(priv_->egl_display, EGL_EXTENSIONS);
-
-  // These extensions are all technically required but not always reported due
-  // to meta EGL filtering them out.
-  if (!has_extension("EGL_KHR_image_base", egl_extensions))
-    ALOGW("EGL_KHR_image_base extension not supported");
-
-  if (!has_extension("EGL_ANDROID_image_native_buffer", egl_extensions))
-    ALOGW("EGL_ANDROID_image_native_buffer extension not supported");
-
-  if (!has_extension("EGL_ANDROID_native_fence_sync", egl_extensions))
-    ALOGW("EGL_ANDROID_native_fence_sync extension not supported");
-
-  if (!eglChooseConfig(priv_->egl_display, config_attribs, &egl_config, 1,
-                       &num_configs)) {
-    ALOGE("eglChooseConfig() failed with error: %s", get_egl_error());
-    goto out;
-  }
-
-  priv_->egl_ctx =
-      eglCreateContext(priv_->egl_display, egl_config,
-                       EGL_NO_CONTEXT /* No shared context */, context_attribs);
-
-  if (priv_->egl_ctx == EGL_NO_CONTEXT) {
-    ALOGE("Failed to create OpenGL ES Context: %s", get_egl_error());
-    ret = 1;
-    goto out;
-  }
-
-  ret = BeginContext();
-  if (ret)
-    goto out;
-
-  gl_extensions = (const char *)glGetString(GL_EXTENSIONS);
-
-  if (!has_extension("GL_OES_EGL_image", gl_extensions))
-    ALOGW("GL_OES_EGL_image extension not supported");
-
-  glGenBuffers(1, &priv_->vertex_buffer);
-  glBindBuffer(GL_ARRAY_BUFFER, priv_->vertex_buffer);
-  glBufferData(GL_ARRAY_BUFFER, sizeof(verts), verts, GL_STATIC_DRAW);
-  glBindBuffer(GL_ARRAY_BUFFER, 0);
-
-  if (GenerateShaders()) {
-    ret = 1;
-    goto end_ctx;
-  }
-
-end_ctx:
-  EndContext();
-
-out:
-  return ret;
+  return priv_->worker.Init();
 }
 
 Targeting *GLCompositor::targeting() {
@@ -434,63 +189,13 @@
 int GLCompositor::CreateTarget(sp<GraphicBuffer> &buffer) {
   int ret;
 
-  ret = BeginContext();
-  if (ret)
-    return -1;
-
   int target_handle = AllocResource(priv_->targets);
   GLTarget *target = &priv_->targets[target_handle];
 
   target->fb = buffer;
-
-  target->egl_fb_image = eglCreateImageKHR(
-      priv_->egl_display, EGL_NO_CONTEXT, EGL_NATIVE_BUFFER_ANDROID,
-      (EGLClientBuffer)target->fb->getNativeBuffer(), NULL /* no attribs */);
-
-  if (target->egl_fb_image == EGL_NO_IMAGE_KHR) {
-    ALOGE("Failed to make image from target buffer: %s", get_egl_error());
-    ret = -1;
-    goto fail_create_image;
-  }
-
-  glGenTextures(1, &target->gl_fb_tex);
-  glBindTexture(GL_TEXTURE_2D, target->gl_fb_tex);
-  glEGLImageTargetTexture2DOES(GL_TEXTURE_2D,
-                               (GLeglImageOES)target->egl_fb_image);
-  glBindTexture(GL_TEXTURE_2D, 0);
-
-  glGenFramebuffers(1, &target->gl_fb);
-  glBindFramebuffer(GL_FRAMEBUFFER, target->gl_fb);
-  glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D,
-                         target->gl_fb_tex, 0);
-
-  if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE) {
-    ALOGE("Failed framebuffer check for created target buffer");
-    ret = 1;
-    goto fail_framebuffer_status;
-  }
-
   target->forgotten = false;
 
-  ret = target_handle;
-  goto out;
-
-fail_framebuffer_status:
-  glBindFramebuffer(GL_FRAMEBUFFER, 0);
-  glDeleteFramebuffers(1, &target->gl_fb);
-  glDeleteTextures(1, &target->gl_fb_tex);
-  eglDestroyImageKHR(priv_->egl_display, target->egl_fb_image);
-  target->gl_fb = 0;
-  target->gl_fb_tex = 0;
-  target->egl_fb_image = EGL_NO_IMAGE_KHR;
-
-fail_create_image:
-  target->fb.clear();
-  FreeResource(priv_->targets, target_handle);
-
-out:
-  EndContext();
-  return ret;
+  return target_handle;
 }
 
 void GLCompositor::SetTarget(int target_handle) {
@@ -525,13 +230,6 @@
 void GLCompositor::CheckAndDestroyTarget(int target_handle) {
   GLTarget *target = &priv_->targets[target_handle];
   if (target->composition_count == 0 && target->forgotten) {
-    if (BeginContext() == 0) {
-      glDeleteFramebuffers(1, &target->gl_fb);
-      glDeleteTextures(1, &target->gl_fb_tex);
-      eglDestroyImageKHR(priv_->egl_display, target->egl_fb_image);
-      EndContext();
-    }
-
     FreeResource(priv_->targets, target_handle);
   }
 }
@@ -557,7 +255,9 @@
 
 int GLCompositor::QueueComposition(Composition *composition) {
   if (composition) {
-    int ret = DoComposition(*(GLComposition *)composition);
+    GLComposition *gl_composition = (GLComposition *)composition;
+    int ret = DoComposition(gl_composition);
+    gl_composition->timeline_fd = -1;
     delete composition;
     return ret;
   }
@@ -571,454 +271,25 @@
   return 0;
 }
 
-int GLCompositor::BeginContext() {
-  priv_->saved_egl_display = eglGetCurrentDisplay();
-  priv_->saved_egl_ctx = eglGetCurrentContext();
-
-  if (priv_->saved_egl_display != priv_->egl_display ||
-      priv_->saved_egl_ctx != priv_->egl_ctx) {
-    priv_->saved_egl_read = eglGetCurrentSurface(EGL_READ);
-    priv_->saved_egl_draw = eglGetCurrentSurface(EGL_DRAW);
-  } else {
-    return 0;
-  }
-
-  if (!eglMakeCurrent(priv_->egl_display, EGL_NO_SURFACE, EGL_NO_SURFACE,
-                      priv_->egl_ctx)) {
-    ALOGE("Failed to make the OpenGL ES Context current: %s", get_egl_error());
-    return 1;
-  }
-  return 0;
-}
-
-int GLCompositor::EndContext() {
-  if (priv_->saved_egl_display != eglGetCurrentDisplay() ||
-      priv_->saved_egl_ctx != eglGetCurrentContext()) {
-    if (!eglMakeCurrent(priv_->saved_egl_display, priv_->saved_egl_read,
-                        priv_->saved_egl_draw, priv_->saved_egl_ctx)) {
-      ALOGE("Failed to make the old OpenGL ES Context current: %s",
-            get_egl_error());
-      return 1;
-    }
-  }
-
-  return 0;
-}
-
-GLint CompileAndCheckShader(GLenum type, unsigned source_count,
-                            const GLchar **sources, std::string *shader_log) {
-  GLint status;
-  GLint shader = glCreateShader(type);
-  if (!shader) {
-    *shader_log = "glCreateShader failed";
-    return 0;
-  }
-  glShaderSource(shader, source_count, sources, NULL);
-  glCompileShader(shader);
-  glGetShaderiv(shader, GL_COMPILE_STATUS, &status);
-  if (!status) {
-    if (shader_log) {
-      GLint log_length;
-      glGetShaderiv(shader, GL_INFO_LOG_LENGTH, &log_length);
-      shader_log->resize(log_length);
-      glGetShaderInfoLog(shader, log_length, NULL, &(*shader_log)[0]);
-    }
-    glDeleteShader(shader);
-    return 0;
-  }
-
-  return shader;
-}
-
-int GLCompositor::GenerateShaders() {
-  // Limits: GL_MAX_VARYING_COMPONENTS, GL_MAX_TEXTURE_IMAGE_UNITS,
-  // GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS
-  // clang-format off
-  const GLchar *shader_preamble = "#version 300 es\n#define LAYER_COUNT ";
-
-  const GLchar *vertex_shader_source =
-"\n"
-"precision mediump int;                                                     \n"
-"uniform vec4 uViewport;                                                    \n"
-"uniform sampler2D uLayerTextures[LAYER_COUNT];                             \n"
-"uniform vec4 uLayerCrop[LAYER_COUNT];                                      \n"
-"in vec2 vPosition;                                                         \n"
-"in vec2 vTexCoords;                                                        \n"
-"out vec2 fTexCoords[LAYER_COUNT];                                          \n"
-"void main() {                                                              \n"
-"  for (int i = 0; i < LAYER_COUNT; i++) {                                  \n"
-"    fTexCoords[i] = (uLayerCrop[i].xy + vTexCoords * uLayerCrop[i].zw) /   \n"
-"                     vec2(textureSize(uLayerTextures[i], 0));              \n"
-"  }                                                                        \n"
-"  vec2 scaledPosition = uViewport.xy + vPosition * uViewport.zw;           \n"
-"  gl_Position = vec4(scaledPosition * vec2(2.0) - vec2(1.0), 0.0, 1.0);    \n"
-"}                                                                          \n";
-
-  const GLchar *fragment_shader_source =
-"\n"
-"precision mediump float;                                                   \n"
-"uniform sampler2D uLayerTextures[LAYER_COUNT];                             \n"
-"uniform float uLayerAlpha[LAYER_COUNT];                                    \n"
-"in vec2 fTexCoords[LAYER_COUNT];                                           \n"
-"out vec4 oFragColor;                                                       \n"
-"void main() {                                                              \n"
-"  vec3 color = vec3(0.0, 0.0, 0.0);                                        \n"
-"  float alphaCover = 1.0;                                                  \n"
-"  for (int i = 0; i < LAYER_COUNT; i++) {                                  \n"
-"    vec4 texSample = texture(uLayerTextures[i], fTexCoords[i]);            \n"
-"    float a = texSample.a * uLayerAlpha[i];                                \n"
-"    color += a * alphaCover * texSample.rgb;                               \n"
-"    alphaCover *= 1.0 - a;                                                 \n"
-"    if (alphaCover <= 0.5/255.0)                                           \n"
-"      break;                                                               \n"
-"  }                                                                        \n"
-"  oFragColor = vec4(color, 1.0 - alphaCover);                              \n"
-"}                                                                          \n";
-  // clang-format on
-
-  int i, ret = 1;
-  GLint max_texture_images, vertex_shader, fragment_shader, program, status;
-  std::string shader_log;
-
-  glGetIntegerv(GL_MAX_TEXTURE_IMAGE_UNITS, &max_texture_images);
-
-  for (i = 1; i <= max_texture_images; i++) {
-    std::ostringstream layer_count_formatter;
-    layer_count_formatter << i;
-    std::string layer_count(layer_count_formatter.str());
-    const GLchar *shader_sources[3] = {shader_preamble, layer_count.c_str(),
-                                       NULL};
-
-    shader_sources[2] = vertex_shader_source;
-    vertex_shader = CompileAndCheckShader(GL_VERTEX_SHADER, 3, shader_sources,
-                                          ret ? &shader_log : NULL);
-    if (!vertex_shader) {
-      if (ret) {
-        ALOGE("Failed to make vertex shader:\n%s", shader_log.c_str());
-      }
-      break;
-    }
-
-    shader_sources[2] = fragment_shader_source;
-    fragment_shader = CompileAndCheckShader(
-        GL_FRAGMENT_SHADER, 3, shader_sources, ret ? &shader_log : NULL);
-    if (!fragment_shader) {
-      if (ret) {
-        ALOGE("Failed to make fragment shader:\n%s", shader_log.c_str());
-      }
-      goto delete_vs;
-    }
-
-    program = glCreateProgram();
-    if (!program) {
-      if (ret)
-        ALOGE("Failed to create program %s", get_gl_error());
-      goto delete_fs;
-    }
-
-    glAttachShader(program, vertex_shader);
-    glAttachShader(program, fragment_shader);
-    glBindAttribLocation(program, 0, "vPosition");
-    glBindAttribLocation(program, 1, "vTexCoords");
-    glLinkProgram(program);
-    glDetachShader(program, vertex_shader);
-    glDeleteShader(vertex_shader);
-    glDetachShader(program, fragment_shader);
-    glDeleteShader(fragment_shader);
-
-    glGetProgramiv(program, GL_LINK_STATUS, &status);
-    if (!status) {
-      if (ret) {
-        GLint log_length;
-        glGetProgramiv(program, GL_INFO_LOG_LENGTH, &log_length);
-        std::string program_log(log_length, ' ');
-        glGetProgramInfoLog(program, log_length, NULL, &program_log[0]);
-        ALOGE("Failed to link program: \n%s", program_log.c_str());
-      }
-      glDeleteProgram(program);
-      break;
-    }
-
-    ret = 0;
-    priv_->blend_programs.push_back(program);
-
-    continue;
-
-  delete_fs:
-    glDeleteShader(fragment_shader);
-
-  delete_vs:
-    glDeleteShader(vertex_shader);
-
-    if (ret)
-      break;
-  }
-
-  return ret;
-}
-
-int GLCompositor::DoComposition(const GLComposition &composition) {
+int GLCompositor::DoComposition(GLComposition *composition) {
   ATRACE_CALL();
   int ret = 0;
-  size_t i;
-  std::vector<struct texture_from_handle> layer_textures;
-  std::vector<RenderingCommand> commands;
 
-  if (composition.layer_data.size() == 0) {
-    return -EALREADY;
+  GLTarget *target = &priv_->targets[composition->target_handle];
+  GLWorker::Work work;
+  work.layers = composition->layers.data();
+  work.num_layers = composition->layers.size();
+  work.timeline_fd = composition->timeline_fd;
+  work.framebuffer = target->fb;
+
+  ret = priv_->worker.DoWork(&work);
+
+  if (work.timeline_fd >= 0) {
+    sw_sync_timeline_inc(work.timeline_fd, work.num_layers + 1);
+    close(work.timeline_fd);
   }
 
-  if (BeginContext()) {
-    return -EINVAL;
-  }
-
-  GLTarget *target = &priv_->targets[composition.target_handle];
-  GLint frame_width = target->fb->getWidth();
-  GLint frame_height = target->fb->getHeight();
-  EGLSyncKHR finished_sync;
-
-  for (i = 0; i < composition.layer_data.size(); i++) {
-    const struct hwc_layer_1 *layer = &composition.layer_data[i].layer;
-
-    if (ret) {
-      if (layer->acquireFenceFd >= 0)
-        close(layer->acquireFenceFd);
-      continue;
-    }
-
-    layer_textures.push_back(texture_from_handle());
-    ret = CreateTextureFromHandle(layer->handle, &layer_textures.back());
-    if (!ret) {
-      ret = DoFenceWait(layer->acquireFenceFd);
-    }
-    if (ret) {
-      layer_textures.pop_back();
-      ret = -EINVAL;
-    }
-  }
-
-  if (ret) {
-    goto destroy_textures;
-  }
-
-  ConstructCommands(composition, &commands);
-
-  glBindFramebuffer(GL_FRAMEBUFFER, target->gl_fb);
-
-  glViewport(0, 0, frame_width, frame_height);
-
-  glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
-  glClear(GL_COLOR_BUFFER_BIT);
-
-  glBindBuffer(GL_ARRAY_BUFFER, priv_->vertex_buffer);
-  glVertexAttribPointer(0, 2, GL_FLOAT, GL_FALSE, sizeof(float) * 4, NULL);
-  glVertexAttribPointer(1, 2, GL_FLOAT, GL_FALSE, sizeof(float) * 4,
-                        (void *)(sizeof(float) * 2));
-  glEnableVertexAttribArray(0);
-  glEnableVertexAttribArray(1);
-
-  for (std::vector<RenderingCommand>::iterator it = commands.begin();
-       it != commands.end(); ++it) {
-    const RenderingCommand &cmd = *it;
-
-    if (cmd.texture_count <= 0) {
-      continue;
-    }
-
-    // TODO(zachr): handle the case of too many overlapping textures for one
-    // area by falling back to rendering as many layers as possible using
-    // multiple blending passes.
-    if (cmd.texture_count > priv_->blend_programs.size()) {
-      ALOGE("Too many layers to render in one area");
-      continue;
-    }
-
-    GLint program = priv_->blend_programs[cmd.texture_count - 1];
-    glUseProgram(program);
-    GLint gl_viewport_loc = glGetUniformLocation(program, "uViewport");
-    GLint gl_tex_loc = glGetUniformLocation(program, "uLayerTextures");
-    GLint gl_crop_loc = glGetUniformLocation(program, "uLayerCrop");
-    GLint gl_alpha_loc = glGetUniformLocation(program, "uLayerAlpha");
-    glUniform4f(gl_viewport_loc, cmd.bounds[0] / (float)frame_width,
-                cmd.bounds[1] / (float)frame_height,
-                (cmd.bounds[2] - cmd.bounds[0]) / (float)frame_width,
-                (cmd.bounds[3] - cmd.bounds[1]) / (float)frame_height);
-
-    for (unsigned src_index = 0; src_index < cmd.texture_count; src_index++) {
-      const RenderingCommand::TextureSource &src = cmd.textures[src_index];
-      glUniform1f(gl_alpha_loc + src_index, src.alpha);
-      glUniform4f(gl_crop_loc + src_index, src.crop_bounds[0],
-                  src.crop_bounds[1], src.crop_bounds[2] - src.crop_bounds[0],
-                  src.crop_bounds[3] - src.crop_bounds[1]);
-
-      glUniform1i(gl_tex_loc + src_index, src_index);
-      glActiveTexture(GL_TEXTURE0 + src_index);
-      glBindTexture(GL_TEXTURE_2D, layer_textures[src.texture_index].texture);
-    }
-
-    glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);
-
-    for (unsigned src_index = 0; src_index < cmd.texture_count; src_index++) {
-      glActiveTexture(GL_TEXTURE0 + src_index);
-      glBindTexture(GL_TEXTURE_2D, 0);
-    }
-  }
-
-  glActiveTexture(GL_TEXTURE0);
-  glDisableVertexAttribArray(0);
-  glDisableVertexAttribArray(1);
-  glBindBuffer(GL_ARRAY_BUFFER, 0);
-  glUseProgram(0);
-
-  glBindFramebuffer(GL_FRAMEBUFFER, 0);
-
-  finished_sync =
-      eglCreateSyncKHR(priv_->egl_display, EGL_SYNC_NATIVE_FENCE_ANDROID, NULL);
-  if (finished_sync != EGL_NO_SYNC_KHR) {
-    glFlush();  // Creates the syncpoint
-    ret = eglDupNativeFenceFDANDROID(priv_->egl_display, finished_sync);
-    eglDestroySyncKHR(priv_->egl_display, finished_sync);
-    if (ret != EGL_NO_NATIVE_FENCE_FD_ANDROID) {
-      goto destroy_textures;
-    }
-  }
-
-  // Used as a fallback if the native sync fence fails.
-  ret = -EALREADY;
-  glFinish();
-
-destroy_textures:
-  for (i = 0; i < layer_textures.size(); i++)
-    DestroyTextureFromHandle(layer_textures[i]);
-
-  EndContext();
-
   return ret;
 }
 
-int GLCompositor::DoFenceWait(int acquireFenceFd) {
-  int ret = 0;
-
-  EGLint attribs[] = {EGL_SYNC_NATIVE_FENCE_FD_ANDROID, acquireFenceFd,
-                      EGL_NONE};
-  EGLSyncKHR egl_sync = eglCreateSyncKHR(
-      priv_->egl_display, EGL_SYNC_NATIVE_FENCE_ANDROID, attribs);
-  if (egl_sync == EGL_NO_SYNC_KHR) {
-    ALOGE("Failed to make EGLSyncKHR from acquireFenceFd: %s", get_egl_error());
-    close(acquireFenceFd);
-    return 1;
-  }
-
-  EGLint success = eglWaitSyncKHR(priv_->egl_display, egl_sync, 0);
-  if (success == EGL_FALSE) {
-    ALOGE("Failed to wait for acquire: %s", get_egl_error());
-    ret = 1;
-  }
-  eglDestroySyncKHR(priv_->egl_display, egl_sync);
-
-  return ret;
-}
-
-int GLCompositor::CreateTextureFromHandle(buffer_handle_t handle,
-                                          struct texture_from_handle *tex) {
-  EGLImageKHR image = eglCreateImageKHR(
-      priv_->egl_display, EGL_NO_CONTEXT, EGL_NATIVE_HANDLE_ANDROID_NVX,
-      (EGLClientBuffer)handle, NULL /* no attribs */);
-
-  if (image == EGL_NO_IMAGE_KHR) {
-    ALOGE("Failed to make image %s %p", get_egl_error(), handle);
-    return 1;
-  }
-
-  glGenTextures(1, &tex->texture);
-  glBindTexture(GL_TEXTURE_2D, tex->texture);
-  glEGLImageTargetTexture2DOES(GL_TEXTURE_2D, (GLeglImageOES)image);
-  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
-  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
-  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
-  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
-
-  tex->image = image;
-
-  return 0;
-}
-
-void GLCompositor::DestroyTextureFromHandle(
-    const struct texture_from_handle &tex) {
-  glDeleteTextures(1, &tex.texture);
-  eglDestroyImageKHR(priv_->egl_display, tex.image);
-}
-
-static const char *get_gl_error(void) {
-  switch (glGetError()) {
-    case GL_NO_ERROR:
-      return "GL_NO_ERROR";
-    case GL_INVALID_ENUM:
-      return "GL_INVALID_ENUM";
-    case GL_INVALID_VALUE:
-      return "GL_INVALID_VALUE";
-    case GL_INVALID_OPERATION:
-      return "GL_INVALID_OPERATION";
-    case GL_INVALID_FRAMEBUFFER_OPERATION:
-      return "GL_INVALID_FRAMEBUFFER_OPERATION";
-    case GL_OUT_OF_MEMORY:
-      return "GL_OUT_OF_MEMORY";
-    default:
-      return "Unknown error";
-  }
-}
-
-static const char *get_egl_error(void) {
-  switch (eglGetError()) {
-    case EGL_SUCCESS:
-      return "EGL_SUCCESS";
-    case EGL_NOT_INITIALIZED:
-      return "EGL_NOT_INITIALIZED";
-    case EGL_BAD_ACCESS:
-      return "EGL_BAD_ACCESS";
-    case EGL_BAD_ALLOC:
-      return "EGL_BAD_ALLOC";
-    case EGL_BAD_ATTRIBUTE:
-      return "EGL_BAD_ATTRIBUTE";
-    case EGL_BAD_CONTEXT:
-      return "EGL_BAD_CONTEXT";
-    case EGL_BAD_CONFIG:
-      return "EGL_BAD_CONFIG";
-    case EGL_BAD_CURRENT_SURFACE:
-      return "EGL_BAD_CURRENT_SURFACE";
-    case EGL_BAD_DISPLAY:
-      return "EGL_BAD_DISPLAY";
-    case EGL_BAD_SURFACE:
-      return "EGL_BAD_SURFACE";
-    case EGL_BAD_MATCH:
-      return "EGL_BAD_MATCH";
-    case EGL_BAD_PARAMETER:
-      return "EGL_BAD_PARAMETER";
-    case EGL_BAD_NATIVE_PIXMAP:
-      return "EGL_BAD_NATIVE_PIXMAP";
-    case EGL_BAD_NATIVE_WINDOW:
-      return "EGL_BAD_NATIVE_WINDOW";
-    case EGL_CONTEXT_LOST:
-      return "EGL_CONTEXT_LOST";
-    default:
-      return "Unknown error";
-  }
-}
-
-static bool has_extension(const char *extension, const char *extensions) {
-  const char *start, *where, *terminator;
-  start = extensions;
-  for (;;) {
-    where = (char *)strstr((const char *)start, extension);
-    if (!where)
-      break;
-    terminator = where + strlen(extension);
-    if (where == start || *(where - 1) == ' ')
-      if (*terminator == ' ' || *terminator == '\0')
-        return true;
-    start = terminator;
-  }
-  return false;
-}
-
 }  // namespace android
