template<typename T> inline T max(T a, T b) { return (a > b) ? a : b; }
template<typename T> inline T min(T a, T b) { return (a < b) ? a : b; }
+static int dup_or_warn(int fence)
+{
+ int dup_fd = dup(fence);
+ if (dup_fd < 0)
+ ALOGW("fence dup failed: %s", strerror(errno));
+ return dup_fd;
+}
+
+static int merge_or_warn(const char *name, int f1, int f2)
+{
+ int merge_fd = sync_merge(name, f1, f2);
+ if (merge_fd < 0)
+ ALOGW("fence merge failed: %s", strerror(errno));
+ return merge_fd;
+}
+
template<typename T> void align_crop_and_center(T &w, T &h,
hwc_rect_t *crop, size_t alignment)
{
if (pdev->bufs.overlay_map[i] != -1) {
hwc_layer_1_t &layer =
contents->hwLayers[pdev->bufs.overlay_map[i]];
- int dup_fd = dup(fence);
- if (dup_fd < 0)
- ALOGW("release fence dup failed: %s", strerror(errno));
+ int dup_fd = dup_or_warn(fence);
if (pdev->bufs.gsc_map[i].mode == exynos5_gsc_map_t::GSC_M2M) {
int gsc_idx = pdev->bufs.gsc_map[i].idx;
exynos5_gsc_data_t &gsc = pdev->gsc[gsc_idx];
}
}
}
- close(fence);
+ contents->retireFenceFd = fence;
return err;
}
gsc.dst_buf_fence[gsc.current_buf] = releaseFenceFd;
gsc.current_buf = (gsc.current_buf + 1) % NUM_GSC_DST_BUFS;
+ if (contents->retireFenceFd < 0)
+ contents->retireFenceFd = dup_or_warn(releaseFenceFd);
+ else {
+ int merged = merge_or_warn("hdmi",
+ contents->retireFenceFd, layer.releaseFenceFd);
+ close(contents->retireFenceFd);
+ contents->retireFenceFd = merged;
+ }
}
if (layer.compositionType == HWC_FRAMEBUFFER_TARGET) {
hdmi_output(pdev, pdev->hdmi_layers[1], layer, h, layer.acquireFenceFd,
&layer.releaseFenceFd);
fb_layer = &layer;
+ if (contents->retireFenceFd < 0)
+ contents->retireFenceFd = dup_or_warn(layer.releaseFenceFd);
+ else {
+ int merged = merge_or_warn("hdmi",
+ contents->retireFenceFd, layer.releaseFenceFd);
+ close(contents->retireFenceFd);
+ contents->retireFenceFd = merged;
+ }
}
}