kms/update: Add way to receive result from later posted update
Something might want to affect the next update that is going to be posted, but without posting it immediately. For example, changing the cursor might need to wait for mode setting. Make it possible to get feedback from posting the update, in order to gracefully handle any errors. Note, the API for notifiying about results take out the result listener from the update, and notifies them in an open coded for loop. The reason for this is that in the next commit we'll sometimes reuse updates, and we only want notify about the results once. Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1488>
This commit is contained in:
parent
5c7e2bfe22
commit
afd0a272cd
@ -93,6 +93,12 @@ typedef struct _MetaKmsPageFlipListener
|
||||
gpointer user_data;
|
||||
} MetaKmsPageFlipListener;
|
||||
|
||||
typedef struct _MetaKmsResultListener
|
||||
{
|
||||
MetaKmsResultListenerFunc func;
|
||||
gpointer user_data;
|
||||
} MetaKmsResultListener;
|
||||
|
||||
void meta_kms_plane_feedback_free (MetaKmsPlaneFeedback *plane_feedback);
|
||||
|
||||
MetaKmsPlaneFeedback * meta_kms_plane_feedback_new_take_error (MetaKmsPlane *plane,
|
||||
@ -130,6 +136,13 @@ void meta_kms_update_get_custom_page_flip_func (MetaKmsUpdate *updat
|
||||
MetaKmsCustomPageFlipFunc *custom_page_flip_func,
|
||||
gpointer *custom_page_flip_user_data);
|
||||
|
||||
GList * meta_kms_update_take_result_listeners (MetaKmsUpdate *update);
|
||||
|
||||
void meta_kms_result_listener_notify (MetaKmsResultListener *listener,
|
||||
const MetaKmsFeedback *feedback);
|
||||
|
||||
void meta_kms_result_listener_free (MetaKmsResultListener *listener);
|
||||
|
||||
G_DEFINE_AUTOPTR_CLEANUP_FUNC (MetaKmsPlaneFeedback,
|
||||
meta_kms_plane_feedback_free)
|
||||
|
||||
|
@ -44,6 +44,7 @@ struct _MetaKmsUpdate
|
||||
gpointer custom_page_flip_user_data;
|
||||
|
||||
GList *page_flip_listeners;
|
||||
GList *result_listeners;
|
||||
};
|
||||
|
||||
void
|
||||
@ -379,6 +380,42 @@ meta_kms_plane_assignment_set_cursor_hotspot (MetaKmsPlaneAssignment *plane_assi
|
||||
plane_assignment->cursor_hotspot.y = y;
|
||||
}
|
||||
|
||||
void
|
||||
meta_kms_update_add_result_listener (MetaKmsUpdate *update,
|
||||
MetaKmsResultListenerFunc func,
|
||||
gpointer user_data)
|
||||
{
|
||||
MetaKmsResultListener *listener;
|
||||
|
||||
listener = g_new0 (MetaKmsResultListener, 1);
|
||||
*listener = (MetaKmsResultListener) {
|
||||
.func = func,
|
||||
.user_data = user_data,
|
||||
};
|
||||
|
||||
update->result_listeners = g_list_append (update->result_listeners,
|
||||
listener);
|
||||
}
|
||||
|
||||
GList *
|
||||
meta_kms_update_take_result_listeners (MetaKmsUpdate *update)
|
||||
{
|
||||
return g_steal_pointer (&update->result_listeners);
|
||||
}
|
||||
|
||||
void
|
||||
meta_kms_result_listener_notify (MetaKmsResultListener *listener,
|
||||
const MetaKmsFeedback *feedback)
|
||||
{
|
||||
listener->func (feedback, listener->user_data);
|
||||
}
|
||||
|
||||
void
|
||||
meta_kms_result_listener_free (MetaKmsResultListener *listener)
|
||||
{
|
||||
g_free (listener);
|
||||
}
|
||||
|
||||
MetaKmsPlaneAssignment *
|
||||
meta_kms_update_get_primary_plane_assignment (MetaKmsUpdate *update,
|
||||
MetaKmsCrtc *crtc)
|
||||
@ -467,6 +504,8 @@ meta_kms_update_new (MetaKmsDevice *device)
|
||||
void
|
||||
meta_kms_update_free (MetaKmsUpdate *update)
|
||||
{
|
||||
g_list_free_full (update->result_listeners,
|
||||
(GDestroyNotify) meta_kms_result_listener_free);
|
||||
g_list_free_full (update->plane_assignments,
|
||||
(GDestroyNotify) meta_kms_plane_assignment_free);
|
||||
g_list_free_full (update->mode_sets,
|
||||
|
@ -69,6 +69,9 @@ typedef struct _MetaKmsPlaneFeedback
|
||||
GError *error;
|
||||
} MetaKmsPlaneFeedback;
|
||||
|
||||
typedef void (* MetaKmsResultListenerFunc) (const MetaKmsFeedback *feedback,
|
||||
gpointer user_data);
|
||||
|
||||
void meta_kms_feedback_free (MetaKmsFeedback *feedback);
|
||||
|
||||
MetaKmsFeedbackResult meta_kms_feedback_get_result (const MetaKmsFeedback *feedback);
|
||||
@ -130,6 +133,10 @@ void meta_kms_plane_assignment_set_cursor_hotspot (MetaKmsPlaneAssignment *plane
|
||||
int x,
|
||||
int y);
|
||||
|
||||
void meta_kms_update_add_result_listener (MetaKmsUpdate *update,
|
||||
MetaKmsResultListenerFunc func,
|
||||
gpointer user_data);
|
||||
|
||||
static inline MetaFixed16
|
||||
meta_fixed_16_from_int (int16_t d)
|
||||
{
|
||||
|
@ -251,6 +251,8 @@ meta_kms_post_pending_update_sync (MetaKms *kms,
|
||||
{
|
||||
MetaKmsUpdate *update;
|
||||
MetaKmsFeedback *feedback;
|
||||
GList *result_listeners;
|
||||
GList *l;
|
||||
|
||||
COGL_TRACE_BEGIN_SCOPED (MetaKmsPostUpdateSync,
|
||||
"KMS (post update)");
|
||||
@ -266,6 +268,17 @@ meta_kms_post_pending_update_sync (MetaKms *kms,
|
||||
update,
|
||||
NULL);
|
||||
|
||||
result_listeners = meta_kms_update_take_result_listeners (update);
|
||||
|
||||
for (l = result_listeners; l; l = l->next)
|
||||
{
|
||||
MetaKmsResultListener *listener = l->data;
|
||||
|
||||
meta_kms_result_listener_notify (listener, feedback);
|
||||
meta_kms_result_listener_free (listener);
|
||||
}
|
||||
g_list_free (result_listeners);
|
||||
|
||||
meta_kms_update_free (update);
|
||||
|
||||
return feedback;
|
||||
|
Loading…
Reference in New Issue
Block a user