+
+static bool
+tdm_output_set_pending_fb(struct ds_tdm_output *output,
+ struct ds_buffer *ds_buffer)
+{
+ struct ds_tdm_buffer *buffer;
+ tdm_region fb_damage;
+ tdm_error err;
+
+ buffer = get_or_create_tdm_buffer(output->backend, ds_buffer);
+ if (!buffer)
+ return false;
+
+ memset(&fb_damage, 0, sizeof(fb_damage));
+ err = tdm_hwc_set_client_target_buffer(output->tdm.hwc,
+ buffer->surface, fb_damage);
+ if (err != TDM_ERROR_NONE) {
+ ds_err("Could not set hwc client target buffer");
+ ds_buffer_unlock(buffer->buffer);
+ return false;
+ }
+
+ tdm_output_attach_back_buffer(output, buffer);
+
+ return true;
+}
+
+static void
+tdm_output_hwc_commit_handler(tdm_hwc *hwc, unsigned int sequence,
+ unsigned int tv_sec, unsigned int tv_usec, void *user_data)
+{
+ struct ds_tdm_output *output;
+
+ output = user_data;
+
+ tdm_output_update_front_buffer(output);
+
+ wl_signal_emit(&output->base.events.frame, &output->base);
+}
+
+static bool
+tdm_output_hwc_commit(struct ds_tdm_output *output)
+{
+ tdm_error err;
+ uint32_t num_changes;
+
+ err = tdm_hwc_validate(output->tdm.hwc, NULL, 0, &num_changes);
+ if (err != TDM_ERROR_NONE) {
+ ds_err("Could not hwc validate");
+ return false;
+ }
+
+ err = tdm_hwc_accept_validation(output->tdm.hwc);
+ if (err != TDM_ERROR_NONE) {
+ ds_err("Could not hwc accept validation");
+ return false;
+ }
+
+ err = tdm_hwc_commit(output->tdm.hwc, 0, tdm_output_hwc_commit_handler,
+ output);
+ if (err != TDM_ERROR_NONE) {
+ ds_err("Could not hwc commit");
+ return false;
+ }
+
+ return true;
+}