mirror of
				https://gitlab.freedesktop.org/pipewire/pipewire.git
				synced 2025-11-03 09:01:54 -05:00 
			
		
		
		
	stream: handle monitor sources
This commit is contained in:
		
							parent
							
								
									c201a1e666
								
							
						
					
					
						commit
						72b61f614a
					
				
					 4 changed files with 31 additions and 12 deletions
				
			
		| 
						 | 
					@ -104,7 +104,7 @@ struct global *pa_context_find_global_by_name(pa_context *c, uint32_t mask, cons
 | 
				
			||||||
	uint32_t id = atoi(name);
 | 
						uint32_t id = atoi(name);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	spa_list_for_each(g, &c->globals, link) {
 | 
						spa_list_for_each(g, &c->globals, link) {
 | 
				
			||||||
		if (!(g->mask & mask))
 | 
							if ((g->mask & mask) == 0)
 | 
				
			||||||
			continue;
 | 
								continue;
 | 
				
			||||||
		if (g->props != NULL &&
 | 
							if (g->props != NULL &&
 | 
				
			||||||
		    (str = pw_properties_get(g->props, "node.name")) != NULL &&
 | 
							    (str = pw_properties_get(g->props, "node.name")) != NULL &&
 | 
				
			||||||
| 
						 | 
					@ -138,7 +138,9 @@ struct global *pa_context_find_linked(pa_context *c, uint32_t idx)
 | 
				
			||||||
		if (f == NULL)
 | 
							if (f == NULL)
 | 
				
			||||||
			continue;
 | 
								continue;
 | 
				
			||||||
		if (f->mask & PA_SUBSCRIPTION_MASK_DSP) {
 | 
							if (f->mask & PA_SUBSCRIPTION_MASK_DSP) {
 | 
				
			||||||
			f = pa_context_find_global(c, f->dsp_info.session);
 | 
								if (!(f->mask & PA_SUBSCRIPTION_MASK_SOURCE) ||
 | 
				
			||||||
 | 
									g->link_info.dst->parent_id != idx)
 | 
				
			||||||
 | 
									f = pa_context_find_global(c, f->dsp_info.session);
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
		return f;
 | 
							return f;
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
| 
						 | 
					@ -148,6 +150,7 @@ struct global *pa_context_find_linked(pa_context *c, uint32_t idx)
 | 
				
			||||||
static int set_mask(pa_context *c, struct global *g)
 | 
					static int set_mask(pa_context *c, struct global *g)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	const char *str;
 | 
						const char *str;
 | 
				
			||||||
 | 
						struct global *f;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	switch (g->type) {
 | 
						switch (g->type) {
 | 
				
			||||||
	case PW_TYPE_INTERFACE_Device:
 | 
						case PW_TYPE_INTERFACE_Device:
 | 
				
			||||||
| 
						 | 
					@ -172,12 +175,16 @@ static int set_mask(pa_context *c, struct global *g)
 | 
				
			||||||
		if (strcmp(str, "Audio/Sink") == 0) {
 | 
							if (strcmp(str, "Audio/Sink") == 0) {
 | 
				
			||||||
			g->mask = PA_SUBSCRIPTION_MASK_SINK;
 | 
								g->mask = PA_SUBSCRIPTION_MASK_SINK;
 | 
				
			||||||
			g->event = PA_SUBSCRIPTION_EVENT_SINK;
 | 
								g->event = PA_SUBSCRIPTION_EVENT_SINK;
 | 
				
			||||||
 | 
								g->node_info.monitor = SPA_ID_INVALID;
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
		else if (strcmp(str, "Audio/DSP/Playback") == 0) {
 | 
							else if (strcmp(str, "Audio/DSP/Playback") == 0) {
 | 
				
			||||||
			if ((str = pw_properties_get(g->props, "node.session")) == NULL)
 | 
								if ((str = pw_properties_get(g->props, "node.session")) == NULL)
 | 
				
			||||||
				return 0;
 | 
									return 0;
 | 
				
			||||||
			g->mask = PA_SUBSCRIPTION_MASK_DSP_SINK;
 | 
								g->mask = PA_SUBSCRIPTION_MASK_DSP_SINK | PA_SUBSCRIPTION_MASK_SOURCE;
 | 
				
			||||||
 | 
								g->event = PA_SUBSCRIPTION_EVENT_SOURCE;
 | 
				
			||||||
			g->dsp_info.session = pw_properties_parse_int(str);
 | 
								g->dsp_info.session = pw_properties_parse_int(str);
 | 
				
			||||||
 | 
								if ((f = pa_context_find_global(c, g->dsp_info.session)) != NULL)
 | 
				
			||||||
 | 
									f->node_info.monitor = g->id;
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
		else if (strcmp(str, "Audio/Source") == 0) {
 | 
							else if (strcmp(str, "Audio/Source") == 0) {
 | 
				
			||||||
			g->mask = PA_SUBSCRIPTION_MASK_SOURCE;
 | 
								g->mask = PA_SUBSCRIPTION_MASK_SOURCE;
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -222,6 +222,10 @@ struct global {
 | 
				
			||||||
		struct {
 | 
							struct {
 | 
				
			||||||
			uint32_t session;
 | 
								uint32_t session;
 | 
				
			||||||
		} dsp_info;
 | 
							} dsp_info;
 | 
				
			||||||
 | 
							/* for sink/source */
 | 
				
			||||||
 | 
							struct {
 | 
				
			||||||
 | 
								uint32_t monitor;
 | 
				
			||||||
 | 
							} node_info;
 | 
				
			||||||
		/* for devices */
 | 
							/* for devices */
 | 
				
			||||||
		struct {
 | 
							struct {
 | 
				
			||||||
			struct pw_array profiles;
 | 
								struct pw_array profiles;
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -334,6 +334,8 @@ static void sink_callback(struct sink_data *d)
 | 
				
			||||||
	pa_format_info ii[1];
 | 
						pa_format_info ii[1];
 | 
				
			||||||
	pa_format_info *ip[1];
 | 
						pa_format_info *ip[1];
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						pw_log_debug("sink %d %s monitor %d", g->id, info->name, g->node_info.monitor);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	spa_zero(i);
 | 
						spa_zero(i);
 | 
				
			||||||
	i.name = info->name;
 | 
						i.name = info->name;
 | 
				
			||||||
	i.index = g->id;
 | 
						i.index = g->id;
 | 
				
			||||||
| 
						 | 
					@ -345,7 +347,7 @@ static void sink_callback(struct sink_data *d)
 | 
				
			||||||
	i.owner_module = g->parent_id;
 | 
						i.owner_module = g->parent_id;
 | 
				
			||||||
	pa_cvolume_set(&i.volume, 2, PA_VOLUME_NORM);
 | 
						pa_cvolume_set(&i.volume, 2, PA_VOLUME_NORM);
 | 
				
			||||||
	i.mute = false;
 | 
						i.mute = false;
 | 
				
			||||||
	i.monitor_source = PA_INVALID_INDEX;
 | 
						i.monitor_source = g->node_info.monitor;
 | 
				
			||||||
	i.monitor_source_name = "unknown";
 | 
						i.monitor_source_name = "unknown";
 | 
				
			||||||
	i.latency = 0;
 | 
						i.latency = 0;
 | 
				
			||||||
	i.driver = "PipeWire";
 | 
						i.driver = "PipeWire";
 | 
				
			||||||
| 
						 | 
					@ -565,8 +567,13 @@ static void source_callback(struct source_data *d)
 | 
				
			||||||
	i.owner_module = g->parent_id;
 | 
						i.owner_module = g->parent_id;
 | 
				
			||||||
	pa_cvolume_set(&i.volume, 2, PA_VOLUME_NORM);
 | 
						pa_cvolume_set(&i.volume, 2, PA_VOLUME_NORM);
 | 
				
			||||||
	i.mute = false;
 | 
						i.mute = false;
 | 
				
			||||||
	i.monitor_of_sink = PA_INVALID_INDEX;
 | 
						if (g->mask & PA_SUBSCRIPTION_MASK_DSP_SINK) {
 | 
				
			||||||
	i.monitor_of_sink_name = "unknown";
 | 
							i.monitor_of_sink = g->dsp_info.session;
 | 
				
			||||||
 | 
							i.monitor_of_sink_name = "unknown";
 | 
				
			||||||
 | 
						} else {
 | 
				
			||||||
 | 
							i.monitor_of_sink = PA_INVALID_INDEX;
 | 
				
			||||||
 | 
							i.monitor_of_sink_name = NULL;
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
	i.latency = 0;
 | 
						i.latency = 0;
 | 
				
			||||||
	i.driver = "PipeWire";
 | 
						i.driver = "PipeWire";
 | 
				
			||||||
	i.flags = 0;
 | 
						i.flags = 0;
 | 
				
			||||||
| 
						 | 
					@ -1473,8 +1480,8 @@ pa_operation* pa_context_set_sink_input_volume(pa_context *c, uint32_t idx, cons
 | 
				
			||||||
		pw_node_proxy_set_param((struct pw_node_proxy*)g->proxy,
 | 
							pw_node_proxy_set_param((struct pw_node_proxy*)g->proxy,
 | 
				
			||||||
			SPA_PARAM_Props, 0,
 | 
								SPA_PARAM_Props, 0,
 | 
				
			||||||
			spa_pod_builder_object(&b,
 | 
								spa_pod_builder_object(&b,
 | 
				
			||||||
				SPA_TYPE_OBJECT_Props, SPA_PARAM_Props,
 | 
									SPA_TYPE_OBJECT_Props,	SPA_PARAM_Props,
 | 
				
			||||||
				SPA_PROP_volume,        &SPA_POD_Float(v),
 | 
									SPA_PROP_volume,	&SPA_POD_Float(v),
 | 
				
			||||||
				0));
 | 
									0));
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	o = pa_operation_new(c, NULL, on_success, sizeof(struct success_ack));
 | 
						o = pa_operation_new(c, NULL, on_success, sizeof(struct success_ack));
 | 
				
			||||||
| 
						 | 
					@ -1511,7 +1518,7 @@ pa_operation* pa_context_set_sink_input_mute(pa_context *c, uint32_t idx, int mu
 | 
				
			||||||
		pw_node_proxy_set_param((struct pw_node_proxy*)g->proxy,
 | 
							pw_node_proxy_set_param((struct pw_node_proxy*)g->proxy,
 | 
				
			||||||
			SPA_PARAM_Props, 0,
 | 
								SPA_PARAM_Props, 0,
 | 
				
			||||||
			spa_pod_builder_object(&b,
 | 
								spa_pod_builder_object(&b,
 | 
				
			||||||
				SPA_TYPE_OBJECT_Props, SPA_PARAM_Props,
 | 
									SPA_TYPE_OBJECT_Props,	SPA_PARAM_Props,
 | 
				
			||||||
				SPA_PROP_mute,		&SPA_POD_Bool(mute),
 | 
									SPA_PROP_mute,		&SPA_POD_Bool(mute),
 | 
				
			||||||
				0));
 | 
									0));
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -202,7 +202,7 @@ static void configure_device(pa_stream *s)
 | 
				
			||||||
		else
 | 
							else
 | 
				
			||||||
			s->device_name = strdup(str);
 | 
								s->device_name = strdup(str);
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	pw_log_debug("linked to %d '%s'", s->device_index, s->device_name);
 | 
						pw_log_debug("stream %p: linked to %d '%s'", s, s->device_index, s->device_name);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void stream_state_changed(void *data, enum pw_stream_state old,
 | 
					static void stream_state_changed(void *data, enum pw_stream_state old,
 | 
				
			||||||
| 
						 | 
					@ -690,6 +690,7 @@ uint32_t pa_stream_get_device_index(pa_stream *s)
 | 
				
			||||||
	PA_CHECK_VALIDITY_RETURN_ANY(s->context, s->device_index != PA_INVALID_INDEX,
 | 
						PA_CHECK_VALIDITY_RETURN_ANY(s->context, s->device_index != PA_INVALID_INDEX,
 | 
				
			||||||
			PA_ERR_BADSTATE, PA_INVALID_INDEX);
 | 
								PA_ERR_BADSTATE, PA_INVALID_INDEX);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						pw_log_trace("stream %p: %d", s, s->device_index);
 | 
				
			||||||
	return s->device_index;
 | 
						return s->device_index;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					@ -840,7 +841,7 @@ static int create_stream(pa_stream_direction_t direction,
 | 
				
			||||||
		if ((str = getenv("PIPEWIRE_NODE")) != NULL)
 | 
							if ((str = getenv("PIPEWIRE_NODE")) != NULL)
 | 
				
			||||||
			devid = atoi(str);
 | 
								devid = atoi(str);
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	else {
 | 
						else if (devid == SPA_ID_INVALID) {
 | 
				
			||||||
		uint32_t mask;
 | 
							uint32_t mask;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
		if (direction == PA_STREAM_PLAYBACK)
 | 
							if (direction == PA_STREAM_PLAYBACK)
 | 
				
			||||||
| 
						 | 
					@ -1131,7 +1132,7 @@ int pa_stream_peek(pa_stream *s,
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	*data = SPA_MEMBER(s->buffer_data, s->buffer_offset, void);
 | 
						*data = SPA_MEMBER(s->buffer_data, s->buffer_offset, void);
 | 
				
			||||||
	*nbytes = s->buffer_size;
 | 
						*nbytes = s->buffer_size;
 | 
				
			||||||
	pw_log_trace("stream %p: %p %zd", s, *data, *nbytes);
 | 
						pw_log_trace("stream %p: %p %zd %f", s, *data, *nbytes, *(float*)*data);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	return 0;
 | 
						return 0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue