mirror of
https://gitlab.freedesktop.org/pipewire/wireplumber.git
synced 2026-02-04 10:50:28 +01:00
m-std-event-source: use type-specific event names and multiple object managers
It is better to have type-specific event names to minimize the amount of constraint string matches we do on hooks, as most hooks (if not all) are interested on specific types of objects only. Similarly, use a different object manager for each object type to minimize the performance impact of iterations and lookups, as all such actions are interested in only 1 object type every time. Port all existing hooks to the new event names and the get-object-manager API.
This commit is contained in:
parent
54b14d1a29
commit
bcb4e80723
13 changed files with 193 additions and 171 deletions
|
|
@ -154,8 +154,7 @@ wp_default_nodes_api_enable (WpPlugin * plugin, WpTransition * transition)
|
|||
WP_EVENT_HOOK_PRIORITY_NORMAL, WP_EVENT_HOOK_EXEC_TYPE_ON_EVENT,
|
||||
g_cclosure_new ((GCallback) on_metadata_added, self, NULL));
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "object-added",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "metadata",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "metadata-added",
|
||||
WP_CONSTRAINT_TYPE_PW_GLOBAL_PROPERTY, "metadata.name", "=s", "default",
|
||||
NULL);
|
||||
wp_event_dispatcher_register_hook (dispatcher, hook);
|
||||
|
|
@ -167,24 +166,21 @@ wp_default_nodes_api_enable (WpPlugin * plugin, WpTransition * transition)
|
|||
g_cclosure_new ((GCallback) on_metadata_changed_hook, self, NULL));
|
||||
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "object-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "metadata",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "metadata-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.key", "=s",
|
||||
"default.audio.sink",
|
||||
WP_CONSTRAINT_TYPE_PW_GLOBAL_PROPERTY, "metadata.name", "=s", "default",
|
||||
NULL);
|
||||
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "object-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "metadata",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "metadata-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.key", "=s",
|
||||
"default.video.sink",
|
||||
WP_CONSTRAINT_TYPE_PW_GLOBAL_PROPERTY, "metadata.name", "=s", "default",
|
||||
NULL);
|
||||
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "object-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "metadata",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "metadata-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.key", "=s",
|
||||
"default.audio.source",
|
||||
WP_CONSTRAINT_TYPE_PW_GLOBAL_PROPERTY, "metadata.name", "=s", "default",
|
||||
|
|
|
|||
|
|
@ -595,8 +595,7 @@ wp_default_nodes_enable (WpPlugin * plugin, WpTransition * transition)
|
|||
WP_EVENT_HOOK_PRIORITY_NORMAL, WP_EVENT_HOOK_EXEC_TYPE_ON_EVENT,
|
||||
g_cclosure_new ((GCallback) on_metadata_added, self, NULL));
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "object-added",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "metadata",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "metadata-added",
|
||||
WP_CONSTRAINT_TYPE_PW_GLOBAL_PROPERTY, "metadata.name", "=s", "default",
|
||||
NULL);
|
||||
wp_event_dispatcher_register_hook (dispatcher, hook);
|
||||
|
|
@ -608,24 +607,21 @@ wp_default_nodes_enable (WpPlugin * plugin, WpTransition * transition)
|
|||
g_cclosure_new ((GCallback) on_metadata_changed, self, NULL));
|
||||
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "object-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "metadata",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "metadata-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.key", "=s",
|
||||
"default.configured.audio.sink",
|
||||
WP_CONSTRAINT_TYPE_PW_GLOBAL_PROPERTY, "metadata.name", "=s", "default",
|
||||
NULL);
|
||||
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "object-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "metadata",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "metadata-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.key", "=s",
|
||||
"default.configured.video.sink",
|
||||
WP_CONSTRAINT_TYPE_PW_GLOBAL_PROPERTY, "metadata.name", "=s", "default",
|
||||
NULL);
|
||||
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "object-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "metadata",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "metadata-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.key", "=s",
|
||||
"default.configured.audio.source",
|
||||
WP_CONSTRAINT_TYPE_PW_GLOBAL_PROPERTY, "metadata.name", "=s", "default",
|
||||
|
|
@ -641,53 +637,46 @@ wp_default_nodes_enable (WpPlugin * plugin, WpTransition * transition)
|
|||
|
||||
/* default.configured.audio.sink changed */
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "object-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "metadata",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "metadata-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.key", "=s", "default.configured.audio.sink",
|
||||
WP_CONSTRAINT_TYPE_PW_GLOBAL_PROPERTY, "metadata.name", "=s", "default",
|
||||
NULL);
|
||||
|
||||
/* default.configured.video.sink changed */
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "object-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "metadata",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "metadata-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.key", "=s", "default.configured.video.sink",
|
||||
WP_CONSTRAINT_TYPE_PW_GLOBAL_PROPERTY, "metadata.name", "=s", "default",
|
||||
NULL);
|
||||
|
||||
/* default.configured.audio.source changed */
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "object-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "metadata",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "metadata-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.key", "=s", "default.configured.audio.source",
|
||||
WP_CONSTRAINT_TYPE_PW_GLOBAL_PROPERTY, "metadata.name", "=s", "default",
|
||||
NULL);
|
||||
|
||||
/* new video device node added */
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "object-added",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "node",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "node-added",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "media.class", "#s", "Video/*",
|
||||
NULL);
|
||||
|
||||
/* new audio device node added */
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "object-added",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "node",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "node-added",
|
||||
WP_CONSTRAINT_TYPE_PW_GLOBAL_PROPERTY, "media.class", "#s", "Audio/*",
|
||||
NULL);
|
||||
|
||||
/* video device node removed */
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "object-removed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "node",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "node-removed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "media.class", "#s", "Video/*",
|
||||
NULL);
|
||||
|
||||
/* audio device node removed */
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "object-removed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "node",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "node-removed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "media.class", "#s", "Audio/*",
|
||||
NULL);
|
||||
|
||||
|
|
|
|||
|
|
@ -272,8 +272,7 @@ wp_default_profile_enable (WpPlugin * plugin, WpTransition * transition)
|
|||
WP_EVENT_HOOK_PRIORITY_NORMAL, WP_EVENT_HOOK_EXEC_TYPE_ON_EVENT,
|
||||
g_cclosure_new ((GCallback) on_device_added, self, NULL));
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "object-added",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "device",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "device-added",
|
||||
NULL);
|
||||
wp_event_dispatcher_register_hook (dispatcher, hook);
|
||||
g_clear_object (&hook);
|
||||
|
|
@ -283,13 +282,11 @@ wp_default_profile_enable (WpPlugin * plugin, WpTransition * transition)
|
|||
WP_EVENT_HOOK_PRIORITY_NORMAL, WP_EVENT_HOOK_EXEC_TYPE_ON_EVENT,
|
||||
g_cclosure_new ((GCallback) on_device_params_changed_hook, self, NULL));
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "params-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "device",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "device-params-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.param-id", "=s", "EnumProfile",
|
||||
NULL);
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "params-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.type", "=s", "device",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "device-params-changed",
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.subject.param-id", "=s", "Profile",
|
||||
NULL);
|
||||
wp_event_dispatcher_register_hook (dispatcher, hook);
|
||||
|
|
|
|||
|
|
@ -14,21 +14,32 @@
|
|||
*/
|
||||
|
||||
enum {
|
||||
PROP_0,
|
||||
PROP_OBJECT_MANAGER,
|
||||
};
|
||||
|
||||
enum {
|
||||
ACTION_GET_OBJECT_MANAGER,
|
||||
ACTION_PUSH_EVENT,
|
||||
ACTION_SCHEDULE_RESCAN,
|
||||
N_SIGNALS
|
||||
};
|
||||
|
||||
typedef enum {
|
||||
OBJECT_TYPE_PORT,
|
||||
OBJECT_TYPE_LINK,
|
||||
OBJECT_TYPE_NODE,
|
||||
OBJECT_TYPE_SESSION_ITEM,
|
||||
OBJECT_TYPE_ENDPOINT,
|
||||
OBJECT_TYPE_CLIENT,
|
||||
OBJECT_TYPE_DEVICE,
|
||||
OBJECT_TYPE_METADATA,
|
||||
N_OBJECT_TYPES,
|
||||
OBJECT_TYPE_INVALID = N_OBJECT_TYPES
|
||||
} ObjectType;
|
||||
|
||||
struct _WpStandardEventSource
|
||||
{
|
||||
WpPlugin parent;
|
||||
WpObjectManager *om;
|
||||
WpObjectManager *oms[N_OBJECT_TYPES];
|
||||
WpEventHook *rescan_done_hook;
|
||||
gboolean rescan_scheduled;
|
||||
gint n_oms_installed;
|
||||
};
|
||||
|
||||
static guint signals[N_SIGNALS] = {0};
|
||||
|
|
@ -42,22 +53,46 @@ wp_standard_event_source_init (WpStandardEventSource * self)
|
|||
{
|
||||
}
|
||||
|
||||
static void
|
||||
wp_standard_event_source_get_property (GObject * object, guint property_id,
|
||||
GValue * value, GParamSpec * pspec)
|
||||
static GType
|
||||
object_type_to_gtype (ObjectType type)
|
||||
{
|
||||
WpStandardEventSource *self = WP_STANDARD_EVENT_SOURCE (object);
|
||||
|
||||
switch (property_id) {
|
||||
case PROP_OBJECT_MANAGER:
|
||||
g_value_set_object (value, self->om);
|
||||
break;
|
||||
default:
|
||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
|
||||
break;
|
||||
switch (type) {
|
||||
case OBJECT_TYPE_PORT: return WP_TYPE_PORT;
|
||||
case OBJECT_TYPE_LINK: return WP_TYPE_LINK;
|
||||
case OBJECT_TYPE_NODE: return WP_TYPE_NODE;
|
||||
case OBJECT_TYPE_SESSION_ITEM: return WP_TYPE_SESSION_ITEM;
|
||||
case OBJECT_TYPE_ENDPOINT: return WP_TYPE_ENDPOINT;
|
||||
case OBJECT_TYPE_CLIENT: return WP_TYPE_CLIENT;
|
||||
case OBJECT_TYPE_DEVICE: return WP_TYPE_DEVICE;
|
||||
case OBJECT_TYPE_METADATA: return WP_TYPE_METADATA;
|
||||
default:
|
||||
g_assert_not_reached ();
|
||||
}
|
||||
}
|
||||
|
||||
static ObjectType
|
||||
type_str_to_object_type (const gchar * type_str)
|
||||
{
|
||||
if (!g_strcmp0 (type_str, "port"))
|
||||
return OBJECT_TYPE_PORT;
|
||||
else if (!g_strcmp0 (type_str, "link"))
|
||||
return OBJECT_TYPE_LINK;
|
||||
else if (!g_strcmp0 (type_str, "node"))
|
||||
return OBJECT_TYPE_NODE;
|
||||
else if (!g_strcmp0 (type_str, "session-item"))
|
||||
return OBJECT_TYPE_SESSION_ITEM;
|
||||
else if (!g_strcmp0 (type_str, "endpoint"))
|
||||
return OBJECT_TYPE_ENDPOINT;
|
||||
else if (!g_strcmp0 (type_str, "client"))
|
||||
return OBJECT_TYPE_CLIENT;
|
||||
else if (!g_strcmp0 (type_str, "device"))
|
||||
return OBJECT_TYPE_DEVICE;
|
||||
else if (!g_strcmp0 (type_str, "metadata"))
|
||||
return OBJECT_TYPE_METADATA;
|
||||
else
|
||||
return OBJECT_TYPE_INVALID;
|
||||
}
|
||||
|
||||
static const gchar *
|
||||
get_object_type (gpointer obj, WpProperties **properties)
|
||||
{
|
||||
|
|
@ -89,47 +124,57 @@ get_object_type (gpointer obj, WpProperties **properties)
|
|||
return "device";
|
||||
else if (WP_IS_METADATA (obj))
|
||||
return "metadata";
|
||||
else if (WP_IS_FACTORY (obj))
|
||||
return "factory";
|
||||
|
||||
wp_debug_object (obj, "Unknown global proxy type");
|
||||
return G_OBJECT_TYPE_NAME (obj);
|
||||
}
|
||||
|
||||
static gint
|
||||
get_default_event_priority (const gchar *event_type, const gchar *subject_type)
|
||||
get_default_event_priority (const gchar *event_type)
|
||||
{
|
||||
if (!g_strcmp0 (event_type, "object-added") ||
|
||||
!g_strcmp0 (event_type, "object-removed"))
|
||||
{
|
||||
if (!g_strcmp0 (subject_type, "client"))
|
||||
return 200;
|
||||
else if (!g_strcmp0 (subject_type, "device"))
|
||||
return 170;
|
||||
else if (!g_strcmp0 (subject_type, "port"))
|
||||
return 150;
|
||||
else if (!g_strcmp0 (subject_type, "node"))
|
||||
return 130;
|
||||
else if (!g_strcmp0 (subject_type, "session-item"))
|
||||
return 110;
|
||||
else
|
||||
return 20;
|
||||
}
|
||||
else if (!g_strcmp0 (event_type, "find-si-target-and-link"))
|
||||
if (!g_strcmp0 (event_type, "find-target-si-and-link"))
|
||||
return 500;
|
||||
else if (!g_strcmp0 (event_type, "rescan-session"))
|
||||
return -500;
|
||||
else if (!g_strcmp0 (event_type, "node-state-changed"))
|
||||
return 50;
|
||||
else if (!g_strcmp0 (event_type, "params-changed"))
|
||||
return 50;
|
||||
else if (!g_strcmp0 (event_type, "metadata-changed"))
|
||||
return 50;
|
||||
else if (g_str_has_suffix (event_type, "-params-changed"))
|
||||
return 50;
|
||||
else if (g_str_has_prefix (event_type, "client-"))
|
||||
return 200;
|
||||
else if (g_str_has_prefix (event_type, "device-"))
|
||||
return 170;
|
||||
else if (g_str_has_prefix (event_type, "port-"))
|
||||
return 150;
|
||||
else if (g_str_has_prefix (event_type, "node-"))
|
||||
return 130;
|
||||
else if (g_str_has_prefix (event_type, "session-item-"))
|
||||
return 110;
|
||||
else if (g_str_has_suffix (event_type, "-added") ||
|
||||
g_str_has_suffix (event_type, "-removed"))
|
||||
return 20;
|
||||
|
||||
wp_debug ("Unknown event type: %s, using priority 0", event_type);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static WpObjectManager *
|
||||
wp_standard_event_get_object_manager (WpStandardEventSource *self,
|
||||
const gchar * type_str)
|
||||
{
|
||||
ObjectType type = type_str_to_object_type (type_str);
|
||||
|
||||
if (G_UNLIKELY (type == OBJECT_TYPE_INVALID)) {
|
||||
wp_critical_object (self, "object type '%s' is not valid", type_str);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
g_return_val_if_fail (self->oms[type], NULL);
|
||||
return g_object_ref (self->oms[type]);
|
||||
}
|
||||
|
||||
static void
|
||||
wp_standard_event_source_push_event (WpStandardEventSource *self,
|
||||
const gchar *event_type, gpointer subject, WpProperties *misc_properties)
|
||||
|
|
@ -140,16 +185,21 @@ wp_standard_event_source_push_event (WpStandardEventSource *self,
|
|||
wp_event_dispatcher_get_instance (core);
|
||||
g_return_if_fail (dispatcher);
|
||||
g_autoptr (WpProperties) properties = wp_properties_new_empty ();
|
||||
g_autofree gchar *full_event_type = NULL;
|
||||
|
||||
const gchar *subject_type =
|
||||
subject ? get_object_type (subject, &properties) : NULL;
|
||||
gint priority = get_default_event_priority (event_type, subject_type);
|
||||
|
||||
if (subject_type)
|
||||
if (subject_type) {
|
||||
wp_properties_set (properties, "event.subject.type", subject_type);
|
||||
full_event_type = g_strdup_printf ("%s-%s", subject_type, event_type);
|
||||
event_type = full_event_type;
|
||||
}
|
||||
if (misc_properties)
|
||||
wp_properties_add (properties, misc_properties);
|
||||
|
||||
gint priority = get_default_event_priority (event_type);
|
||||
|
||||
wp_debug_object (self,
|
||||
"pushing event '%s', prio %d, subject " WP_OBJECT_FORMAT " (%s)",
|
||||
event_type, priority, WP_OBJECT_ARGS (subject), subject_type);
|
||||
|
|
@ -179,8 +229,7 @@ on_metadata_changed (WpMetadata *obj, guint32 subject,
|
|||
wp_properties_set (properties, "event.subject.spa_type", spa_type);
|
||||
wp_properties_set (properties, "event.subject.value", value);
|
||||
|
||||
wp_standard_event_source_push_event (self, "metadata-changed", obj,
|
||||
properties);
|
||||
wp_standard_event_source_push_event (self, "changed", obj, properties);
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
@ -201,14 +250,14 @@ on_node_state_changed (WpNode *obj, WpNodeState old_state,
|
|||
"event.subject.old-state", g_enum_to_string (WP_TYPE_NODE_STATE, old_state),
|
||||
"event.subject.new-state", g_enum_to_string (WP_TYPE_NODE_STATE, new_state),
|
||||
NULL);
|
||||
wp_standard_event_source_push_event (self, "node-state-changed", obj,
|
||||
wp_standard_event_source_push_event (self, "state-changed", obj,
|
||||
properties);
|
||||
}
|
||||
|
||||
static void
|
||||
on_object_added (WpObjectManager *om, WpObject *obj, WpStandardEventSource *self)
|
||||
{
|
||||
wp_standard_event_source_push_event (self, "object-added", obj, NULL);
|
||||
wp_standard_event_source_push_event (self, "added", obj, NULL);
|
||||
|
||||
if (WP_IS_PIPEWIRE_OBJECT (obj)) {
|
||||
g_signal_connect_object (obj, "params-changed",
|
||||
|
|
@ -228,13 +277,14 @@ on_object_added (WpObjectManager *om, WpObject *obj, WpStandardEventSource *self
|
|||
static void
|
||||
on_object_removed (WpObjectManager *om, WpObject *obj, WpStandardEventSource *self)
|
||||
{
|
||||
wp_standard_event_source_push_event (self, "object-removed", obj, NULL);
|
||||
wp_standard_event_source_push_event (self, "removed", obj, NULL);
|
||||
}
|
||||
|
||||
static void
|
||||
on_om_installed (WpObjectManager * om, WpStandardEventSource * self)
|
||||
{
|
||||
wp_object_update_features (WP_OBJECT (self), WP_PLUGIN_FEATURE_ENABLED, 0);
|
||||
if (++self->n_oms_installed == N_OBJECT_TYPES)
|
||||
wp_object_update_features (WP_OBJECT (self), WP_PLUGIN_FEATURE_ENABLED, 0);
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
@ -252,52 +302,66 @@ wp_standard_event_source_enable (WpPlugin * plugin, WpTransition * transition)
|
|||
g_autoptr (WpEventDispatcher) dispatcher =
|
||||
wp_event_dispatcher_get_instance (core);
|
||||
g_return_if_fail (dispatcher);
|
||||
g_autoptr (WpEventHook) hook = NULL;
|
||||
|
||||
self->om = wp_object_manager_new ();
|
||||
wp_object_manager_add_interest (self->om, WP_TYPE_GLOBAL_PROXY, NULL);
|
||||
wp_object_manager_add_interest (self->om, WP_TYPE_SESSION_ITEM, NULL);
|
||||
wp_object_manager_request_object_features (self->om,
|
||||
WP_TYPE_GLOBAL_PROXY, WP_OBJECT_FEATURES_ALL);
|
||||
g_signal_connect_object (self->om, "object-added",
|
||||
G_CALLBACK (on_object_added), self, 0);
|
||||
g_signal_connect_object (self->om, "object-removed",
|
||||
G_CALLBACK (on_object_removed), self, 0);
|
||||
g_signal_connect_object (self->om, "installed",
|
||||
G_CALLBACK (on_om_installed), self, 0);
|
||||
wp_core_install_object_manager (core, self->om);
|
||||
/* install object managers */
|
||||
self->n_oms_installed = 0;
|
||||
for (gint i = 0; i < N_OBJECT_TYPES; i++) {
|
||||
GType gtype = object_type_to_gtype (i);
|
||||
self->oms[i] = wp_object_manager_new ();
|
||||
wp_object_manager_add_interest (self->oms[i], gtype, NULL);
|
||||
wp_object_manager_request_object_features (self->oms[i],
|
||||
gtype, WP_OBJECT_FEATURES_ALL);
|
||||
g_signal_connect_object (self->oms[i], "object-added",
|
||||
G_CALLBACK (on_object_added), self, 0);
|
||||
g_signal_connect_object (self->oms[i], "object-removed",
|
||||
G_CALLBACK (on_object_removed), self, 0);
|
||||
g_signal_connect_object (self->oms[i], "installed",
|
||||
G_CALLBACK (on_om_installed), self, 0);
|
||||
wp_core_install_object_manager (core, self->oms[i]);
|
||||
}
|
||||
|
||||
hook = wp_simple_event_hook_new ("rescan-done@std-event-source",
|
||||
/* install hook to restore the rescan_scheduled state after rescanning */
|
||||
self->rescan_done_hook = wp_simple_event_hook_new (
|
||||
"rescan-done@std-event-source",
|
||||
WP_EVENT_HOOK_PRIORITY_LOWEST, WP_EVENT_HOOK_EXEC_TYPE_ON_EVENT,
|
||||
g_cclosure_new_object ((GCallback) on_rescan_done, G_OBJECT (self)));
|
||||
wp_interest_event_hook_add_interest (WP_INTEREST_EVENT_HOOK (hook),
|
||||
wp_interest_event_hook_add_interest (
|
||||
WP_INTEREST_EVENT_HOOK (self->rescan_done_hook),
|
||||
WP_CONSTRAINT_TYPE_PW_PROPERTY, "event.type", "=s", "rescan-session",
|
||||
NULL);
|
||||
wp_event_dispatcher_register_hook (dispatcher, hook);
|
||||
wp_event_dispatcher_register_hook (dispatcher, self->rescan_done_hook);
|
||||
}
|
||||
|
||||
static void
|
||||
wp_standard_event_source_disable (WpPlugin * plugin)
|
||||
{
|
||||
WpStandardEventSource * self = WP_STANDARD_EVENT_SOURCE (plugin);
|
||||
g_clear_object (&self->om);
|
||||
g_autoptr (WpCore) core = wp_object_get_core (WP_OBJECT (plugin));
|
||||
g_return_if_fail (core);
|
||||
g_autoptr (WpEventDispatcher) dispatcher =
|
||||
wp_event_dispatcher_get_instance (core);
|
||||
|
||||
for (gint i = 0; i < N_OBJECT_TYPES; i++)
|
||||
g_clear_object (&self->oms[i]);
|
||||
|
||||
if (dispatcher)
|
||||
wp_event_dispatcher_unregister_hook (dispatcher, self->rescan_done_hook);
|
||||
g_clear_object (&self->rescan_done_hook);
|
||||
}
|
||||
|
||||
static void
|
||||
wp_standard_event_source_class_init (WpStandardEventSourceClass * klass)
|
||||
{
|
||||
GObjectClass *object_class = (GObjectClass *) klass;
|
||||
WpPluginClass *plugin_class = (WpPluginClass *) klass;
|
||||
|
||||
object_class->get_property = wp_standard_event_source_get_property;
|
||||
|
||||
plugin_class->enable = wp_standard_event_source_enable;
|
||||
plugin_class->disable = wp_standard_event_source_disable;
|
||||
|
||||
g_object_class_install_property (object_class, PROP_OBJECT_MANAGER,
|
||||
g_param_spec_string ("object-manager", "object-manager",
|
||||
"The WpObjectManager instance that is used to generate events", NULL,
|
||||
G_PARAM_READABLE | G_PARAM_STATIC_STRINGS));
|
||||
signals[ACTION_GET_OBJECT_MANAGER] = g_signal_new_class_handler (
|
||||
"get-object-manager", G_TYPE_FROM_CLASS (klass),
|
||||
G_SIGNAL_RUN_LAST | G_SIGNAL_ACTION,
|
||||
(GCallback) wp_standard_event_get_object_manager,
|
||||
NULL, NULL, NULL, WP_TYPE_OBJECT_MANAGER, 1, G_TYPE_STRING);
|
||||
|
||||
signals[ACTION_PUSH_EVENT] = g_signal_new_class_handler (
|
||||
"push-event", G_TYPE_FROM_CLASS (klass),
|
||||
|
|
|
|||
|
|
@ -71,18 +71,15 @@ AsyncEventHook {
|
|||
priority = HookPriority.LOW,
|
||||
interests = {
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-added" },
|
||||
Constraint { "event.subject.type", "=", "node" },
|
||||
Constraint { "event.type", "=", "node-added" },
|
||||
Constraint { "media.class", "#", "Stream/*", type = "pw-global" },
|
||||
},
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-added" },
|
||||
Constraint { "event.subject.type", "=", "node" },
|
||||
Constraint { "event.type", "=", "node-added" },
|
||||
Constraint { "media.class", "#", "Video/*", type = "pw-global" },
|
||||
},
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-added" },
|
||||
Constraint { "event.subject.type", "=", "node" },
|
||||
Constraint { "event.type", "=", "node-added" },
|
||||
Constraint { "media.class", "#", "Audio/*", type = "pw-global" },
|
||||
Constraint { "wireplumber.is-endpoint", "-", type = "pw" },
|
||||
},
|
||||
|
|
@ -146,18 +143,15 @@ SimpleEventHook {
|
|||
priority = HookPriority.LOW,
|
||||
interests = {
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-removed" },
|
||||
Constraint { "event.subject.type", "=", "node" },
|
||||
Constraint { "event.type", "=", "node-removed" },
|
||||
Constraint { "media.class", "#", "Stream/*", type = "pw-global" },
|
||||
},
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-removed" },
|
||||
Constraint { "event.subject.type", "=", "node" },
|
||||
Constraint { "event.type", "=", "node-removed" },
|
||||
Constraint { "media.class", "#", "Video/*", type = "pw-global" },
|
||||
},
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-removed" },
|
||||
Constraint { "event.subject.type", "=", "node" },
|
||||
Constraint { "event.type", "=", "node-removed" },
|
||||
Constraint { "media.class", "#", "Audio/*", type = "pw-global" },
|
||||
Constraint { "wireplumber.is-endpoint", "-", type = "pw" },
|
||||
},
|
||||
|
|
|
|||
|
|
@ -33,10 +33,10 @@ function putils.unwrap_find_target_event (self, event)
|
|||
local source = event:get_source ()
|
||||
local si = event:get_subject ()
|
||||
local target = event:get_data ("target")
|
||||
local om = source:call ("get-object-manager", "session-item")
|
||||
local si_id = si.id
|
||||
|
||||
return source, source ["object-manager"],
|
||||
si, si.properties, self:get_flags (si_id), target
|
||||
return source, om, si, si.properties, self:get_flags (si_id), target
|
||||
end
|
||||
|
||||
function putils.canPassthrough (si, si_target)
|
||||
|
|
|
|||
|
|
@ -391,8 +391,7 @@ SimpleEventHook {
|
|||
priority = HookPriority.NORMAL,
|
||||
interests = {
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-removed" },
|
||||
Constraint { "event.subject.type", "=", "node" },
|
||||
Constraint { "event.type", "=", "node-removed" },
|
||||
Constraint { "media.class", "matches", "Stream/Input/Audio", type = "pw-global" },
|
||||
},
|
||||
},
|
||||
|
|
@ -410,15 +409,13 @@ SimpleEventHook {
|
|||
priority = HookPriority.NORMAL,
|
||||
interests = {
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "state-changed" },
|
||||
Constraint { "event.subject.type", "=", "node" },
|
||||
Constraint { "event.type", "=", "node-state-changed" },
|
||||
Constraint { "media.class", "#", "Stream/Input/Audio", type = "pw-global" },
|
||||
-- Do not consider monitor streams
|
||||
Constraint { "stream.monitor", "!", "true" }
|
||||
},
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "params-changed" },
|
||||
Constraint { "event.subject.type", "=", "node" },
|
||||
Constraint { "event.type", "=", "node-params-changed" },
|
||||
Constraint { "media.class", "#", "Stream/Input/Audio", type = "pw-global" },
|
||||
-- Do not consider monitor streams
|
||||
Constraint { "stream.monitor", "!", "true" }
|
||||
|
|
@ -435,8 +432,7 @@ SimpleEventHook {
|
|||
priority = HookPriority.VERY_LOW,
|
||||
interests = {
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-added" },
|
||||
Constraint { "event.subject.type", "=", "device" },
|
||||
Constraint { "event.type", "=", "device-added" },
|
||||
Constraint { "device.api", "=", "bluez5" },
|
||||
},
|
||||
},
|
||||
|
|
@ -456,8 +452,7 @@ SimpleEventHook {
|
|||
priority = HookPriority.VERY_LOW,
|
||||
interests = {
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-changed" },
|
||||
Constraint { "event.subject.type", "=", "metadata" },
|
||||
Constraint { "event.type", "=", "metadata-changed" },
|
||||
Constraint { "metadata.name", "=", "default" },
|
||||
Constraint { "event.subject.key", "=", "default.audio.sink" },
|
||||
Constraint { "event.subject.id", "=", "0" },
|
||||
|
|
|
|||
|
|
@ -21,7 +21,7 @@ function findAssociatedLinkGroupNode (si)
|
|||
end
|
||||
|
||||
local std_event_source = Plugin.find ("standard-event-source")
|
||||
local om = std_event_source ["object-manager"]
|
||||
local om = std_event_source:call ("get-object-manager", "session-item")
|
||||
|
||||
-- get the associated media class
|
||||
local assoc_direction = cutils.getTargetDirection (si_props)
|
||||
|
|
@ -84,8 +84,8 @@ SimpleEventHook {
|
|||
priority = HookPriority.NORMAL,
|
||||
interests = {
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-added" },
|
||||
Constraint { "event.subject.type", "=", "linkable" },
|
||||
Constraint { "event.type", "=", "session-item-added" },
|
||||
Constraint { "event.session-item.interface", "=", "linkable" },
|
||||
Constraint { "item.factory.name", "c", "si-audio-adapter", "si-node" },
|
||||
Constraint { "media.class", "#", "Stream/*", type = "pw-global" },
|
||||
Constraint { "active-features", "!", 0, type = "gobject" },
|
||||
|
|
|
|||
|
|
@ -21,7 +21,7 @@ SimpleEventHook {
|
|||
},
|
||||
},
|
||||
execute = function (event)
|
||||
local source, om, si, si_props, si_flags, target =
|
||||
local source, _, si, si_props, si_flags, target =
|
||||
putils:unwrap_find_target_event (event)
|
||||
|
||||
local reconnect = not cutils.parseBool (si_props ["node.dont-reconnect"])
|
||||
|
|
@ -104,8 +104,8 @@ SimpleEventHook {
|
|||
|
||||
local client_id = node.properties ["client.id"]
|
||||
if client_id then
|
||||
local client = om:lookup {
|
||||
type = "client",
|
||||
local clients_om = source:call ("get-object-manager", "client")
|
||||
local client = clients_om:lookup {
|
||||
Constraint { "bound-id", "=", client_id, type = "gobject" }
|
||||
}
|
||||
if client then
|
||||
|
|
|
|||
|
|
@ -36,14 +36,14 @@ SimpleEventHook {
|
|||
priority = HookPriority.VERY_LOW,
|
||||
interests = {
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-removed" },
|
||||
Constraint { "event.subject.type", "=", "linkable" },
|
||||
Constraint { "event.type", "=", "session-item-removed" },
|
||||
Constraint { "event.session-item.interface", "=", "linkable" },
|
||||
},
|
||||
},
|
||||
execute = function (event)
|
||||
local si = event:get_subject ()
|
||||
local source = event:get_source ()
|
||||
local om = source ["object-manager"]
|
||||
local om = source:call ("get-object-manager", "session-item")
|
||||
local si_id = si.id
|
||||
local valid, si_props = checkLinkable (si, om, true)
|
||||
if not valid then
|
||||
|
|
@ -91,7 +91,7 @@ SimpleEventHook {
|
|||
},
|
||||
execute = function (event)
|
||||
local source = event:get_source ()
|
||||
local om = source ["object-manager"]
|
||||
local om = source:call ("get-object-manager", "session-item")
|
||||
|
||||
Log.info ("rescanning...")
|
||||
|
||||
|
|
@ -125,14 +125,13 @@ SimpleEventHook {
|
|||
interests = {
|
||||
-- on linkable added or removed, where linkable is adapter or plain node
|
||||
EventInterest {
|
||||
Constraint { "event.type", "c", "object-added", "object-removed" },
|
||||
Constraint { "event.subject.type", "=", "linkable" },
|
||||
Constraint { "event.type", "c", "session-item-added", "session-item-removed" },
|
||||
Constraint { "event.session-item.interface", "=", "linkable" },
|
||||
Constraint { "item.factory.name", "c", "si-audio-adapter", "si-node" },
|
||||
},
|
||||
-- on device Routes changed
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "params-changed" },
|
||||
Constraint { "event.subject.type", "=", "device" },
|
||||
Constraint { "event.type", "=", "device-params-changed" },
|
||||
Constraint { "event.subject.param-id", "=", "Route" },
|
||||
},
|
||||
},
|
||||
|
|
|
|||
|
|
@ -107,19 +107,17 @@ SimpleEventHook {
|
|||
priority = HookPriority.LOW,
|
||||
interests = {
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-added" },
|
||||
Constraint { "event.subject.type", "=", "device" },
|
||||
Constraint { "event.type", "=", "device-added" },
|
||||
},
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "params-changed" },
|
||||
Constraint { "event.subject.type", "=", "device" },
|
||||
Constraint { "event.type", "=", "device-params-changed" },
|
||||
Constraint { "event.subject.param-id", "=", "EnumProfile" },
|
||||
},
|
||||
},
|
||||
execute = function (event)
|
||||
local device = event:get_subject ()
|
||||
local event_properties = event:get_properties ()
|
||||
local new_device = (event_properties ["event.type"] == "object-added")
|
||||
local new_device = (event_properties ["event.type"] == "device-added")
|
||||
|
||||
local dev_id = device ["bound-id"]
|
||||
local dev_name = device.properties ["device.name"]
|
||||
|
|
@ -172,8 +170,7 @@ SimpleEventHook {
|
|||
priority = HookPriority.NORMAL,
|
||||
interests = {
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-removed" },
|
||||
Constraint { "event.subject.type", "=", "device" },
|
||||
Constraint { "event.type", "=", "device-removed" },
|
||||
},
|
||||
},
|
||||
execute = function (event)
|
||||
|
|
|
|||
|
|
@ -515,13 +515,11 @@ SimpleEventHook {
|
|||
priority = HookPriority.ULTRA_LOW,
|
||||
interests = {
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "params-changed" },
|
||||
Constraint { "event.subject.type", "=", "device" },
|
||||
Constraint { "event.type", "=", "device-params-changed" },
|
||||
Constraint { "event.subject.param-id", "=", "Route" },
|
||||
},
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "params-changed" },
|
||||
Constraint { "event.subject.type", "=", "device" },
|
||||
Constraint { "event.type", "=", "device-params-changed" },
|
||||
Constraint { "event.subject.param-id", "=", "EnumRoute" },
|
||||
},
|
||||
},
|
||||
|
|
|
|||
|
|
@ -349,8 +349,7 @@ local function handleRestoreTargetSetting (enable)
|
|||
priority = HookPriority.ULTRA_LOW,
|
||||
interests = {
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-added" },
|
||||
Constraint { "event.subject.type", "=", "metadata" },
|
||||
Constraint { "event.type", "=", "metadata-added" },
|
||||
Constraint { "metadata.name", "=", "default" },
|
||||
},
|
||||
},
|
||||
|
|
@ -473,20 +472,17 @@ local function handleRestoreStreamSetting (enable)
|
|||
priority = HookPriority.NORMAL,
|
||||
interests = {
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-added" },
|
||||
Constraint { "event.subject.type", "=", "node" },
|
||||
Constraint { "event.type", "=", "node-added" },
|
||||
Constraint { "media.class", "matches", "Stream/*", type = "pw-global" },
|
||||
},
|
||||
-- and device nodes that are not associated with any routes
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-added" },
|
||||
Constraint { "event.subject.type", "=", "node" },
|
||||
Constraint { "event.type", "=", "node-added" },
|
||||
Constraint { "media.class", "matches", "Audio/*", type = "pw-global" },
|
||||
Constraint { "device.routes", "is-absent", type = "pw" },
|
||||
},
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "object-added" },
|
||||
Constraint { "event.subject.type", "=", "node" },
|
||||
Constraint { "event.type", "=", "node-added" },
|
||||
Constraint { "media.class", "matches", "Audio/*", type = "pw-global" },
|
||||
Constraint { "device.routes", "equals", "0", type = "pw" },
|
||||
},
|
||||
|
|
@ -503,22 +499,19 @@ local function handleRestoreStreamSetting (enable)
|
|||
priority = HookPriority.NORMAL,
|
||||
interests = {
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "params-changed" },
|
||||
Constraint { "event.subject.type", "=", "node" },
|
||||
Constraint { "event.type", "=", "node-params-changed" },
|
||||
Constraint { "event.subject.param-id", "=", "Props" },
|
||||
Constraint { "media.class", "matches", "Stream/*", type = "pw-global" },
|
||||
},
|
||||
-- and device nodes that are not associated with any routes
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "params-changed" },
|
||||
Constraint { "event.subject.type", "=", "node" },
|
||||
Constraint { "event.type", "=", "node-params-changed" },
|
||||
Constraint { "event.subject.param-id", "=", "Props" },
|
||||
Constraint { "media.class", "matches", "Audio/*", type = "pw-global" },
|
||||
Constraint { "device.routes", "is-absent", type = "pw" },
|
||||
},
|
||||
EventInterest {
|
||||
Constraint { "event.type", "=", "params-changed" },
|
||||
Constraint { "event.subject.type", "=", "node" },
|
||||
Constraint { "event.type", "=", "node-params-changed" },
|
||||
Constraint { "event.subject.param-id", "=", "Props" },
|
||||
Constraint { "media.class", "matches", "Audio/*", type = "pw-global" },
|
||||
Constraint { "device.routes", "equals", "0", type = "pw" },
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue