Split out generic portal / pipewire code
It will be reused by the video capture portal / pipewire backend.
Bug: webrtc:13177
Change-Id: Ia1a77f1c6e289149cd8a1d54b550754bf192e62e
Reviewed-on: https://webrtc-review.googlesource.com/c/src/+/263721
Reviewed-by: Mark Foltz <mfoltz@chromium.org>
Commit-Queue: Alexander Cooper <alcooper@chromium.org>
Reviewed-by: Erik Språng <sprang@webrtc.org>
Reviewed-by: Tomas Gunnarsson <tommi@webrtc.org>
Reviewed-by: Salman Malik <salmanmalik@google.com>
Cr-Commit-Position: refs/heads/main@{#38487}
diff --git a/modules/desktop_capture/BUILD.gn b/modules/desktop_capture/BUILD.gn
index 34a5704..a496ce5 100644
--- a/modules/desktop_capture/BUILD.gn
+++ b/modules/desktop_capture/BUILD.gn
@@ -7,9 +7,7 @@
# be found in the AUTHORS file in the root of the source tree.
import("//build/config/linux/gtk/gtk.gni")
-import("//build/config/linux/pkg_config.gni")
import("//build/config/ui.gni")
-import("//tools/generate_stubs/rules.gni")
import("../../webrtc.gni")
use_desktop_capture_differ_sse2 = current_cpu == "x86" || current_cpu == "x64"
@@ -84,7 +82,7 @@
]
if ((is_linux || is_chromeos) && rtc_use_pipewire) {
- configs += [ ":gio" ]
+ configs += [ "../portal:gio" ]
}
public_configs = [ ":x11_config" ]
@@ -105,14 +103,7 @@
"linux/wayland/test/test_screencast_stream_provider.h",
]
- configs += [
- ":gio",
- ":pipewire",
- ":gbm",
- ":egl",
- ":epoxy",
- ":libdrm",
- ]
+ configs += [ "../portal:pipewire_all" ]
deps = [
":desktop_capture",
@@ -122,6 +113,7 @@
"../../rtc_base:logging",
"../../rtc_base:random",
"../../rtc_base:timeutils",
+ "../portal",
# TODO(bugs.webrtc.org/9987): Remove this dep on rtc_base:rtc_base once
# rtc_base:threading is fully defined.
@@ -135,11 +127,7 @@
"//rtc_base:rtc_event",
]
- if (!rtc_link_pipewire) {
- deps += [ ":pipewire_stubs" ]
- }
-
- public_configs = [ ":pipewire_config" ]
+ public_configs = [ "../portal:pipewire_config" ]
}
group("pipewire_shared_screencast_stream_test") {
@@ -178,7 +166,7 @@
]
if ((is_linux || is_chromeos) && rtc_use_pipewire) {
- configs += [ ":gio" ]
+ configs += [ "../portal:gio" ]
}
deps = [
@@ -288,7 +276,7 @@
]
if ((is_linux || is_chromeos) && rtc_use_pipewire) {
- configs += [ ":gio" ]
+ configs += [ "../portal:gio" ]
}
deps = [
@@ -299,71 +287,10 @@
}
}
-if (is_linux || is_chromeos) {
- if (rtc_use_pipewire) {
- pkg_config("gio") {
- packages = [
- "gio-2.0",
- "gio-unix-2.0",
- ]
- }
-
- pkg_config("pipewire") {
- packages = [ "libpipewire-0.3" ]
- if (!rtc_link_pipewire) {
- ignore_libs = true
- }
- }
-
- pkg_config("gbm") {
- packages = [ "gbm" ]
- }
- pkg_config("egl") {
- packages = [ "egl" ]
- }
- pkg_config("epoxy") {
- packages = [ "epoxy" ]
- ignore_libs = true
- }
- pkg_config("libdrm") {
- packages = [ "libdrm" ]
- }
-
- if (!rtc_link_pipewire) {
- # When libpipewire is not directly linked, use stubs to allow for dlopening of
- # the binary.
- generate_stubs("pipewire_stubs") {
- configs = [
- "../../:common_config",
- ":pipewire",
- ]
- deps = [ "../../rtc_base" ]
- extra_header = "linux/wayland/pipewire_stub_header.fragment"
- logging_function = "RTC_LOG(LS_VERBOSE)"
- logging_include = "rtc_base/logging.h"
- output_name = "linux/wayland/pipewire_stubs"
- path_from_source = "modules/desktop_capture/linux/wayland"
- sigs = [ "linux/wayland/pipewire.sigs" ]
- if (!build_with_chromium) {
- macro_include = "rtc_base/system/no_cfi_icall.h"
- macro_deps = [ "../../rtc_base/system:no_cfi_icall" ]
- }
- }
- }
-
- config("pipewire_config") {
- defines = [ "WEBRTC_USE_PIPEWIRE" ]
- if (!rtc_link_pipewire) {
- defines += [ "WEBRTC_DLOPEN_PIPEWIRE" ]
- }
-
- # Chromecast build config overrides `WEBRTC_USE_PIPEWIRE` even when
- # `rtc_use_pipewire` is not set, which causes pipewire_config to not be
- # included in targets. More details in: webrtc:13898
- if (is_linux && !is_castos) {
- defines += [ "WEBRTC_USE_GIO" ]
- }
- }
+# TODO(bugs.webrtc.org/14187): remove when all users are gone
+if (is_linux && rtc_use_pipewire) {
+ config("pipewire_config") {
+ configs = [ "../portal:pipewire_config" ]
}
}
@@ -644,12 +571,9 @@
"linux/wayland/egl_dmabuf.h",
"linux/wayland/mouse_cursor_monitor_pipewire.cc",
"linux/wayland/mouse_cursor_monitor_pipewire.h",
- "linux/wayland/pipewire_utils.cc",
- "linux/wayland/pipewire_utils.h",
"linux/wayland/portal_request_response.h",
"linux/wayland/restore_token_manager.cc",
"linux/wayland/restore_token_manager.h",
- "linux/wayland/scoped_glib.cc",
"linux/wayland/scoped_glib.h",
"linux/wayland/screen_capture_portal_interface.cc",
"linux/wayland/screen_capture_portal_interface.h",
@@ -659,27 +583,18 @@
"linux/wayland/screencast_stream_utils.h",
"linux/wayland/shared_screencast_stream.cc",
"linux/wayland/shared_screencast_stream.h",
- "linux/wayland/xdg_desktop_portal_utils.cc",
"linux/wayland/xdg_desktop_portal_utils.h",
"linux/wayland/xdg_session_details.h",
]
- configs += [
- ":gio",
- ":pipewire",
- ":gbm",
- ":egl",
- ":epoxy",
- ":libdrm",
+ configs += [ "../portal:pipewire_all" ]
+
+ public_configs += [ "../portal:pipewire_config" ]
+
+ deps += [
+ "../../rtc_base:sanitizer",
+ "../portal",
]
-
- if (!rtc_link_pipewire) {
- deps += [ ":pipewire_stubs" ]
- }
-
- public_configs += [ ":pipewire_config" ]
-
- deps += [ "../../rtc_base:sanitizer" ]
}
if (rtc_enable_win_wgc) {
diff --git a/modules/desktop_capture/DEPS b/modules/desktop_capture/DEPS
index 8c894c4..d5f4487 100644
--- a/modules/desktop_capture/DEPS
+++ b/modules/desktop_capture/DEPS
@@ -1,4 +1,5 @@
include_rules = [
+ "+common_video",
"+system_wrappers",
"+third_party/libyuv",
]
diff --git a/modules/desktop_capture/desktop_capture_metadata.h b/modules/desktop_capture/desktop_capture_metadata.h
index faca156..49a20e7 100644
--- a/modules/desktop_capture/desktop_capture_metadata.h
+++ b/modules/desktop_capture/desktop_capture_metadata.h
@@ -12,7 +12,7 @@
#define MODULES_DESKTOP_CAPTURE_DESKTOP_CAPTURE_METADATA_H_
#if defined(WEBRTC_USE_GIO)
-#include "modules/desktop_capture/linux/wayland/xdg_session_details.h"
+#include "modules/portal/xdg_session_details.h"
#endif // defined(WEBRTC_USE_GIO)
namespace webrtc {
diff --git a/modules/desktop_capture/linux/wayland/base_capturer_pipewire.cc b/modules/desktop_capture/linux/wayland/base_capturer_pipewire.cc
index a0af638..e9e45b5 100644
--- a/modules/desktop_capture/linux/wayland/base_capturer_pipewire.cc
+++ b/modules/desktop_capture/linux/wayland/base_capturer_pipewire.cc
@@ -12,9 +12,9 @@
#include "modules/desktop_capture/desktop_capture_options.h"
#include "modules/desktop_capture/desktop_capturer.h"
-#include "modules/desktop_capture/linux/wayland/pipewire_utils.h"
#include "modules/desktop_capture/linux/wayland/restore_token_manager.h"
-#include "modules/desktop_capture/linux/wayland/xdg_desktop_portal_utils.h"
+#include "modules/portal/pipewire_utils.h"
+#include "modules/portal/xdg_desktop_portal_utils.h"
#include "rtc_base/checks.h"
#include "rtc_base/logging.h"
diff --git a/modules/desktop_capture/linux/wayland/base_capturer_pipewire.h b/modules/desktop_capture/linux/wayland/base_capturer_pipewire.h
index d84718a..c5c122c 100644
--- a/modules/desktop_capture/linux/wayland/base_capturer_pipewire.h
+++ b/modules/desktop_capture/linux/wayland/base_capturer_pipewire.h
@@ -14,12 +14,12 @@
#include "modules/desktop_capture/delegated_source_list_controller.h"
#include "modules/desktop_capture/desktop_capture_options.h"
#include "modules/desktop_capture/desktop_capturer.h"
-#include "modules/desktop_capture/linux/wayland/portal_request_response.h"
#include "modules/desktop_capture/linux/wayland/screen_capture_portal_interface.h"
#include "modules/desktop_capture/linux/wayland/screencast_portal.h"
#include "modules/desktop_capture/linux/wayland/shared_screencast_stream.h"
-#include "modules/desktop_capture/linux/wayland/xdg_desktop_portal_utils.h"
-#include "modules/desktop_capture/linux/wayland/xdg_session_details.h"
+#include "modules/portal/portal_request_response.h"
+#include "modules/portal/xdg_desktop_portal_utils.h"
+#include "modules/portal/xdg_session_details.h"
namespace webrtc {
diff --git a/modules/desktop_capture/linux/wayland/portal_request_response.h b/modules/desktop_capture/linux/wayland/portal_request_response.h
index dde9ac5..25894793 100644
--- a/modules/desktop_capture/linux/wayland/portal_request_response.h
+++ b/modules/desktop_capture/linux/wayland/portal_request_response.h
@@ -11,24 +11,7 @@
#ifndef MODULES_DESKTOP_CAPTURE_LINUX_WAYLAND_PORTAL_REQUEST_RESPONSE_H_
#define MODULES_DESKTOP_CAPTURE_LINUX_WAYLAND_PORTAL_REQUEST_RESPONSE_H_
-namespace webrtc {
-namespace xdg_portal {
+// TODO(bugs.webrtc.org/14187): remove when all users are gone
+#include "modules/portal/portal_request_response.h"
-// Contains type of responses that can be observed when making a request to
-// a desktop portal interface.
-enum class RequestResponse {
- // Unknown, the initialized status.
- kUnknown,
- // Success, the request is carried out.
- kSuccess,
- // The user cancelled the interaction.
- kUserCancelled,
- // The user interaction was ended in some other way.
- kError,
-
- kMaxValue = kError,
-};
-
-} // namespace xdg_portal
-} // namespace webrtc
#endif // MODULES_DESKTOP_CAPTURE_LINUX_WAYLAND_PORTAL_REQUEST_RESPONSE_H_
diff --git a/modules/desktop_capture/linux/wayland/scoped_glib.h b/modules/desktop_capture/linux/wayland/scoped_glib.h
index 908bd6f..1361f84 100644
--- a/modules/desktop_capture/linux/wayland/scoped_glib.h
+++ b/modules/desktop_capture/linux/wayland/scoped_glib.h
@@ -11,55 +11,7 @@
#ifndef MODULES_DESKTOP_CAPTURE_LINUX_WAYLAND_SCOPED_GLIB_H_
#define MODULES_DESKTOP_CAPTURE_LINUX_WAYLAND_SCOPED_GLIB_H_
-#include <gio/gio.h>
-
-#include "rtc_base/checks.h"
-
-namespace webrtc {
-
-template <class T>
-class Scoped {
- public:
- Scoped() {}
- explicit Scoped(T* val) { ptr_ = val; }
- ~Scoped() { RTC_DCHECK_NOTREACHED(); }
-
- T* operator->() const { return ptr_; }
-
- explicit operator bool() const { return ptr_ != nullptr; }
-
- bool operator!() const { return ptr_ == nullptr; }
-
- T* get() const { return ptr_; }
-
- T** receive() {
- RTC_CHECK(!ptr_);
- return &ptr_;
- }
-
- Scoped& operator=(T* val) {
- RTC_DCHECK(val);
- ptr_ = val;
- return *this;
- }
-
- protected:
- T* ptr_ = nullptr;
-};
-
-template <>
-Scoped<GError>::~Scoped();
-template <>
-Scoped<char>::~Scoped();
-template <>
-Scoped<GVariant>::~Scoped();
-template <>
-Scoped<GVariantIter>::~Scoped();
-template <>
-Scoped<GDBusMessage>::~Scoped();
-template <>
-Scoped<GUnixFDList>::~Scoped();
-
-} // namespace webrtc
+// TODO(bugs.webrtc.org/14187): remove when all users are gone
+#include "modules/portal/scoped_glib.h"
#endif // MODULES_DESKTOP_CAPTURE_LINUX_WAYLAND_SCOPED_GLIB_H_
diff --git a/modules/desktop_capture/linux/wayland/screen_capture_portal_interface.cc b/modules/desktop_capture/linux/wayland/screen_capture_portal_interface.cc
index 02d9d2e..1c7cc37 100644
--- a/modules/desktop_capture/linux/wayland/screen_capture_portal_interface.cc
+++ b/modules/desktop_capture/linux/wayland/screen_capture_portal_interface.cc
@@ -8,10 +8,10 @@
* be found in the AUTHORS file in the root of the source tree.
*/
#include "modules/desktop_capture/linux/wayland/screen_capture_portal_interface.h"
-#include "modules/desktop_capture/linux/wayland/xdg_desktop_portal_utils.h"
#include <string>
+#include "modules/portal/xdg_desktop_portal_utils.h"
#include "rtc_base/logging.h"
namespace webrtc {
diff --git a/modules/desktop_capture/linux/wayland/screen_capture_portal_interface.h b/modules/desktop_capture/linux/wayland/screen_capture_portal_interface.h
index 59aaf13..deb57a4 100644
--- a/modules/desktop_capture/linux/wayland/screen_capture_portal_interface.h
+++ b/modules/desktop_capture/linux/wayland/screen_capture_portal_interface.h
@@ -15,10 +15,10 @@
#include <string>
-#include "modules/desktop_capture/linux/wayland/portal_request_response.h"
-#include "modules/desktop_capture/linux/wayland/scoped_glib.h"
-#include "modules/desktop_capture/linux/wayland/xdg_desktop_portal_utils.h"
-#include "modules/desktop_capture/linux/wayland/xdg_session_details.h"
+#include "modules/portal/portal_request_response.h"
+#include "modules/portal/scoped_glib.h"
+#include "modules/portal/xdg_desktop_portal_utils.h"
+#include "modules/portal/xdg_session_details.h"
namespace webrtc {
namespace xdg_portal {
diff --git a/modules/desktop_capture/linux/wayland/screencast_portal.cc b/modules/desktop_capture/linux/wayland/screencast_portal.cc
index f9cdb08..9848004 100644
--- a/modules/desktop_capture/linux/wayland/screencast_portal.cc
+++ b/modules/desktop_capture/linux/wayland/screencast_portal.cc
@@ -13,8 +13,8 @@
#include <gio/gunixfdlist.h>
#include <glib-object.h>
-#include "modules/desktop_capture/linux/wayland/scoped_glib.h"
-#include "modules/desktop_capture/linux/wayland/xdg_desktop_portal_utils.h"
+#include "modules/portal/scoped_glib.h"
+#include "modules/portal/xdg_desktop_portal_utils.h"
#include "rtc_base/checks.h"
#include "rtc_base/logging.h"
diff --git a/modules/desktop_capture/linux/wayland/screencast_portal.h b/modules/desktop_capture/linux/wayland/screencast_portal.h
index 96e4ba3..c54d482 100644
--- a/modules/desktop_capture/linux/wayland/screencast_portal.h
+++ b/modules/desktop_capture/linux/wayland/screencast_portal.h
@@ -16,10 +16,10 @@
#include <string>
#include "modules/desktop_capture/desktop_capture_types.h"
-#include "modules/desktop_capture/linux/wayland/portal_request_response.h"
#include "modules/desktop_capture/linux/wayland/screen_capture_portal_interface.h"
-#include "modules/desktop_capture/linux/wayland/xdg_desktop_portal_utils.h"
-#include "modules/desktop_capture/linux/wayland/xdg_session_details.h"
+#include "modules/portal/portal_request_response.h"
+#include "modules/portal/xdg_desktop_portal_utils.h"
+#include "modules/portal/xdg_session_details.h"
namespace webrtc {
diff --git a/modules/desktop_capture/linux/wayland/screencast_stream_utils.cc b/modules/desktop_capture/linux/wayland/screencast_stream_utils.cc
index dc07847..0c4900d 100644
--- a/modules/desktop_capture/linux/wayland/screencast_stream_utils.cc
+++ b/modules/desktop_capture/linux/wayland/screencast_stream_utils.cc
@@ -27,15 +27,6 @@
namespace webrtc {
-PipeWireThreadLoopLock::PipeWireThreadLoopLock(pw_thread_loop* loop)
- : loop_(loop) {
- pw_thread_loop_lock(loop_);
-}
-
-PipeWireThreadLoopLock::~PipeWireThreadLoopLock() {
- pw_thread_loop_unlock(loop_);
-}
-
PipeWireVersion PipeWireVersion::Parse(const absl::string_view& version) {
std::vector<absl::string_view> parsed_version = rtc::split(version, '.');
diff --git a/modules/desktop_capture/linux/wayland/screencast_stream_utils.h b/modules/desktop_capture/linux/wayland/screencast_stream_utils.h
index 70262c2..e04d7db 100644
--- a/modules/desktop_capture/linux/wayland/screencast_stream_utils.h
+++ b/modules/desktop_capture/linux/wayland/screencast_stream_utils.h
@@ -18,23 +18,12 @@
#include "rtc_base/string_encode.h"
-struct pw_thread_loop;
struct spa_pod;
struct spa_pod_builder;
struct spa_rectangle;
namespace webrtc {
-// Locks pw_thread_loop in the current scope
-class PipeWireThreadLoopLock {
- public:
- explicit PipeWireThreadLoopLock(pw_thread_loop* loop);
- ~PipeWireThreadLoopLock();
-
- private:
- pw_thread_loop* const loop_;
-};
-
struct PipeWireVersion {
static PipeWireVersion Parse(const absl::string_view& version);
diff --git a/modules/desktop_capture/linux/wayland/shared_screencast_stream.cc b/modules/desktop_capture/linux/wayland/shared_screencast_stream.cc
index 4651486..7a2b9ba 100644
--- a/modules/desktop_capture/linux/wayland/shared_screencast_stream.cc
+++ b/modules/desktop_capture/linux/wayland/shared_screencast_stream.cc
@@ -20,8 +20,8 @@
#include "absl/memory/memory.h"
#include "modules/desktop_capture/linux/wayland/egl_dmabuf.h"
-#include "modules/desktop_capture/linux/wayland/pipewire_utils.h"
#include "modules/desktop_capture/linux/wayland/screencast_stream_utils.h"
+#include "modules/portal/pipewire_utils.h"
#include "rtc_base/checks.h"
#include "rtc_base/logging.h"
#include "rtc_base/sanitizer.h"
diff --git a/modules/desktop_capture/linux/wayland/test/test_screencast_stream_provider.cc b/modules/desktop_capture/linux/wayland/test/test_screencast_stream_provider.cc
index bf212d0..3b82995 100644
--- a/modules/desktop_capture/linux/wayland/test/test_screencast_stream_provider.cc
+++ b/modules/desktop_capture/linux/wayland/test/test_screencast_stream_provider.cc
@@ -20,7 +20,7 @@
#include <utility>
#include <vector>
-#include "modules/desktop_capture/linux/wayland/pipewire_utils.h"
+#include "modules/portal/pipewire_utils.h"
#include "rtc_base/logging.h"
namespace webrtc {
diff --git a/modules/desktop_capture/linux/wayland/xdg_desktop_portal_utils.h b/modules/desktop_capture/linux/wayland/xdg_desktop_portal_utils.h
index f6ac92b..b213e50 100644
--- a/modules/desktop_capture/linux/wayland/xdg_desktop_portal_utils.h
+++ b/modules/desktop_capture/linux/wayland/xdg_desktop_portal_utils.h
@@ -11,101 +11,7 @@
#ifndef MODULES_DESKTOP_CAPTURE_LINUX_WAYLAND_XDG_DESKTOP_PORTAL_UTILS_H_
#define MODULES_DESKTOP_CAPTURE_LINUX_WAYLAND_XDG_DESKTOP_PORTAL_UTILS_H_
-#include <gio/gio.h>
-#include <stdint.h>
-
-#include <string>
-#include <vector>
-
-#include "absl/strings/string_view.h"
-#include "modules/desktop_capture/linux/wayland/portal_request_response.h"
-#include "modules/desktop_capture/linux/wayland/scoped_glib.h"
-#include "modules/desktop_capture/linux/wayland/xdg_session_details.h"
-#include "rtc_base/checks.h"
-#include "rtc_base/logging.h"
-
-namespace webrtc {
-namespace xdg_portal {
-
-constexpr char kDesktopBusName[] = "org.freedesktop.portal.Desktop";
-constexpr char kDesktopObjectPath[] = "/org/freedesktop/portal/desktop";
-constexpr char kDesktopRequestObjectPath[] =
- "/org/freedesktop/portal/desktop/request";
-constexpr char kSessionInterfaceName[] = "org.freedesktop.portal.Session";
-constexpr char kRequestInterfaceName[] = "org.freedesktop.portal.Request";
-constexpr char kScreenCastInterfaceName[] = "org.freedesktop.portal.ScreenCast";
-
-using ProxyRequestCallback = void (*)(GObject*, GAsyncResult*, gpointer);
-using SessionRequestCallback = void (*)(GDBusProxy*, GAsyncResult*, gpointer);
-using SessionRequestResponseSignalHandler = void (*)(GDBusConnection*,
- const char*,
- const char*,
- const char*,
- const char*,
- GVariant*,
- gpointer);
-using StartRequestResponseSignalHandler = void (*)(GDBusConnection*,
- const char*,
- const char*,
- const char*,
- const char*,
- GVariant*,
- gpointer);
-using SessionStartRequestedHandler = void (*)(GDBusProxy*,
- GAsyncResult*,
- gpointer);
-
-std::string RequestResponseToString(RequestResponse request);
-
-RequestResponse RequestResponseFromPortalResponse(uint32_t portal_response);
-
-// Returns a string path for signal handle based on the provided connection and
-// token.
-std::string PrepareSignalHandle(absl::string_view token,
- GDBusConnection* connection);
-
-// Sets up the callback to execute when a response signal is received for the
-// given object.
-uint32_t SetupRequestResponseSignal(absl::string_view object_path,
- const GDBusSignalCallback callback,
- gpointer user_data,
- GDBusConnection* connection);
-
-void RequestSessionProxy(absl::string_view interface_name,
- const ProxyRequestCallback proxy_request_callback,
- GCancellable* cancellable,
- gpointer user_data);
-
-void SetupSessionRequestHandlers(
- absl::string_view portal_prefix,
- const SessionRequestCallback session_request_callback,
- const SessionRequestResponseSignalHandler request_response_signale_handler,
- GDBusConnection* connection,
- GDBusProxy* proxy,
- GCancellable* cancellable,
- std::string& portal_handle,
- guint& session_request_signal_id,
- gpointer user_data);
-
-void StartSessionRequest(
- absl::string_view prefix,
- absl::string_view session_handle,
- const StartRequestResponseSignalHandler signal_handler,
- const SessionStartRequestedHandler session_started_handler,
- GDBusProxy* proxy,
- GDBusConnection* connection,
- GCancellable* cancellable,
- guint& start_request_signal_id,
- std::string& start_handle,
- gpointer user_data);
-
-// Tears down the portal session and cleans up related objects.
-void TearDownSession(absl::string_view session_handle,
- GDBusProxy* proxy,
- GCancellable* cancellable,
- GDBusConnection* connection);
-
-} // namespace xdg_portal
-} // namespace webrtc
+// TODO(bugs.webrtc.org/14187): remove when all users are gone
+#include "modules/portal/xdg_desktop_portal_utils.h"
#endif // MODULES_DESKTOP_CAPTURE_LINUX_WAYLAND_XDG_DESKTOP_PORTAL_UTILS_H_
diff --git a/modules/desktop_capture/linux/wayland/xdg_session_details.h b/modules/desktop_capture/linux/wayland/xdg_session_details.h
index b70ac4a..9feff5b 100644
--- a/modules/desktop_capture/linux/wayland/xdg_session_details.h
+++ b/modules/desktop_capture/linux/wayland/xdg_session_details.h
@@ -11,23 +11,7 @@
#ifndef MODULES_DESKTOP_CAPTURE_LINUX_WAYLAND_XDG_SESSION_DETAILS_H_
#define MODULES_DESKTOP_CAPTURE_LINUX_WAYLAND_XDG_SESSION_DETAILS_H_
-#include <gio/gio.h>
-
-#include <string>
-
-namespace webrtc {
-namespace xdg_portal {
-
-// Details of the session associated with XDG desktop portal session. Portal API
-// calls can be invoked by utilizing the information here.
-struct SessionDetails {
- GDBusProxy* proxy = nullptr;
- GCancellable* cancellable = nullptr;
- std::string session_handle;
- uint32_t pipewire_stream_node_id = 0;
-};
-
-} // namespace xdg_portal
-} // namespace webrtc
+// TODO(bugs.webrtc.org/14187): remove when all users are gone
+#include "modules/portal/xdg_session_details.h"
#endif // MODULES_DESKTOP_CAPTURE_LINUX_WAYLAND_XDG_SESSION_DETAILS_H_
diff --git a/modules/portal/BUILD.gn b/modules/portal/BUILD.gn
new file mode 100644
index 0000000..730d327
--- /dev/null
+++ b/modules/portal/BUILD.gn
@@ -0,0 +1,124 @@
+# Copyright (c) 2022 The WebRTC project authors. All Rights Reserved.
+#
+# Use of this source code is governed by a BSD-style license
+# that can be found in the LICENSE file in the root of the source
+# tree. An additional intellectual property rights grant can be found
+# in the file PATENTS. All contributing project authors may
+# be found in the AUTHORS file in the root of the source tree.
+
+import("//build/config/linux/pkg_config.gni")
+import("//tools/generate_stubs/rules.gni")
+import("../../webrtc.gni")
+
+assert(is_linux)
+assert(rtc_use_pipewire)
+
+pkg_config("gio") {
+ packages = [
+ "gio-2.0",
+ "gio-unix-2.0",
+ ]
+}
+
+pkg_config("pipewire") {
+ packages = [ "libpipewire-0.3" ]
+ if (!rtc_link_pipewire) {
+ ignore_libs = true
+ }
+}
+
+pkg_config("gbm") {
+ packages = [ "gbm" ]
+}
+pkg_config("egl") {
+ packages = [ "egl" ]
+}
+pkg_config("epoxy") {
+ packages = [ "epoxy" ]
+ ignore_libs = true
+}
+pkg_config("libdrm") {
+ packages = [ "libdrm" ]
+}
+
+if (!rtc_link_pipewire) {
+ # When libpipewire is not directly linked, use stubs to allow for dlopening of
+ # the binary.
+ generate_stubs("pipewire_stubs") {
+ configs = [
+ "../../:common_config",
+ ":pipewire",
+ ]
+ deps = [ "../../rtc_base" ]
+ extra_header = "pipewire_stub_header.fragment"
+ logging_function = "RTC_LOG(LS_VERBOSE)"
+ logging_include = "rtc_base/logging.h"
+ output_name = "pipewire_stubs"
+ path_from_source = "modules/portal"
+ sigs = [ "pipewire.sigs" ]
+ if (!build_with_chromium) {
+ macro_include = "rtc_base/system/no_cfi_icall.h"
+ macro_deps = [ "../../rtc_base/system:no_cfi_icall" ]
+ }
+ }
+}
+
+config("pipewire_base") {
+ configs = [
+ ":gio",
+ ":pipewire",
+ ]
+}
+
+config("pipewire_all") {
+ configs = [
+ ":pipewire_base",
+ ":gbm",
+ ":egl",
+ ":epoxy",
+ ":libdrm",
+ ]
+}
+
+config("pipewire_config") {
+ defines = [ "WEBRTC_USE_PIPEWIRE" ]
+
+ # Chromecast build config overrides `WEBRTC_USE_PIPEWIRE` even when
+ # `rtc_use_pipewire` is not set, which causes pipewire_config to not be
+ # included in targets. More details in: webrtc:13898
+ if (is_linux && !is_castos) {
+ defines += [ "WEBRTC_USE_GIO" ]
+ }
+}
+
+rtc_library("portal") {
+ sources = [
+ "pipewire_utils.cc",
+ "pipewire_utils.h",
+ "portal_request_response.h",
+ "scoped_glib.cc",
+ "scoped_glib.h",
+ "xdg_desktop_portal_utils.cc",
+ "xdg_desktop_portal_utils.h",
+ "xdg_session_details.h",
+ ]
+
+ configs += [
+ ":gio",
+ ":pipewire",
+ ":pipewire_config",
+ ]
+
+ deps = [
+ "../../rtc_base:checks",
+ "../../rtc_base:logging",
+ "../../rtc_base:sanitizer",
+ ]
+ absl_deps = [ "//third_party/abseil-cpp/absl/strings" ]
+
+ if (!rtc_link_pipewire) {
+ defines = [ "WEBRTC_DLOPEN_PIPEWIRE" ]
+
+ deps += [ ":pipewire_stubs" ]
+ }
+}
diff --git a/modules/portal/OWNERS b/modules/portal/OWNERS
new file mode 100644
index 0000000..e3bc32e
--- /dev/null
+++ b/modules/portal/OWNERS
@@ -0,0 +1,2 @@
+alcooper@chromium.org
+mfoltz@chromium.org
diff --git a/modules/desktop_capture/linux/wayland/pipewire.sigs b/modules/portal/pipewire.sigs
similarity index 100%
rename from modules/desktop_capture/linux/wayland/pipewire.sigs
rename to modules/portal/pipewire.sigs
diff --git a/modules/desktop_capture/linux/wayland/pipewire_stub_header.fragment b/modules/portal/pipewire_stub_header.fragment
similarity index 100%
rename from modules/desktop_capture/linux/wayland/pipewire_stub_header.fragment
rename to modules/portal/pipewire_stub_header.fragment
diff --git a/modules/desktop_capture/linux/wayland/pipewire_utils.cc b/modules/portal/pipewire_utils.cc
similarity index 68%
rename from modules/desktop_capture/linux/wayland/pipewire_utils.cc
rename to modules/portal/pipewire_utils.cc
index 878e459..fd96b4a 100644
--- a/modules/desktop_capture/linux/wayland/pipewire_utils.cc
+++ b/modules/portal/pipewire_utils.cc
@@ -8,12 +8,14 @@
* be found in the AUTHORS file in the root of the source tree.
*/
-#include "modules/desktop_capture/linux/wayland/pipewire_utils.h"
+#include "modules/portal/pipewire_utils.h"
+
+#include <pipewire/pipewire.h>
#include "rtc_base/sanitizer.h"
#if defined(WEBRTC_DLOPEN_PIPEWIRE)
-#include "modules/desktop_capture/linux/wayland/pipewire_stubs.h"
+#include "modules/portal/pipewire_stubs.h"
#endif // defined(WEBRTC_DLOPEN_PIPEWIRE)
namespace webrtc {
@@ -23,10 +25,10 @@
#if defined(WEBRTC_DLOPEN_PIPEWIRE)
static constexpr char kPipeWireLib[] = "libpipewire-0.3.so.0";
- using modules_desktop_capture_linux_wayland::InitializeStubs;
- using modules_desktop_capture_linux_wayland::kModulePipewire;
+ using modules_portal::InitializeStubs;
+ using modules_portal::kModulePipewire;
- modules_desktop_capture_linux_wayland::StubPathMap paths;
+ modules_portal::StubPathMap paths;
// Check if the PipeWire library is available.
paths[kModulePipewire].push_back(kPipeWireLib);
@@ -39,4 +41,13 @@
#endif // defined(WEBRTC_DLOPEN_PIPEWIRE)
}
+PipeWireThreadLoopLock::PipeWireThreadLoopLock(pw_thread_loop* loop)
+ : loop_(loop) {
+ pw_thread_loop_lock(loop_);
+}
+
+PipeWireThreadLoopLock::~PipeWireThreadLoopLock() {
+ pw_thread_loop_unlock(loop_);
+}
+
} // namespace webrtc
diff --git a/modules/desktop_capture/linux/wayland/pipewire_utils.h b/modules/portal/pipewire_utils.h
similarity index 65%
rename from modules/desktop_capture/linux/wayland/pipewire_utils.h
rename to modules/portal/pipewire_utils.h
index b785d39..0f5ccf3 100644
--- a/modules/desktop_capture/linux/wayland/pipewire_utils.h
+++ b/modules/portal/pipewire_utils.h
@@ -8,8 +8,10 @@
* be found in the AUTHORS file in the root of the source tree.
*/
-#ifndef MODULES_DESKTOP_CAPTURE_LINUX_WAYLAND_PIPEWIRE_UTILS_H_
-#define MODULES_DESKTOP_CAPTURE_LINUX_WAYLAND_PIPEWIRE_UTILS_H_
+#ifndef MODULES_PORTAL_PIPEWIRE_UTILS_H_
+#define MODULES_PORTAL_PIPEWIRE_UTILS_H_
+
+struct pw_thread_loop;
namespace webrtc {
@@ -18,6 +20,16 @@
// running nor does it establish a connection to one.
bool InitializePipeWire();
+// Locks pw_thread_loop in the current scope
+class PipeWireThreadLoopLock {
+ public:
+ explicit PipeWireThreadLoopLock(pw_thread_loop* loop);
+ ~PipeWireThreadLoopLock();
+
+ private:
+ pw_thread_loop* const loop_;
+};
+
} // namespace webrtc
-#endif // MODULES_DESKTOP_CAPTURE_LINUX_WAYLAND_PIPEWIRE_UTILS_H_
+#endif // MODULES_PORTAL_PIPEWIRE_UTILS_H_
diff --git a/modules/portal/portal_request_response.h b/modules/portal/portal_request_response.h
new file mode 100644
index 0000000..5fac4eb
--- /dev/null
+++ b/modules/portal/portal_request_response.h
@@ -0,0 +1,34 @@
+/*
+ * Copyright (c) 2022 The WebRTC project authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style license
+ * that can be found in the LICENSE file in the root of the source
+ * tree. An additional intellectual property rights grant can be found
+ * in the file PATENTS. All contributing project authors may
+ * be found in the AUTHORS file in the root of the source tree.
+ */
+
+#ifndef MODULES_PORTAL_PORTAL_REQUEST_RESPONSE_H_
+#define MODULES_PORTAL_PORTAL_REQUEST_RESPONSE_H_
+
+namespace webrtc {
+namespace xdg_portal {
+
+// Contains type of responses that can be observed when making a request to
+// a desktop portal interface.
+enum class RequestResponse {
+ // Unknown, the initialized status.
+ kUnknown,
+ // Success, the request is carried out.
+ kSuccess,
+ // The user cancelled the interaction.
+ kUserCancelled,
+ // The user interaction was ended in some other way.
+ kError,
+
+ kMaxValue = kError,
+};
+
+} // namespace xdg_portal
+} // namespace webrtc
+#endif // MODULES_PORTAL_PORTAL_REQUEST_RESPONSE_H_
diff --git a/modules/desktop_capture/linux/wayland/scoped_glib.cc b/modules/portal/scoped_glib.cc
similarity index 93%
rename from modules/desktop_capture/linux/wayland/scoped_glib.cc
rename to modules/portal/scoped_glib.cc
index 0d9a87d..cb4c805 100644
--- a/modules/desktop_capture/linux/wayland/scoped_glib.cc
+++ b/modules/portal/scoped_glib.cc
@@ -8,7 +8,7 @@
* be found in the AUTHORS file in the root of the source tree.
*/
-#include "modules/desktop_capture/linux/wayland/scoped_glib.h"
+#include "modules/portal/scoped_glib.h"
namespace webrtc {
diff --git a/modules/portal/scoped_glib.h b/modules/portal/scoped_glib.h
new file mode 100644
index 0000000..b2aaa2e
--- /dev/null
+++ b/modules/portal/scoped_glib.h
@@ -0,0 +1,65 @@
+/*
+ * Copyright 2022 The WebRTC project authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style license
+ * that can be found in the LICENSE file in the root of the source
+ * tree. An additional intellectual property rights grant can be found
+ * in the file PATENTS. All contributing project authors may
+ * be found in the AUTHORS file in the root of the source tree.
+ */
+
+#ifndef MODULES_PORTAL_SCOPED_GLIB_H_
+#define MODULES_PORTAL_SCOPED_GLIB_H_
+
+#include <gio/gio.h>
+
+#include "rtc_base/checks.h"
+
+namespace webrtc {
+
+template <class T>
+class Scoped {
+ public:
+ Scoped() {}
+ explicit Scoped(T* val) { ptr_ = val; }
+ ~Scoped() { RTC_DCHECK_NOTREACHED(); }
+
+ T* operator->() const { return ptr_; }
+
+ explicit operator bool() const { return ptr_ != nullptr; }
+
+ bool operator!() const { return ptr_ == nullptr; }
+
+ T* get() const { return ptr_; }
+
+ T** receive() {
+ RTC_CHECK(!ptr_);
+ return &ptr_;
+ }
+
+ Scoped& operator=(T* val) {
+ RTC_DCHECK(val);
+ ptr_ = val;
+ return *this;
+ }
+
+ protected:
+ T* ptr_ = nullptr;
+};
+
+template <>
+Scoped<GError>::~Scoped();
+template <>
+Scoped<char>::~Scoped();
+template <>
+Scoped<GVariant>::~Scoped();
+template <>
+Scoped<GVariantIter>::~Scoped();
+template <>
+Scoped<GDBusMessage>::~Scoped();
+template <>
+Scoped<GUnixFDList>::~Scoped();
+
+} // namespace webrtc
+
+#endif // MODULES_PORTAL_SCOPED_GLIB_H_
diff --git a/modules/desktop_capture/linux/wayland/xdg_desktop_portal_utils.cc b/modules/portal/xdg_desktop_portal_utils.cc
similarity index 97%
rename from modules/desktop_capture/linux/wayland/xdg_desktop_portal_utils.cc
rename to modules/portal/xdg_desktop_portal_utils.cc
index 75dbf2b..271e084 100644
--- a/modules/desktop_capture/linux/wayland/xdg_desktop_portal_utils.cc
+++ b/modules/portal/xdg_desktop_portal_utils.cc
@@ -7,12 +7,12 @@
* in the file PATENTS. All contributing project authors may
* be found in the AUTHORS file in the root of the source tree.
*/
-#include "modules/desktop_capture/linux/wayland/xdg_desktop_portal_utils.h"
+#include "modules/portal/xdg_desktop_portal_utils.h"
#include <string>
#include "absl/strings/string_view.h"
-#include "modules/desktop_capture/linux/wayland/scoped_glib.h"
+#include "modules/portal/scoped_glib.h"
#include "rtc_base/logging.h"
namespace webrtc {
diff --git a/modules/portal/xdg_desktop_portal_utils.h b/modules/portal/xdg_desktop_portal_utils.h
new file mode 100644
index 0000000..8571c64
--- /dev/null
+++ b/modules/portal/xdg_desktop_portal_utils.h
@@ -0,0 +1,111 @@
+/*
+ * Copyright 2022 The WebRTC project authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style license
+ * that can be found in the LICENSE file in the root of the source
+ * tree. An additional intellectual property rights grant can be found
+ * in the file PATENTS. All contributing project authors may
+ * be found in the AUTHORS file in the root of the source tree.
+ */
+
+#ifndef MODULES_PORTAL_XDG_DESKTOP_PORTAL_UTILS_H_
+#define MODULES_PORTAL_XDG_DESKTOP_PORTAL_UTILS_H_
+
+#include <gio/gio.h>
+#include <stdint.h>
+
+#include <string>
+#include <vector>
+
+#include "absl/strings/string_view.h"
+#include "modules/portal/portal_request_response.h"
+#include "modules/portal/scoped_glib.h"
+#include "modules/portal/xdg_session_details.h"
+#include "rtc_base/checks.h"
+#include "rtc_base/logging.h"
+
+namespace webrtc {
+namespace xdg_portal {
+
+constexpr char kDesktopBusName[] = "org.freedesktop.portal.Desktop";
+constexpr char kDesktopObjectPath[] = "/org/freedesktop/portal/desktop";
+constexpr char kDesktopRequestObjectPath[] =
+ "/org/freedesktop/portal/desktop/request";
+constexpr char kSessionInterfaceName[] = "org.freedesktop.portal.Session";
+constexpr char kRequestInterfaceName[] = "org.freedesktop.portal.Request";
+constexpr char kScreenCastInterfaceName[] = "org.freedesktop.portal.ScreenCast";
+
+using ProxyRequestCallback = void (*)(GObject*, GAsyncResult*, gpointer);
+using SessionRequestCallback = void (*)(GDBusProxy*, GAsyncResult*, gpointer);
+using SessionRequestResponseSignalHandler = void (*)(GDBusConnection*,
+ const char*,
+ const char*,
+ const char*,
+ const char*,
+ GVariant*,
+ gpointer);
+using StartRequestResponseSignalHandler = void (*)(GDBusConnection*,
+ const char*,
+ const char*,
+ const char*,
+ const char*,
+ GVariant*,
+ gpointer);
+using SessionStartRequestedHandler = void (*)(GDBusProxy*,
+ GAsyncResult*,
+ gpointer);
+
+std::string RequestResponseToString(RequestResponse request);
+
+RequestResponse RequestResponseFromPortalResponse(uint32_t portal_response);
+
+// Returns a string path for signal handle based on the provided connection and
+// token.
+std::string PrepareSignalHandle(absl::string_view token,
+ GDBusConnection* connection);
+
+// Sets up the callback to execute when a response signal is received for the
+// given object.
+uint32_t SetupRequestResponseSignal(absl::string_view object_path,
+ const GDBusSignalCallback callback,
+ gpointer user_data,
+ GDBusConnection* connection);
+
+void RequestSessionProxy(absl::string_view interface_name,
+ const ProxyRequestCallback proxy_request_callback,
+ GCancellable* cancellable,
+ gpointer user_data);
+
+void SetupSessionRequestHandlers(
+ absl::string_view portal_prefix,
+ const SessionRequestCallback session_request_callback,
+ const SessionRequestResponseSignalHandler request_response_signale_handler,
+ GDBusConnection* connection,
+ GDBusProxy* proxy,
+ GCancellable* cancellable,
+ std::string& portal_handle,
+ guint& session_request_signal_id,
+ gpointer user_data);
+
+void StartSessionRequest(
+ absl::string_view prefix,
+ absl::string_view session_handle,
+ const StartRequestResponseSignalHandler signal_handler,
+ const SessionStartRequestedHandler session_started_handler,
+ GDBusProxy* proxy,
+ GDBusConnection* connection,
+ GCancellable* cancellable,
+ guint& start_request_signal_id,
+ std::string& start_handle,
+ gpointer user_data);
+
+// Tears down the portal session and cleans up related objects.
+void TearDownSession(absl::string_view session_handle,
+ GDBusProxy* proxy,
+ GCancellable* cancellable,
+ GDBusConnection* connection);
+
+} // namespace xdg_portal
+} // namespace webrtc
+
+#endif // MODULES_PORTAL_XDG_DESKTOP_PORTAL_UTILS_H_
diff --git a/modules/portal/xdg_session_details.h b/modules/portal/xdg_session_details.h
new file mode 100644
index 0000000..ab52508
--- /dev/null
+++ b/modules/portal/xdg_session_details.h
@@ -0,0 +1,33 @@
+/*
+ * Copyright 2022 The WebRTC project authors. All Rights Reserved.
+ *
+ * Use of this source code is governed by a BSD-style license
+ * that can be found in the LICENSE file in the root of the source
+ * tree. An additional intellectual property rights grant can be found
+ * in the file PATENTS. All contributing project authors may
+ * be found in the AUTHORS file in the root of the source tree.
+ */
+
+#ifndef MODULES_PORTAL_XDG_SESSION_DETAILS_H_
+#define MODULES_PORTAL_XDG_SESSION_DETAILS_H_
+
+#include <gio/gio.h>
+
+#include <string>
+
+namespace webrtc {
+namespace xdg_portal {
+
+// Details of the session associated with XDG desktop portal session. Portal API
+// calls can be invoked by utilizing the information here.
+struct SessionDetails {
+ GDBusProxy* proxy = nullptr;
+ GCancellable* cancellable = nullptr;
+ std::string session_handle;
+ uint32_t pipewire_stream_node_id = 0;
+};
+
+} // namespace xdg_portal
+} // namespace webrtc
+
+#endif // MODULES_PORTAL_XDG_SESSION_DETAILS_H_