mirror of
https://gitlab.freedesktop.org/monado/monado.git
synced 2025-01-28 17:38:27 +00:00
a/util: Have all timestamps be injected into pacing.
No more calling os_monotonic_get_ns() inside the pacing helpers. Much better testability.
This commit is contained in:
parent
40caa24d4b
commit
a2e1eb7e75
|
@ -62,6 +62,8 @@ struct u_pacing_compositor
|
|||
* Predict the next frame.
|
||||
*
|
||||
* @param[in] upc The compositor pacing helper.
|
||||
* @param[in] now_ns The current timestamp in nanoseconds, nominally from @ref
|
||||
* os_monotonic_get_ns
|
||||
* @param[out] out_frame_id Id used to refer to this frame again.
|
||||
* @param[out] out_wake_up_time_ns When should the compositor wake up.
|
||||
* @param[out] out_desired_present_time_ns The GPU should start scanning out at this time.
|
||||
|
@ -73,6 +75,7 @@ struct u_pacing_compositor
|
|||
* @see @ref frame-pacing.
|
||||
*/
|
||||
void (*predict)(struct u_pacing_compositor *upc,
|
||||
uint64_t now_ns,
|
||||
int64_t *out_frame_id,
|
||||
uint64_t *out_wake_up_time_ns,
|
||||
uint64_t *out_desired_present_time_ns,
|
||||
|
@ -118,6 +121,8 @@ struct u_pacing_compositor
|
|||
* actual_present_time_ns if a @p desired_present_time_ns was passed.
|
||||
* @param[in] present_margin_ns How "early" present happened compared to when it needed to happen in
|
||||
* order to hit @p earliestPresentTime.
|
||||
* @param[in] when_ns The time when we got the info, nominally from @ref
|
||||
* os_monotonic_get_ns
|
||||
*
|
||||
* @see @ref frame-pacing.
|
||||
*/
|
||||
|
@ -126,7 +131,8 @@ struct u_pacing_compositor
|
|||
uint64_t desired_present_time_ns,
|
||||
uint64_t actual_present_time_ns,
|
||||
uint64_t earliest_present_time_ns,
|
||||
uint64_t present_margin_ns);
|
||||
uint64_t present_margin_ns,
|
||||
uint64_t when_ns);
|
||||
|
||||
/*!
|
||||
* Destroy this u_pacing_compositor.
|
||||
|
@ -144,6 +150,7 @@ struct u_pacing_compositor
|
|||
*/
|
||||
static inline void
|
||||
u_pc_predict(struct u_pacing_compositor *upc,
|
||||
uint64_t now_ns,
|
||||
int64_t *out_frame_id,
|
||||
uint64_t *out_wake_up_time_ns,
|
||||
uint64_t *out_desired_present_time_ns,
|
||||
|
@ -153,6 +160,7 @@ u_pc_predict(struct u_pacing_compositor *upc,
|
|||
uint64_t *out_min_display_period_ns)
|
||||
{
|
||||
upc->predict(upc, //
|
||||
now_ns, //
|
||||
out_frame_id, //
|
||||
out_wake_up_time_ns, //
|
||||
out_desired_present_time_ns, //
|
||||
|
@ -190,10 +198,11 @@ u_pc_info(struct u_pacing_compositor *upc,
|
|||
uint64_t desired_present_time_ns,
|
||||
uint64_t actual_present_time_ns,
|
||||
uint64_t earliest_present_time_ns,
|
||||
uint64_t present_margin_ns)
|
||||
uint64_t present_margin_ns,
|
||||
uint64_t when_ns)
|
||||
{
|
||||
upc->info(upc, frame_id, desired_present_time_ns, actual_present_time_ns, earliest_present_time_ns,
|
||||
present_margin_ns);
|
||||
present_margin_ns, when_ns);
|
||||
}
|
||||
|
||||
/*!
|
||||
|
@ -244,12 +253,15 @@ struct u_pacing_app
|
|||
* should wait till `out_wake_up_time`.
|
||||
*
|
||||
* @param upa Render timing helper.
|
||||
* @param[in] now_ns The current timestamp in nanoseconds, nominally from @ref
|
||||
* os_monotonic_get_ns
|
||||
* @param[out] out_frame_id Frame ID of this predicted frame.
|
||||
* @param[out] out_wake_up_time When the client should be woken up.
|
||||
* @param[out] out_predicted_display_time Predicted display time.
|
||||
* @param[out] out_predicted_display_period Predicted display period.
|
||||
*/
|
||||
void (*predict)(struct u_pacing_app *upa,
|
||||
uint64_t now_ns,
|
||||
int64_t *out_frame_id,
|
||||
uint64_t *out_wake_up_time,
|
||||
uint64_t *out_predicted_display_time,
|
||||
|
@ -272,8 +284,9 @@ struct u_pacing_app
|
|||
*
|
||||
* @param upa Render timing helper.
|
||||
* @param[in] frame_id The frame ID to mark as discarded.
|
||||
* @param[in] when_ns The time when it was discarded, nominally from @ref os_monotonic_get_ns
|
||||
*/
|
||||
void (*mark_discarded)(struct u_pacing_app *upa, int64_t frame_id);
|
||||
void (*mark_discarded)(struct u_pacing_app *upa, int64_t frame_id, uint64_t when_ns);
|
||||
|
||||
/*!
|
||||
* A frame has been delivered from the client, see `xrEndFrame`. The GPU might
|
||||
|
@ -281,8 +294,9 @@ struct u_pacing_app
|
|||
*
|
||||
* @param upa Render timing helper.
|
||||
* @param[in] frame_id The frame ID to mark as delivered.
|
||||
* @param[in] when_ns The time when it was delivered, nominally from @ref os_monotonic_get_ns
|
||||
*/
|
||||
void (*mark_delivered)(struct u_pacing_app *upa, int64_t frame_id);
|
||||
void (*mark_delivered)(struct u_pacing_app *upa, int64_t frame_id, uint64_t when_ns);
|
||||
|
||||
/*!
|
||||
* Add a new sample point from the main render loop.
|
||||
|
@ -323,12 +337,14 @@ struct u_pacing_app
|
|||
*/
|
||||
static inline void
|
||||
u_pa_predict(struct u_pacing_app *upa,
|
||||
uint64_t now_ns,
|
||||
int64_t *out_frame_id,
|
||||
uint64_t *out_wake_up_time,
|
||||
uint64_t *out_predicted_display_time,
|
||||
uint64_t *out_predicted_display_period)
|
||||
{
|
||||
upa->predict(upa, out_frame_id, out_wake_up_time, out_predicted_display_time, out_predicted_display_period);
|
||||
upa->predict(upa, now_ns, out_frame_id, out_wake_up_time, out_predicted_display_time,
|
||||
out_predicted_display_period);
|
||||
}
|
||||
|
||||
/*!
|
||||
|
@ -354,9 +370,9 @@ u_pa_mark_point(struct u_pacing_app *upa, int64_t frame_id, enum u_timing_point
|
|||
* @ingroup aux_pacing
|
||||
*/
|
||||
static inline void
|
||||
u_pa_mark_discarded(struct u_pacing_app *upa, int64_t frame_id)
|
||||
u_pa_mark_discarded(struct u_pacing_app *upa, int64_t frame_id, uint64_t when_ns)
|
||||
{
|
||||
upa->mark_discarded(upa, frame_id);
|
||||
upa->mark_discarded(upa, frame_id, when_ns);
|
||||
}
|
||||
|
||||
/*!
|
||||
|
@ -368,9 +384,9 @@ u_pa_mark_discarded(struct u_pacing_app *upa, int64_t frame_id)
|
|||
* @ingroup aux_pacing
|
||||
*/
|
||||
static inline void
|
||||
u_pa_mark_delivered(struct u_pacing_app *upa, int64_t frame_id)
|
||||
u_pa_mark_delivered(struct u_pacing_app *upa, int64_t frame_id, uint64_t when_ns)
|
||||
{
|
||||
upa->mark_delivered(upa, frame_id);
|
||||
upa->mark_delivered(upa, frame_id, when_ns);
|
||||
}
|
||||
|
||||
/*!
|
||||
|
@ -477,11 +493,15 @@ u_pc_display_timing_create(uint64_t estimated_frame_period_ns,
|
|||
*
|
||||
* When you cannot get display timing information, use this.
|
||||
*
|
||||
* @param[in] estimated_frame_period_ns The estimated duration/period of a frame in nanoseconds.
|
||||
* @param[in] now_ns The current timestamp in nanoseconds, nominally from @ref os_monotonic_get_ns
|
||||
* @param[out] out_upc The pointer to populate with the created compositor pacing helper
|
||||
*
|
||||
* @ingroup aux_pacing
|
||||
* @see u_pacing_compositor
|
||||
*/
|
||||
xrt_result_t
|
||||
u_pc_fake_create(uint64_t estimated_frame_period_ns, struct u_pacing_compositor **out_upc);
|
||||
u_pc_fake_create(uint64_t estimated_frame_period_ns, uint64_t now_ns, struct u_pacing_compositor **out_upc);
|
||||
|
||||
/*!
|
||||
* Creates a new application pacing helper.
|
||||
|
|
|
@ -188,11 +188,8 @@ calc_period(const struct pacing_app *pa)
|
|||
}
|
||||
|
||||
static uint64_t
|
||||
predict_display_time(const struct pacing_app *pa, uint64_t period_ns)
|
||||
predict_display_time(const struct pacing_app *pa, uint64_t now_ns, uint64_t period_ns)
|
||||
{
|
||||
// Now
|
||||
uint64_t now_ns = os_monotonic_get_ns();
|
||||
|
||||
|
||||
// Total app and compositor time to produce a frame
|
||||
uint64_t app_and_compositor_time_ns = total_app_and_compositor_time_ns(pa);
|
||||
|
@ -222,6 +219,7 @@ predict_display_time(const struct pacing_app *pa, uint64_t period_ns)
|
|||
|
||||
static void
|
||||
pa_predict(struct u_pacing_app *upa,
|
||||
uint64_t now_ns,
|
||||
int64_t *out_frame_id,
|
||||
uint64_t *out_wake_up_time,
|
||||
uint64_t *out_predicted_display_time,
|
||||
|
@ -235,7 +233,7 @@ pa_predict(struct u_pacing_app *upa,
|
|||
DEBUG_PRINT_FRAME_ID();
|
||||
|
||||
uint64_t period_ns = calc_period(pa);
|
||||
uint64_t predict_ns = predict_display_time(pa, period_ns);
|
||||
uint64_t predict_ns = predict_display_time(pa, now_ns, period_ns);
|
||||
// When should the client wake up.
|
||||
uint64_t wake_up_time_ns = predict_ns - total_app_and_compositor_time_ns(pa);
|
||||
// When the client should deliver the frame to us.
|
||||
|
@ -255,7 +253,7 @@ pa_predict(struct u_pacing_app *upa,
|
|||
pa->frames[index].frame_id = frame_id;
|
||||
pa->frames[index].predicted_delivery_time_ns = delivery_time_ns;
|
||||
pa->frames[index].predicted_display_period_ns = period_ns;
|
||||
pa->frames[index].when.predicted_ns = os_monotonic_get_ns();
|
||||
pa->frames[index].when.predicted_ns = now_ns;
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -278,7 +276,7 @@ pa_mark_point(struct u_pacing_app *upa, int64_t frame_id, enum u_timing_point po
|
|||
case U_TIMING_POINT_BEGIN:
|
||||
assert(pa->frames[index].state == U_RT_WAIT_LEFT);
|
||||
|
||||
pa->frames[index].when.begin_ns = os_monotonic_get_ns();
|
||||
pa->frames[index].when.begin_ns = when_ns;
|
||||
pa->frames[index].state = U_RT_BEGUN;
|
||||
break;
|
||||
case U_TIMING_POINT_SUBMIT:
|
||||
|
@ -287,7 +285,7 @@ pa_mark_point(struct u_pacing_app *upa, int64_t frame_id, enum u_timing_point po
|
|||
}
|
||||
|
||||
static void
|
||||
pa_mark_discarded(struct u_pacing_app *upa, int64_t frame_id)
|
||||
pa_mark_discarded(struct u_pacing_app *upa, int64_t frame_id, uint64_t when_ns)
|
||||
{
|
||||
struct pacing_app *pa = pacing_app(upa);
|
||||
|
||||
|
@ -297,13 +295,13 @@ pa_mark_discarded(struct u_pacing_app *upa, int64_t frame_id)
|
|||
assert(pa->frames[index].frame_id == frame_id);
|
||||
assert(pa->frames[index].state == U_RT_WAIT_LEFT || pa->frames[index].state == U_RT_BEGUN);
|
||||
|
||||
pa->frames[index].when.delivered_ns = os_monotonic_get_ns();
|
||||
pa->frames[index].when.delivered_ns = when_ns;
|
||||
pa->frames[index].state = U_PA_READY;
|
||||
pa->frames[index].frame_id = -1;
|
||||
}
|
||||
|
||||
static void
|
||||
pa_mark_delivered(struct u_pacing_app *upa, int64_t frame_id)
|
||||
pa_mark_delivered(struct u_pacing_app *upa, int64_t frame_id, uint64_t when_ns)
|
||||
{
|
||||
struct pacing_app *pa = pacing_app(upa);
|
||||
|
||||
|
@ -314,17 +312,15 @@ pa_mark_delivered(struct u_pacing_app *upa, int64_t frame_id)
|
|||
assert(f->frame_id == frame_id);
|
||||
assert(f->state == U_RT_BEGUN);
|
||||
|
||||
uint64_t now_ns = os_monotonic_get_ns();
|
||||
|
||||
// Update all data.
|
||||
f->when.delivered_ns = now_ns;
|
||||
f->when.delivered_ns = when_ns;
|
||||
|
||||
|
||||
/*
|
||||
* Process data.
|
||||
*/
|
||||
|
||||
int64_t diff_ns = f->predicted_delivery_time_ns - now_ns;
|
||||
int64_t diff_ns = f->predicted_delivery_time_ns - when_ns;
|
||||
bool late = false;
|
||||
if (diff_ns < 0) {
|
||||
diff_ns = -diff_ns;
|
||||
|
|
|
@ -259,13 +259,12 @@ get_latest_frame_with_state_at_least(struct display_timing *dt, enum frame_state
|
|||
* frame::desired_present_time_ns (with a crude estimate) and frame::when_predict_ns.
|
||||
*/
|
||||
static struct frame *
|
||||
do_clean_slate_frame(struct display_timing *dt)
|
||||
do_clean_slate_frame(struct display_timing *dt, uint64_t now_ns)
|
||||
{
|
||||
struct frame *f = create_frame(dt, STATE_PREDICTED);
|
||||
uint64_t now_ns = os_monotonic_get_ns();
|
||||
|
||||
// Wild shot in the dark.
|
||||
uint64_t the_time_ns = os_monotonic_get_ns() + dt->frame_period_ns * 10;
|
||||
uint64_t the_time_ns = now_ns + dt->frame_period_ns * 10;
|
||||
f->when_predict_ns = now_ns;
|
||||
f->desired_present_time_ns = the_time_ns;
|
||||
|
||||
|
@ -277,9 +276,8 @@ do_clean_slate_frame(struct display_timing *dt)
|
|||
* prediction in it.
|
||||
*/
|
||||
static struct frame *
|
||||
walk_forward_through_frames(struct display_timing *dt, uint64_t last_present_time_ns)
|
||||
walk_forward_through_frames(struct display_timing *dt, uint64_t last_present_time_ns, uint64_t now_ns)
|
||||
{
|
||||
uint64_t now_ns = os_monotonic_get_ns();
|
||||
// This is the earliest possible time we could present, assuming rendering still must take place.
|
||||
uint64_t from_time_ns = now_ns + calc_total_app_time(dt);
|
||||
uint64_t desired_present_time_ns = last_present_time_ns + dt->frame_period_ns;
|
||||
|
@ -306,17 +304,17 @@ walk_forward_through_frames(struct display_timing *dt, uint64_t last_present_tim
|
|||
}
|
||||
|
||||
static struct frame *
|
||||
predict_next_frame(struct display_timing *dt)
|
||||
predict_next_frame(struct display_timing *dt, uint64_t now_ns)
|
||||
{
|
||||
struct frame *f = NULL;
|
||||
// Last earliest display time, can be zero.
|
||||
struct frame *last_predicted = get_latest_frame_with_state_at_least(dt, STATE_PREDICTED);
|
||||
struct frame *last_completed = get_latest_frame_with_state_at_least(dt, STATE_INFO);
|
||||
if (last_predicted == NULL && last_completed == NULL) {
|
||||
f = do_clean_slate_frame(dt);
|
||||
f = do_clean_slate_frame(dt, now_ns);
|
||||
} else if (last_completed == last_predicted) {
|
||||
// Very high propability that we missed a frame.
|
||||
f = walk_forward_through_frames(dt, last_completed->earliest_present_time_ns);
|
||||
f = walk_forward_through_frames(dt, last_completed->earliest_present_time_ns, now_ns);
|
||||
} else if (last_completed != NULL) {
|
||||
assert(last_predicted != NULL);
|
||||
assert(last_predicted->frame_id > last_completed->frame_id);
|
||||
|
@ -342,11 +340,11 @@ predict_next_frame(struct display_timing *dt)
|
|||
diff_id = 1;
|
||||
}
|
||||
|
||||
f = walk_forward_through_frames(dt, adjusted_last_present_time_ns);
|
||||
f = walk_forward_through_frames(dt, adjusted_last_present_time_ns, now_ns);
|
||||
} else {
|
||||
assert(last_predicted != NULL);
|
||||
|
||||
f = walk_forward_through_frames(dt, last_predicted->predicted_display_time_ns);
|
||||
f = walk_forward_through_frames(dt, last_predicted->predicted_display_time_ns, now_ns);
|
||||
}
|
||||
|
||||
f->predicted_display_time_ns = calc_display_time_from_present_time(dt, f->desired_present_time_ns);
|
||||
|
@ -404,6 +402,7 @@ adjust_app_time(struct display_timing *dt, struct frame *f)
|
|||
|
||||
static void
|
||||
dt_predict(struct u_pacing_compositor *upc,
|
||||
uint64_t now_ns,
|
||||
int64_t *out_frame_id,
|
||||
uint64_t *out_wake_up_time_ns,
|
||||
uint64_t *out_desired_present_time_ns,
|
||||
|
@ -414,7 +413,7 @@ dt_predict(struct u_pacing_compositor *upc,
|
|||
{
|
||||
struct display_timing *dt = display_timing(upc);
|
||||
|
||||
struct frame *f = predict_next_frame(dt);
|
||||
struct frame *f = predict_next_frame(dt, now_ns);
|
||||
|
||||
uint64_t wake_up_time_ns = f->wake_up_time_ns;
|
||||
uint64_t desired_present_time_ns = f->desired_present_time_ns;
|
||||
|
@ -464,7 +463,8 @@ dt_info(struct u_pacing_compositor *upc,
|
|||
uint64_t desired_present_time_ns,
|
||||
uint64_t actual_present_time_ns,
|
||||
uint64_t earliest_present_time_ns,
|
||||
uint64_t present_margin_ns)
|
||||
uint64_t present_margin_ns,
|
||||
uint64_t when_ns)
|
||||
{
|
||||
struct display_timing *dt = display_timing(upc);
|
||||
(void)dt;
|
||||
|
@ -481,7 +481,7 @@ dt_info(struct u_pacing_compositor *upc,
|
|||
assert(f->state == STATE_SUBMITTED);
|
||||
assert(f->desired_present_time_ns == desired_present_time_ns);
|
||||
|
||||
f->when_infoed_ns = os_monotonic_get_ns();
|
||||
f->when_infoed_ns = when_ns;
|
||||
f->actual_present_time_ns = actual_present_time_ns;
|
||||
f->earliest_present_time_ns = earliest_present_time_ns;
|
||||
f->present_margin_ns = present_margin_ns;
|
||||
|
|
|
@ -69,10 +69,9 @@ fake_timing(struct u_pacing_compositor *upc)
|
|||
}
|
||||
|
||||
static uint64_t
|
||||
predict_next_frame(struct fake_timing *ft)
|
||||
predict_next_frame(struct fake_timing *ft, uint64_t now_ns)
|
||||
{
|
||||
uint64_t time_needed_ns = ft->present_offset_ns + ft->app_time_ns;
|
||||
uint64_t now_ns = os_monotonic_get_ns();
|
||||
uint64_t predicted_display_time_ns = ft->last_display_time_ns + ft->frame_period_ns;
|
||||
|
||||
while (now_ns + time_needed_ns > predicted_display_time_ns) {
|
||||
|
@ -98,6 +97,7 @@ get_percent_of_time(uint64_t time_ns, uint32_t fraction_percent)
|
|||
|
||||
static void
|
||||
pc_predict(struct u_pacing_compositor *upc,
|
||||
uint64_t now_ns,
|
||||
int64_t *out_frame_id,
|
||||
uint64_t *out_wake_up_time_ns,
|
||||
uint64_t *out_desired_present_time_ns,
|
||||
|
@ -109,7 +109,7 @@ pc_predict(struct u_pacing_compositor *upc,
|
|||
struct fake_timing *ft = fake_timing(upc);
|
||||
|
||||
int64_t frame_id = ft->frame_id_generator++;
|
||||
uint64_t predicted_display_time_ns = predict_next_frame(ft);
|
||||
uint64_t predicted_display_time_ns = predict_next_frame(ft, now_ns);
|
||||
uint64_t desired_present_time_ns = predicted_display_time_ns - ft->present_offset_ns;
|
||||
uint64_t wake_up_time_ns = desired_present_time_ns - ft->app_time_ns;
|
||||
uint64_t present_slop_ns = U_TIME_HALF_MS_IN_NS;
|
||||
|
@ -143,7 +143,8 @@ pc_info(struct u_pacing_compositor *upc,
|
|||
uint64_t desired_present_time_ns,
|
||||
uint64_t actual_present_time_ns,
|
||||
uint64_t earliest_present_time_ns,
|
||||
uint64_t present_margin_ns)
|
||||
uint64_t present_margin_ns,
|
||||
uint64_t when_ns)
|
||||
{
|
||||
/*
|
||||
* The compositor might call this function because it selected the
|
||||
|
@ -166,7 +167,7 @@ pc_destroy(struct u_pacing_compositor *upc)
|
|||
*/
|
||||
|
||||
xrt_result_t
|
||||
u_pc_fake_create(uint64_t estimated_frame_period_ns, struct u_pacing_compositor **out_uft)
|
||||
u_pc_fake_create(uint64_t estimated_frame_period_ns, uint64_t now_ns, struct u_pacing_compositor **out_uft)
|
||||
{
|
||||
struct fake_timing *ft = U_TYPED_CALLOC(struct fake_timing);
|
||||
ft->base.predict = pc_predict;
|
||||
|
@ -185,7 +186,7 @@ u_pc_fake_create(uint64_t estimated_frame_period_ns, struct u_pacing_compositor
|
|||
ft->app_time_ns = get_percent_of_time(estimated_frame_period_ns, 20);
|
||||
|
||||
// Make the next display time be in the future.
|
||||
ft->last_display_time_ns = os_monotonic_get_ns() + U_TIME_1MS_IN_NS * 50.0;
|
||||
ft->last_display_time_ns = now_ns + U_TIME_1MS_IN_NS * 50.0;
|
||||
|
||||
// Return value.
|
||||
*out_uft = &ft->base;
|
||||
|
|
|
@ -123,13 +123,14 @@ comp_target_swapchain_create_images(struct comp_target *ct,
|
|||
VkBool32 supported;
|
||||
VkResult ret;
|
||||
|
||||
uint64_t now_ns = os_monotonic_get_ns();
|
||||
// Some platforms really don't like the display_timing code.
|
||||
bool use_display_timing_if_available = cts->timing_usage == COMP_TARGET_USE_DISPLAY_IF_AVAILABLE;
|
||||
if (cts->upc == NULL && use_display_timing_if_available && vk->has_GOOGLE_display_timing) {
|
||||
u_pc_display_timing_create(ct->c->settings.nominal_frame_interval_ns,
|
||||
&U_PC_DISPLAY_TIMING_CONFIG_DEFAULT, &cts->upc);
|
||||
} else if (cts->upc == NULL) {
|
||||
u_pc_fake_create(ct->c->settings.nominal_frame_interval_ns, &cts->upc);
|
||||
u_pc_fake_create(ct->c->settings.nominal_frame_interval_ns, now_ns, &cts->upc);
|
||||
}
|
||||
|
||||
// Free old image views.
|
||||
|
@ -598,8 +599,10 @@ comp_target_swapchain_calc_frame_pacing(struct comp_target *ct,
|
|||
uint64_t predicted_display_time_ns = 0;
|
||||
uint64_t predicted_display_period_ns = 0;
|
||||
uint64_t min_display_period_ns = 0;
|
||||
uint64_t now_ns = os_monotonic_get_ns();
|
||||
|
||||
u_pc_predict(cts->upc, //
|
||||
now_ns, //
|
||||
&frame_id, //
|
||||
&wake_up_time_ns, //
|
||||
&desired_present_time_ns, //
|
||||
|
@ -670,14 +673,15 @@ comp_target_swapchain_update_timings(struct comp_target *ct)
|
|||
cts->swapchain.handle, //
|
||||
&count, //
|
||||
timings); //
|
||||
|
||||
uint64_t now_ns = os_monotonic_get_ns();
|
||||
for (uint32_t i = 0; i < count; i++) {
|
||||
u_pc_info(cts->upc, //
|
||||
timings[i].presentID, //
|
||||
timings[i].desiredPresentTime, //
|
||||
timings[i].actualPresentTime, //
|
||||
timings[i].earliestPresentTime, //
|
||||
timings[i].presentMargin); //
|
||||
timings[i].presentMargin, //
|
||||
now_ns); //
|
||||
}
|
||||
free(timings);
|
||||
return VK_SUCCESS;
|
||||
|
|
|
@ -194,11 +194,12 @@ multi_compositor_predict_frame(struct xrt_compositor *xc,
|
|||
COMP_TRACE_MARKER();
|
||||
|
||||
struct multi_compositor *mc = multi_compositor(xc);
|
||||
|
||||
uint64_t now_ns = os_monotonic_get_ns();
|
||||
os_mutex_lock(&mc->msc->list_and_timing_lock);
|
||||
|
||||
u_pa_predict( //
|
||||
mc->upa, //
|
||||
now_ns, //
|
||||
out_frame_id, //
|
||||
out_wake_time_ns, //
|
||||
out_predicted_display_time_ns, //
|
||||
|
@ -290,9 +291,10 @@ multi_compositor_discard_frame(struct xrt_compositor *xc, int64_t frame_id)
|
|||
COMP_TRACE_MARKER();
|
||||
|
||||
struct multi_compositor *mc = multi_compositor(xc);
|
||||
uint64_t now_ns = os_monotonic_get_ns();
|
||||
|
||||
os_mutex_lock(&mc->msc->list_and_timing_lock);
|
||||
u_pa_mark_discarded(mc->upa, frame_id);
|
||||
u_pa_mark_discarded(mc->upa, frame_id, now_ns);
|
||||
os_mutex_unlock(&mc->msc->list_and_timing_lock);
|
||||
|
||||
return XRT_SUCCESS;
|
||||
|
@ -507,9 +509,10 @@ multi_compositor_layer_commit(struct xrt_compositor *xc, int64_t frame_id, xrt_g
|
|||
}
|
||||
|
||||
wait_for_scheduled_free(mc);
|
||||
uint64_t now_ns = os_monotonic_get_ns();
|
||||
|
||||
os_mutex_lock(&mc->msc->list_and_timing_lock);
|
||||
u_pa_mark_delivered(mc->upa, frame_id);
|
||||
u_pa_mark_delivered(mc->upa, frame_id, now_ns);
|
||||
os_mutex_unlock(&mc->msc->list_and_timing_lock);
|
||||
|
||||
return XRT_SUCCESS;
|
||||
|
|
Loading…
Reference in a new issue