mirror of
https://gitlab.freedesktop.org/pipewire/pipewire.git
synced 2025-11-01 22:58:50 -04:00
node: unlink ports before destroy
First unlink the ports, then destroy them. This is a more natural way of cleaning up. Make sure we destroy the node after destroying the ports. Destroy the port after destroying its controls Destroy resources after destroying the global
This commit is contained in:
parent
3db9a44679
commit
5034770eae
6 changed files with 74 additions and 47 deletions
|
|
@ -301,9 +301,8 @@ void pw_client_destroy(struct pw_client *client)
|
|||
|
||||
spa_hook_remove(&impl->core_listener);
|
||||
|
||||
if (client->registered) {
|
||||
if (client->registered)
|
||||
spa_list_remove(&client->link);
|
||||
}
|
||||
|
||||
if (client->global) {
|
||||
spa_hook_remove(&client->global_listener);
|
||||
|
|
|
|||
|
|
@ -1253,17 +1253,8 @@ void pw_link_destroy(struct pw_link *link)
|
|||
|
||||
pw_link_deactivate(link);
|
||||
|
||||
if (link->registered) {
|
||||
if (link->registered)
|
||||
spa_list_remove(&link->link);
|
||||
}
|
||||
|
||||
if (link->global) {
|
||||
spa_hook_remove(&link->global_listener);
|
||||
pw_global_destroy(link->global);
|
||||
}
|
||||
|
||||
spa_list_for_each_safe(resource, tmp, &link->resource_list, link)
|
||||
pw_resource_destroy(resource);
|
||||
|
||||
input_remove(link, link->input);
|
||||
spa_list_remove(&link->input_link);
|
||||
|
|
@ -1275,6 +1266,14 @@ void pw_link_destroy(struct pw_link *link)
|
|||
spa_hook_list_call(&link->output->listener_list, struct pw_port_events, link_removed, link);
|
||||
link->output = NULL;
|
||||
|
||||
if (link->global) {
|
||||
spa_hook_remove(&link->global_listener);
|
||||
pw_global_destroy(link->global);
|
||||
}
|
||||
|
||||
spa_list_for_each_safe(resource, tmp, &link->resource_list, link)
|
||||
pw_resource_destroy(resource);
|
||||
|
||||
pw_log_debug("link %p: free", impl);
|
||||
spa_hook_list_call(&link->listener_list, struct pw_link_events, free);
|
||||
|
||||
|
|
|
|||
|
|
@ -300,6 +300,12 @@ void pw_module_destroy(struct pw_module *module)
|
|||
pw_log_debug("module %p: destroy", module);
|
||||
spa_hook_list_call(&module->listener_list, struct pw_module_events, destroy);
|
||||
|
||||
spa_list_remove(&module->link);
|
||||
|
||||
if (module->global) {
|
||||
spa_hook_remove(&module->global_listener);
|
||||
pw_global_destroy(module->global);
|
||||
}
|
||||
spa_list_for_each_safe(resource, tmp, &module->resource_list, link)
|
||||
pw_resource_destroy(resource);
|
||||
|
||||
|
|
@ -310,12 +316,6 @@ void pw_module_destroy(struct pw_module *module)
|
|||
if (module->info.args)
|
||||
free((char *) module->info.args);
|
||||
|
||||
spa_list_remove(&module->link);
|
||||
|
||||
if (module->global) {
|
||||
spa_hook_remove(&module->global_listener);
|
||||
pw_global_destroy(module->global);
|
||||
}
|
||||
dlclose(impl->hnd);
|
||||
free(impl);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -621,25 +621,29 @@ void pw_node_destroy(struct pw_node *node)
|
|||
spa_list_remove(&node->link);
|
||||
}
|
||||
|
||||
if (node->global) {
|
||||
spa_hook_remove(&node->global_listener);
|
||||
pw_global_destroy(node->global);
|
||||
}
|
||||
|
||||
spa_list_for_each_safe(resource, tmp, &node->resource_list, link)
|
||||
pw_resource_destroy(resource);
|
||||
pw_log_debug("node %p: unlink ports", node);
|
||||
spa_list_for_each(port, &node->input_ports, link)
|
||||
pw_port_unlink(port);
|
||||
spa_list_for_each(port, &node->output_ports, link)
|
||||
pw_port_unlink(port);
|
||||
|
||||
pw_log_debug("node %p: destroy ports", node);
|
||||
spa_list_for_each_safe(port, tmpp, &node->input_ports, link) {
|
||||
spa_hook_list_call(&node->listener_list, struct pw_node_events, port_removed, port);
|
||||
pw_port_destroy(port);
|
||||
}
|
||||
|
||||
spa_list_for_each_safe(port, tmpp, &node->output_ports, link) {
|
||||
spa_hook_list_call(&node->listener_list, struct pw_node_events, port_removed, port);
|
||||
pw_port_destroy(port);
|
||||
}
|
||||
|
||||
if (node->global) {
|
||||
spa_hook_remove(&node->global_listener);
|
||||
pw_global_destroy(node->global);
|
||||
}
|
||||
spa_list_for_each_safe(resource, tmp, &node->resource_list, link)
|
||||
pw_resource_destroy(resource);
|
||||
|
||||
pw_log_debug("node %p: free", node);
|
||||
spa_hook_list_call(&node->listener_list, struct pw_node_events, free);
|
||||
|
||||
|
|
|
|||
|
|
@ -391,6 +391,20 @@ int pw_port_add(struct pw_port *port, struct pw_node *node)
|
|||
return 0;
|
||||
}
|
||||
|
||||
void pw_port_unlink(struct pw_port *port)
|
||||
{
|
||||
struct pw_link *l, *t;
|
||||
|
||||
if (port->direction == PW_DIRECTION_OUTPUT) {
|
||||
spa_list_for_each_safe(l, t, &port->links, output_link)
|
||||
pw_link_destroy(l);
|
||||
}
|
||||
else {
|
||||
spa_list_for_each_safe(l, t, &port->links, input_link)
|
||||
pw_link_destroy(l);
|
||||
}
|
||||
}
|
||||
|
||||
static int do_remove_port(struct spa_loop *loop,
|
||||
bool async, uint32_t seq, const void *data, size_t size, void *user_data)
|
||||
{
|
||||
|
|
@ -409,6 +423,28 @@ static int do_remove_port(struct spa_loop *loop,
|
|||
return 0;
|
||||
}
|
||||
|
||||
static void pw_port_remove(struct pw_port *port)
|
||||
{
|
||||
struct pw_node *node = port->node;
|
||||
|
||||
pw_log_debug("port %p: remove", port);
|
||||
|
||||
if (port->rt.graph)
|
||||
pw_loop_invoke(port->node->data_loop, do_remove_port,
|
||||
SPA_ID_INVALID, NULL, 0, true, port);
|
||||
|
||||
if (port->direction == PW_DIRECTION_INPUT) {
|
||||
pw_map_remove(&node->input_port_map, port->port_id);
|
||||
node->info.n_input_ports--;
|
||||
}
|
||||
else {
|
||||
pw_map_remove(&node->output_port_map, port->port_id);
|
||||
node->info.n_output_ports--;
|
||||
}
|
||||
spa_list_remove(&port->link);
|
||||
spa_hook_list_call(&node->listener_list, struct pw_node_events, port_removed, port);
|
||||
}
|
||||
|
||||
void pw_port_destroy(struct pw_port *port)
|
||||
{
|
||||
struct pw_node *node = port->node;
|
||||
|
|
@ -418,33 +454,19 @@ void pw_port_destroy(struct pw_port *port)
|
|||
|
||||
spa_hook_list_call(&port->listener_list, struct pw_port_events, destroy);
|
||||
|
||||
if (port->global) {
|
||||
spa_hook_remove(&port->global_listener);
|
||||
pw_global_destroy(port->global);
|
||||
}
|
||||
|
||||
if (node) {
|
||||
if (port->rt.graph)
|
||||
pw_loop_invoke(port->node->data_loop, do_remove_port,
|
||||
SPA_ID_INVALID, NULL, 0, true, port);
|
||||
|
||||
if (port->direction == PW_DIRECTION_INPUT) {
|
||||
pw_map_remove(&node->input_port_map, port->port_id);
|
||||
node->info.n_input_ports--;
|
||||
}
|
||||
else {
|
||||
pw_map_remove(&node->output_port_map, port->port_id);
|
||||
node->info.n_output_ports--;
|
||||
}
|
||||
spa_list_remove(&port->link);
|
||||
spa_hook_list_call(&node->listener_list, struct pw_node_events, port_removed, port);
|
||||
}
|
||||
if (node)
|
||||
pw_port_remove(port);
|
||||
|
||||
spa_list_for_each_safe(control, ctemp, &port->control_list[0], port_link)
|
||||
pw_control_destroy(control);
|
||||
spa_list_for_each_safe(control, ctemp, &port->control_list[1], port_link)
|
||||
pw_control_destroy(control);
|
||||
|
||||
if (port->global) {
|
||||
spa_hook_remove(&port->global_listener);
|
||||
pw_global_destroy(port->global);
|
||||
}
|
||||
|
||||
pw_log_debug("port %p: free", port);
|
||||
spa_hook_list_call(&port->listener_list, struct pw_port_events, free);
|
||||
|
||||
|
|
|
|||
|
|
@ -487,6 +487,9 @@ void * pw_port_get_user_data(struct pw_port *port);
|
|||
/** Add a port to a node \memberof pw_port */
|
||||
int pw_port_add(struct pw_port *port, struct pw_node *node);
|
||||
|
||||
/** Unlink a port \memberof pw_port */
|
||||
void pw_port_unlink(struct pw_port *port);
|
||||
|
||||
/** Destroy a port \memberof pw_port */
|
||||
void pw_port_destroy(struct pw_port *port);
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue