mirror of
https://gitlab.freedesktop.org/pipewire/pipewire.git
synced 2025-10-31 22:25:38 -04:00
spa: use clock info
Use the port clock io area to get timing info and use this as the time in the graph when we wake up.
This commit is contained in:
parent
2b1b356455
commit
d3c203b744
10 changed files with 134 additions and 15 deletions
|
|
@ -317,7 +317,9 @@ impl_node_port_enum_params(struct spa_node *node,
|
|||
uint32_t list[] = { t->param.idEnumFormat,
|
||||
t->param.idFormat,
|
||||
t->param.idBuffers,
|
||||
t->param.idMeta };
|
||||
t->param.idMeta,
|
||||
t->param_io.idBuffers,
|
||||
t->param_io.idClock, };
|
||||
|
||||
if (*index < SPA_N_ELEMENTS(list))
|
||||
param = spa_pod_builder_object(&b, id, t->param.List,
|
||||
|
|
@ -375,6 +377,42 @@ impl_node_port_enum_params(struct spa_node *node,
|
|||
return 0;
|
||||
}
|
||||
}
|
||||
else if (id == t->param_io.idBuffers) {
|
||||
switch (*index) {
|
||||
case 0:
|
||||
param = spa_pod_builder_object(&b,
|
||||
id, t->param_io.Buffers,
|
||||
":", t->param_io.id, "I", t->io.Buffers,
|
||||
":", t->param_io.size, "i", sizeof(struct spa_io_buffers));
|
||||
break;
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else if (id == t->param_io.idControl) {
|
||||
switch (*index) {
|
||||
case 0:
|
||||
param = spa_pod_builder_object(&b,
|
||||
id, t->param_io.Control,
|
||||
":", t->param_io.id, "I", t->io.ControlRange,
|
||||
":", t->param_io.size, "i", sizeof(struct spa_io_control_range));
|
||||
break;
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else if (id == t->param_io.idClock) {
|
||||
switch (*index) {
|
||||
case 0:
|
||||
param = spa_pod_builder_object(&b,
|
||||
id, t->param_io.Clock,
|
||||
":", t->param_io.id, "I", t->io.Clock,
|
||||
":", t->param_io.size, "i", sizeof(struct spa_io_clock));
|
||||
break;
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else
|
||||
return -ENOENT;
|
||||
|
||||
|
|
|
|||
|
|
@ -401,6 +401,30 @@ impl_node_port_enum_params(struct spa_node *node,
|
|||
return 0;
|
||||
}
|
||||
}
|
||||
else if (id == t->param_io.idBuffers) {
|
||||
switch (*index) {
|
||||
case 0:
|
||||
param = spa_pod_builder_object(&b,
|
||||
id, t->param_io.Buffers,
|
||||
":", t->param_io.id, "I", t->io.Buffers,
|
||||
":", t->param_io.size, "i", sizeof(struct spa_io_buffers));
|
||||
break;
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else if (id == t->param_io.idClock) {
|
||||
switch (*index) {
|
||||
case 0:
|
||||
param = spa_pod_builder_object(&b,
|
||||
id, t->param_io.Clock,
|
||||
":", t->param_io.id, "I", t->io.Clock,
|
||||
":", t->param_io.size, "i", sizeof(struct spa_io_clock));
|
||||
break;
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else
|
||||
return -ENOENT;
|
||||
|
||||
|
|
|
|||
|
|
@ -36,6 +36,7 @@ extern "C" {
|
|||
#include <spa/node/node.h>
|
||||
#include <spa/node/io.h>
|
||||
#include <spa/param/buffers.h>
|
||||
#include <spa/param/io.h>
|
||||
#include <spa/param/meta.h>
|
||||
#include <spa/param/audio/format-utils.h>
|
||||
|
||||
|
|
@ -82,6 +83,7 @@ struct type {
|
|||
struct spa_type_format_audio format_audio;
|
||||
struct spa_type_param_buffers param_buffers;
|
||||
struct spa_type_param_meta param_meta;
|
||||
struct spa_type_param_io param_io;
|
||||
};
|
||||
|
||||
static inline void init_type(struct type *type, struct spa_type_map *map)
|
||||
|
|
@ -108,6 +110,7 @@ static inline void init_type(struct type *type, struct spa_type_map *map)
|
|||
spa_type_format_audio_map(map, &type->format_audio);
|
||||
spa_type_param_buffers_map(map, &type->param_buffers);
|
||||
spa_type_param_meta_map(map, &type->param_meta);
|
||||
spa_type_param_io_map(map, &type->param_io);
|
||||
}
|
||||
|
||||
struct state {
|
||||
|
|
|
|||
|
|
@ -158,6 +158,7 @@ struct port {
|
|||
|
||||
bool have_format;
|
||||
struct spa_video_info current_format;
|
||||
struct spa_fraction rate;
|
||||
|
||||
int fd;
|
||||
bool opened;
|
||||
|
|
@ -178,9 +179,7 @@ struct port {
|
|||
|
||||
struct spa_port_info info;
|
||||
struct spa_io_buffers *io;
|
||||
|
||||
int64_t last_ticks;
|
||||
int64_t last_monotonic;
|
||||
struct spa_io_clock *clock;
|
||||
};
|
||||
|
||||
struct impl {
|
||||
|
|
@ -562,6 +561,30 @@ static int impl_node_port_enum_params(struct spa_node *node,
|
|||
else if (id == t->param_io.idPropsIn) {
|
||||
return spa_v4l2_enum_controls(this, index, filter, result, builder);
|
||||
}
|
||||
else if (id == t->param_io.idBuffers) {
|
||||
switch (*index) {
|
||||
case 0:
|
||||
param = spa_pod_builder_object(&b,
|
||||
id, t->param_io.Buffers,
|
||||
":", t->param_io.id, "I", t->io.Buffers,
|
||||
":", t->param_io.size, "i", sizeof(struct spa_io_buffers));
|
||||
break;
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else if (id == t->param_io.idClock) {
|
||||
switch (*index) {
|
||||
case 0:
|
||||
param = spa_pod_builder_object(&b,
|
||||
id, t->param_io.Clock,
|
||||
":", t->param_io.id, "I", t->io.Clock,
|
||||
":", t->param_io.size, "i", sizeof(struct spa_io_clock));
|
||||
break;
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else
|
||||
return -ENOENT;
|
||||
|
||||
|
|
@ -767,6 +790,9 @@ static int impl_node_port_set_io(struct spa_node *node,
|
|||
if (id == t->io.Buffers) {
|
||||
port->io = data;
|
||||
}
|
||||
else if (id == t->io.Clock) {
|
||||
port->clock = data;
|
||||
}
|
||||
else if ((control = find_control(port, id))) {
|
||||
if (data && size >= sizeof(struct spa_pod_double))
|
||||
control->io = &SPA_POD_VALUE(struct spa_pod_double, data);
|
||||
|
|
|
|||
|
|
@ -911,6 +911,7 @@ static int spa_v4l2_set_format(struct impl *this, struct spa_video_info *format,
|
|||
SPA_PORT_INFO_FLAG_PHYSICAL |
|
||||
SPA_PORT_INFO_FLAG_TERMINAL;
|
||||
port->info.rate = streamparm.parm.capture.timeperframe.denominator;
|
||||
port->rate = *framerate;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
@ -1156,14 +1157,13 @@ static int mmap_read(struct impl *this)
|
|||
if (xioctl(port->fd, VIDIOC_DQBUF, &buf) < 0)
|
||||
return -errno;
|
||||
|
||||
port->last_ticks = (int64_t) buf.timestamp.tv_sec * SPA_USEC_PER_SEC +
|
||||
(uint64_t) buf.timestamp.tv_usec;
|
||||
pts = port->last_ticks * 1000;
|
||||
pts = SPA_TIMEVAL_TO_TIME(&buf.timestamp);
|
||||
|
||||
if (buf.flags & V4L2_BUF_FLAG_TIMESTAMP_MONOTONIC)
|
||||
port->last_monotonic = pts;
|
||||
else
|
||||
port->last_monotonic = SPA_TIME_INVALID;
|
||||
if (port->clock) {
|
||||
port->clock->nsec = pts;
|
||||
port->clock->rate = port->rate;
|
||||
port->clock->position = buf.sequence;
|
||||
}
|
||||
|
||||
b = &port->buffers[buf.index];
|
||||
if (b->h) {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue