Skip to content
GitLab
Explore
Sign in
Register
Primary navigation
Search or go to…
Project
W
wireplumber
Manage
Activity
Members
Labels
Code
Merge requests
Repository
Branches
Commits
Tags
Repository graph
Compare revisions
Snippets
Build
Pipelines
Jobs
Pipeline schedules
Artifacts
Deploy
Releases
Package Registry
Model registry
Operate
Environments
Terraform modules
Analyze
Value stream analytics
Contributor analytics
CI/CD analytics
Repository analytics
Model experiments
Help
Help
Support
GitLab documentation
Compare GitLab plans
Community forum
Contribute to GitLab
Provide feedback
Terms and privacy
Keyboard shortcuts
?
Snippets
Groups
Projects
Show more breadcrumbs
pkg
wireplumber
Commits
8887cce5
Commit
8887cce5
authored
5 years ago
by
Julian Bouzas
Browse files
Options
Downloads
Patches
Plain Diff
modules: add monitor reservation data API
parent
daa80916
No related branches found
No related tags found
No related merge requests found
Changes
3
Hide whitespace changes
Inline
Side-by-side
Showing
3 changed files
modules/meson.build
+1
-0
1 addition, 0 deletions
modules/meson.build
modules/module-monitor/reservation-data.c
+450
-0
450 additions, 0 deletions
modules/module-monitor/reservation-data.c
modules/module-monitor/reservation-data.h
+54
-0
54 additions, 0 deletions
modules/module-monitor/reservation-data.h
with
505 additions
and
0 deletions
modules/meson.build
+
1
−
0
View file @
8887cce5
...
...
@@ -24,6 +24,7 @@ shared_library(
'wireplumber-module-monitor'
,
[
'module-monitor.c'
,
'module-monitor/reservation-data.c'
,
'module-monitor/dbus-device-reservation.c'
,
reserve_device_interface_src
,
],
...
...
This diff is collapsed.
Click to expand it.
modules/module-monitor/reservation-data.c
0 → 100644
+
450
−
0
View file @
8887cce5
/* WirePlumber
*
* Copyright © 2020 Collabora Ltd.
* @author Julian Bouzas <julian.bouzas@collabora.com>
*
* SPDX-License-Identifier: MIT
*/
#include
"reservation-data.h"
#include
<spa/pod/builder.h>
#include
<pipewire/pipewire.h>
struct
_WpMonitorDeviceReservationData
{
GObject
parent
;
/* Props */
GWeakRef
device
;
WpMonitorDbusDeviceReservation
*
reservation
;
guint
n_acquired
;
};
enum
{
DEVICE_PROP_0
,
DEVICE_PROP_DEVICE
,
DEVICE_PROP_RESERVATION
,
};
G_DEFINE_TYPE
(
WpMonitorDeviceReservationData
,
wp_monitor_device_reservation_data
,
G_TYPE_OBJECT
)
static
void
on_device_done
(
WpCore
*
core
,
GAsyncResult
*
res
,
WpMonitorDeviceReservationData
*
self
)
{
if
(
self
->
reservation
)
wp_monitor_dbus_device_reservation_complete_release
(
self
->
reservation
,
TRUE
);
}
static
void
on_reservation_acquired
(
GObject
*
obj
,
GAsyncResult
*
res
,
gpointer
user_data
)
{
WpMonitorDeviceReservationData
*
self
=
user_data
;
WpMonitorDbusDeviceReservation
*
reserv
=
WP_MONITOR_DBUS_DEVICE_RESERVATION
(
obj
);
g_autoptr
(
GError
)
error
=
NULL
;
g_autoptr
(
WpProxy
)
device
=
NULL
;
char
buf
[
1024
];
struct
spa_pod_builder
b
=
SPA_POD_BUILDER_INIT
(
buf
,
sizeof
(
buf
));
/* Finish */
if
(
!
wp_monitor_dbus_device_reservation_async_finish
(
reserv
,
res
,
&
error
))
{
g_warning
(
"%s"
,
error
->
message
);
return
;
}
/* Get the device */
device
=
g_weak_ref_get
(
&
self
->
device
);
if
(
!
device
)
return
;
/* Set profile 1 */
wp_proxy_set_param
(
device
,
SPA_PARAM_Profile
,
0
,
spa_pod_builder_add_object
(
&
b
,
SPA_TYPE_OBJECT_ParamProfile
,
SPA_PARAM_Profile
,
SPA_PARAM_PROFILE_index
,
SPA_POD_Int
(
1
)));
}
static
void
on_reservation_release
(
WpMonitorDbusDeviceReservation
*
reservation
,
int
forced
,
WpMonitorDeviceReservationData
*
self
)
{
g_autoptr
(
WpProxy
)
device
=
NULL
;
g_autoptr
(
WpCore
)
core
=
NULL
;
char
buf
[
1024
];
struct
spa_pod_builder
b
=
SPA_POD_BUILDER_INIT
(
buf
,
sizeof
(
buf
));
/* Get the device and core */
device
=
g_weak_ref_get
(
&
self
->
device
);
if
(
!
device
)
return
;
core
=
wp_proxy_get_core
(
device
);
if
(
!
core
)
return
;
/* Set profile 0 */
wp_proxy_set_param
(
device
,
SPA_PARAM_Profile
,
0
,
spa_pod_builder_add_object
(
&
b
,
SPA_TYPE_OBJECT_ParamProfile
,
SPA_PARAM_Profile
,
SPA_PARAM_PROFILE_index
,
SPA_POD_Int
(
0
)));
/* Complete release on done */
wp_core_sync
(
core
,
NULL
,
(
GAsyncReadyCallback
)
on_device_done
,
self
);
}
static
void
on_device_destroyed
(
WpProxy
*
device
,
WpMonitorDeviceReservationData
*
self
)
{
wp_monitor_dbus_device_reservation_release
(
self
->
reservation
);
}
static
void
wp_monitor_device_reservation_data_constructed
(
GObject
*
object
)
{
WpMonitorDeviceReservationData
*
self
=
WP_MONITOR_DEVICE_RESERVATION_DATA
(
object
);
g_autoptr
(
WpProxy
)
device
=
g_weak_ref_get
(
&
self
->
device
);
/* Make sure the device is released when the pw proxy device is destroyed */
g_return_if_fail
(
device
);
g_signal_connect_object
(
device
,
"pw-proxy-destroyed"
,
(
GCallback
)
on_device_destroyed
,
self
,
0
);
/* Handle the reservation signals */
g_return_if_fail
(
self
->
reservation
);
g_signal_connect_object
(
self
->
reservation
,
"release"
,
(
GCallback
)
on_reservation_release
,
self
,
0
);
/* Try to acquire the device */
wp_monitor_dbus_device_reservation_acquire
(
self
->
reservation
,
NULL
,
on_reservation_acquired
,
self
);
G_OBJECT_CLASS
(
wp_monitor_device_reservation_data_parent_class
)
->
constructed
(
object
);
}
static
void
wp_monitor_device_reservation_data_get_property
(
GObject
*
object
,
guint
property_id
,
GValue
*
value
,
GParamSpec
*
pspec
)
{
WpMonitorDeviceReservationData
*
self
=
WP_MONITOR_DEVICE_RESERVATION_DATA
(
object
);
switch
(
property_id
)
{
case
DEVICE_PROP_DEVICE
:
g_value_take_object
(
value
,
g_weak_ref_get
(
&
self
->
device
));
break
;
case
DEVICE_PROP_RESERVATION
:
g_value_set_object
(
value
,
self
->
reservation
);
break
;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID
(
object
,
property_id
,
pspec
);
break
;
}
}
static
void
wp_monitor_device_reservation_data_set_property
(
GObject
*
object
,
guint
property_id
,
const
GValue
*
value
,
GParamSpec
*
pspec
)
{
WpMonitorDeviceReservationData
*
self
=
WP_MONITOR_DEVICE_RESERVATION_DATA
(
object
);
switch
(
property_id
)
{
case
DEVICE_PROP_DEVICE
:
g_weak_ref_set
(
&
self
->
device
,
g_value_get_object
(
value
));
break
;
case
DEVICE_PROP_RESERVATION
:
self
->
reservation
=
g_value_dup_object
(
value
);
break
;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID
(
object
,
property_id
,
pspec
);
break
;
}
}
static
void
wp_monitor_device_reservation_data_finalize
(
GObject
*
object
)
{
WpMonitorDeviceReservationData
*
self
=
WP_MONITOR_DEVICE_RESERVATION_DATA
(
object
);
wp_monitor_dbus_device_reservation_release
(
self
->
reservation
);
/* Props */
g_weak_ref_clear
(
&
self
->
device
);
g_clear_object
(
&
self
->
reservation
);
G_OBJECT_CLASS
(
wp_monitor_device_reservation_data_parent_class
)
->
finalize
(
object
);
}
static
void
wp_monitor_device_reservation_data_init
(
WpMonitorDeviceReservationData
*
self
)
{
/* Props */
g_weak_ref_init
(
&
self
->
device
,
NULL
);
self
->
n_acquired
=
0
;
}
static
void
wp_monitor_device_reservation_data_class_init
(
WpMonitorDeviceReservationDataClass
*
klass
)
{
GObjectClass
*
object_class
=
(
GObjectClass
*
)
klass
;
object_class
->
constructed
=
wp_monitor_device_reservation_data_constructed
;
object_class
->
get_property
=
wp_monitor_device_reservation_data_get_property
;
object_class
->
set_property
=
wp_monitor_device_reservation_data_set_property
;
object_class
->
finalize
=
wp_monitor_device_reservation_data_finalize
;
/* Props */
g_object_class_install_property
(
object_class
,
DEVICE_PROP_DEVICE
,
g_param_spec_object
(
"device"
,
"device"
,
"The device"
,
WP_TYPE_PROXY
,
G_PARAM_READWRITE
|
G_PARAM_CONSTRUCT_ONLY
|
G_PARAM_STATIC_STRINGS
));
g_object_class_install_property
(
object_class
,
DEVICE_PROP_RESERVATION
,
g_param_spec_object
(
"reservation"
,
"reservation"
,
"The dbus device reservation"
,
WP_TYPE_MONITOR_DBUS_DEVICE_RESERVATION
,
G_PARAM_READWRITE
|
G_PARAM_CONSTRUCT_ONLY
|
G_PARAM_STATIC_STRINGS
));
}
WpMonitorDeviceReservationData
*
wp_monitor_device_reservation_data_new
(
WpProxy
*
device
,
WpMonitorDbusDeviceReservation
*
reservation
)
{
return
g_object_new
(
WP_TYPE_MONITOR_DEVICE_RESERVATION_DATA
,
"device"
,
device
,
"reservation"
,
reservation
,
NULL
);
}
void
wp_monitor_device_reservation_data_acquire
(
WpMonitorDeviceReservationData
*
self
)
{
g_return_if_fail
(
WP_IS_MONITOR_DEVICE_RESERVATION_DATA
(
self
));
g_return_if_fail
(
self
->
reservation
);
if
(
self
->
n_acquired
==
0
)
wp_monitor_dbus_device_reservation_acquire
(
self
->
reservation
,
NULL
,
on_reservation_acquired
,
self
);
self
->
n_acquired
++
;
}
void
wp_monitor_device_reservation_data_release
(
WpMonitorDeviceReservationData
*
self
)
{
g_return_if_fail
(
WP_IS_MONITOR_DEVICE_RESERVATION_DATA
(
self
));
g_return_if_fail
(
self
->
reservation
);
if
(
self
->
n_acquired
==
1
)
wp_monitor_dbus_device_reservation_release
(
self
->
reservation
);
self
->
n_acquired
--
;
}
struct
_WpMonitorNodeReservationData
{
GObject
parent
;
/* Props */
GWeakRef
node
;
WpMonitorDeviceReservationData
*
device_data
;
gboolean
acquired
;
GSource
*
timeout_source
;
};
enum
{
NODE_PROP_0
,
NODE_PROP_NODE
,
NODE_PROP_DEVICE_DATA
,
};
G_DEFINE_TYPE
(
WpMonitorNodeReservationData
,
wp_monitor_node_reservation_data
,
G_TYPE_OBJECT
)
static
void
on_node_destroyed
(
WpProxy
*
node
,
WpMonitorNodeReservationData
*
self
)
{
if
(
self
->
acquired
)
wp_monitor_device_reservation_data_release
(
self
->
device_data
);
}
static
void
wp_monitor_node_reservation_data_constructed
(
GObject
*
object
)
{
WpMonitorNodeReservationData
*
self
=
WP_MONITOR_NODE_RESERVATION_DATA
(
object
);
WpProxy
*
node
=
g_weak_ref_get
(
&
self
->
node
);
g_return_if_fail
(
node
);
/* Make sure the device is released when the pw proxy node is destroyed */
g_signal_connect_object
(
node
,
"pw-proxy-destroyed"
,
(
GCallback
)
on_node_destroyed
,
self
,
0
);
G_OBJECT_CLASS
(
wp_monitor_node_reservation_data_parent_class
)
->
constructed
(
object
);
}
static
void
wp_monitor_node_reservation_data_get_property
(
GObject
*
object
,
guint
property_id
,
GValue
*
value
,
GParamSpec
*
pspec
)
{
WpMonitorNodeReservationData
*
self
=
WP_MONITOR_NODE_RESERVATION_DATA
(
object
);
switch
(
property_id
)
{
case
NODE_PROP_NODE
:
g_value_take_object
(
value
,
g_weak_ref_get
(
&
self
->
node
));
break
;
case
NODE_PROP_DEVICE_DATA
:
g_value_set_object
(
value
,
self
->
device_data
);
break
;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID
(
object
,
property_id
,
pspec
);
break
;
}
}
static
void
wp_monitor_node_reservation_data_set_property
(
GObject
*
object
,
guint
property_id
,
const
GValue
*
value
,
GParamSpec
*
pspec
)
{
WpMonitorNodeReservationData
*
self
=
WP_MONITOR_NODE_RESERVATION_DATA
(
object
);
switch
(
property_id
)
{
case
NODE_PROP_NODE
:
g_weak_ref_set
(
&
self
->
node
,
g_value_get_object
(
value
));
break
;
case
NODE_PROP_DEVICE_DATA
:
self
->
device_data
=
g_value_dup_object
(
value
);
break
;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID
(
object
,
property_id
,
pspec
);
break
;
}
}
static
void
wp_monitor_node_reservation_data_finalize
(
GObject
*
object
)
{
WpMonitorNodeReservationData
*
self
=
WP_MONITOR_NODE_RESERVATION_DATA
(
object
);
/* Clear the current timeout release callback */
if
(
self
->
timeout_source
)
g_source_destroy
(
self
->
timeout_source
);
g_clear_pointer
(
&
self
->
timeout_source
,
g_source_unref
);
/* Release device if acquired */
if
(
self
->
acquired
)
wp_monitor_device_reservation_data_release
(
self
->
device_data
);
/* Props */
g_weak_ref_clear
(
&
self
->
node
);
g_clear_object
(
&
self
->
device_data
);
G_OBJECT_CLASS
(
wp_monitor_node_reservation_data_parent_class
)
->
finalize
(
object
);
}
static
void
wp_monitor_node_reservation_data_init
(
WpMonitorNodeReservationData
*
self
)
{
/* Props */
g_weak_ref_init
(
&
self
->
node
,
NULL
);
self
->
acquired
=
FALSE
;
self
->
timeout_source
=
NULL
;
}
static
void
wp_monitor_node_reservation_data_class_init
(
WpMonitorNodeReservationDataClass
*
klass
)
{
GObjectClass
*
object_class
=
(
GObjectClass
*
)
klass
;
object_class
->
constructed
=
wp_monitor_node_reservation_data_constructed
;
object_class
->
get_property
=
wp_monitor_node_reservation_data_get_property
;
object_class
->
set_property
=
wp_monitor_node_reservation_data_set_property
;
object_class
->
finalize
=
wp_monitor_node_reservation_data_finalize
;
/* Props */
g_object_class_install_property
(
object_class
,
NODE_PROP_NODE
,
g_param_spec_object
(
"node"
,
"node"
,
"The node"
,
WP_TYPE_PROXY
,
G_PARAM_READWRITE
|
G_PARAM_CONSTRUCT_ONLY
|
G_PARAM_STATIC_STRINGS
));
g_object_class_install_property
(
object_class
,
NODE_PROP_DEVICE_DATA
,
g_param_spec_object
(
"device-data"
,
"device-data"
,
"The monitor device reservation data"
,
WP_TYPE_MONITOR_DEVICE_RESERVATION_DATA
,
G_PARAM_READWRITE
|
G_PARAM_CONSTRUCT_ONLY
|
G_PARAM_STATIC_STRINGS
));
}
WpMonitorNodeReservationData
*
wp_monitor_node_reservation_data_new
(
WpProxy
*
node
,
WpMonitorDeviceReservationData
*
device_data
)
{
return
g_object_new
(
WP_TYPE_MONITOR_NODE_RESERVATION_DATA
,
"node"
,
node
,
"device-data"
,
device_data
,
NULL
);
}
static
gboolean
timeout_release_callback
(
gpointer
data
)
{
WpMonitorNodeReservationData
*
self
=
data
;
g_return_val_if_fail
(
self
,
G_SOURCE_REMOVE
);
wp_monitor_device_reservation_data_release
(
self
->
device_data
);
self
->
acquired
=
FALSE
;
return
G_SOURCE_REMOVE
;
}
void
wp_monitor_node_reservation_data_timeout_release
(
WpMonitorNodeReservationData
*
self
,
guint64
timeout_ms
)
{
g_autoptr
(
WpProxy
)
node
=
NULL
;
g_autoptr
(
WpCore
)
core
=
NULL
;
g_return_if_fail
(
WP_IS_MONITOR_NODE_RESERVATION_DATA
(
self
));
node
=
g_weak_ref_get
(
&
self
->
node
);
g_return_if_fail
(
node
);
core
=
wp_proxy_get_core
(
node
);
g_return_if_fail
(
core
);
/* Clear the current timeout release callback */
if
(
self
->
timeout_source
)
g_source_destroy
(
self
->
timeout_source
);
g_clear_pointer
(
&
self
->
timeout_source
,
g_source_unref
);
/* Add new timeout release callback */
wp_core_timeout_add
(
core
,
&
self
->
timeout_source
,
timeout_ms
,
timeout_release_callback
,
g_object_ref
(
self
),
g_object_unref
);
}
void
wp_monitor_node_reservation_data_acquire
(
WpMonitorNodeReservationData
*
self
)
{
g_return_if_fail
(
WP_IS_MONITOR_NODE_RESERVATION_DATA
(
self
));
/* Clear the current timeout release callback */
if
(
self
->
timeout_source
)
g_source_destroy
(
self
->
timeout_source
);
g_clear_pointer
(
&
self
->
timeout_source
,
g_source_unref
);
/* Don't do anything if already acquired */
if
(
self
->
acquired
)
return
;
/* Acquire the device */
wp_monitor_device_reservation_data_acquire
(
self
->
device_data
);
self
->
acquired
=
TRUE
;
}
This diff is collapsed.
Click to expand it.
modules/module-monitor/reservation-data.h
0 → 100644
+
54
−
0
View file @
8887cce5
/* WirePlumber
*
* Copyright © 2020 Collabora Ltd.
* @author Julian Bouzas <julian.bouzas@collabora.com>
*
* SPDX-License-Identifier: MIT
*/
#ifndef __WIREPLUMBER_MONITOR_RESERVATION_DATA_H__
#define __WIREPLUMBER_MONITOR_RESERVATION_DATA_H__
#include
<wp/wp.h>
#include
"dbus-device-reservation.h"
G_BEGIN_DECLS
#define WP_TYPE_MONITOR_DEVICE_RESERVATION_DATA (wp_monitor_device_reservation_data_get_type ())
G_DECLARE_FINAL_TYPE
(
WpMonitorDeviceReservationData
,
wp_monitor_device_reservation_data
,
WP
,
MONITOR_DEVICE_RESERVATION_DATA
,
GObject
)
WpMonitorDeviceReservationData
*
wp_monitor_device_reservation_data_new
(
WpProxy
*
device
,
WpMonitorDbusDeviceReservation
*
reservation
);
void
wp_monitor_device_reservation_data_acquire
(
WpMonitorDeviceReservationData
*
self
);
void
wp_monitor_device_reservation_data_release
(
WpMonitorDeviceReservationData
*
self
);
#define WP_TYPE_MONITOR_NODE_RESERVATION_DATA (wp_monitor_node_reservation_data_get_type ())
G_DECLARE_FINAL_TYPE
(
WpMonitorNodeReservationData
,
wp_monitor_node_reservation_data
,
WP
,
MONITOR_NODE_RESERVATION_DATA
,
GObject
)
WpMonitorNodeReservationData
*
wp_monitor_node_reservation_data_new
(
WpProxy
*
node
,
WpMonitorDeviceReservationData
*
device_data
);
void
wp_monitor_node_reservation_data_timeout_release
(
WpMonitorNodeReservationData
*
self
,
guint64
timeout_ms
);
void
wp_monitor_node_reservation_data_acquire
(
WpMonitorNodeReservationData
*
self
);
G_END_DECLS
#endif
This diff is collapsed.
Click to expand it.
Preview
0%
Loading
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Save comment
Cancel
Please
register
or
sign in
to comment