summaryrefslogtreecommitdiff
path: root/platform/linuxbsd
diff options
context:
space:
mode:
Diffstat (limited to 'platform/linuxbsd')
-rw-r--r--platform/linuxbsd/detect.py16
-rw-r--r--platform/linuxbsd/display_server_x11.cpp95
-rw-r--r--platform/linuxbsd/display_server_x11.h6
-rw-r--r--platform/linuxbsd/freedesktop_screensaver.cpp4
-rw-r--r--platform/linuxbsd/os_linuxbsd.cpp5
5 files changed, 92 insertions, 34 deletions
diff --git a/platform/linuxbsd/detect.py b/platform/linuxbsd/detect.py
index 8eb22c1c72..4b3804d049 100644
--- a/platform/linuxbsd/detect.py
+++ b/platform/linuxbsd/detect.py
@@ -105,14 +105,12 @@ def configure(env):
env.Prepend(CCFLAGS=["-O2"])
elif env["optimize"] == "size": # optimize for size
env.Prepend(CCFLAGS=["-Os"])
- env.Prepend(CPPDEFINES=["DEBUG_ENABLED"])
if env["debug_symbols"]:
env.Prepend(CCFLAGS=["-g2"])
elif env["target"] == "debug":
env.Prepend(CCFLAGS=["-g3"])
- env.Prepend(CPPDEFINES=["DEBUG_ENABLED"])
env.Append(LINKFLAGS=["-rdynamic"])
## Architecture
@@ -121,6 +119,13 @@ def configure(env):
if env["bits"] == "default":
env["bits"] = "64" if is64 else "32"
+ if env["arch"] == "" and platform.machine() == "riscv64":
+ env["arch"] = "rv64"
+
+ if env["arch"] == "rv64":
+ # G = General-purpose extensions, C = Compression extension (very common).
+ env.Append(CCFLAGS=["-march=rv64gc"])
+
## Compiler configuration
if "CXX" in env and "clang" in os.path.basename(env["CXX"]):
@@ -290,17 +295,10 @@ def configure(env):
if any(platform.machine() in s for s in list_of_x86):
env["x86_libtheora_opt_gcc"] = True
- if not env["builtin_libvpx"]:
- env.ParseConfig("pkg-config vpx --cflags --libs")
-
if not env["builtin_libvorbis"]:
env["builtin_libogg"] = False # Needed to link against system libvorbis
env.ParseConfig("pkg-config vorbis vorbisfile --cflags --libs")
- if not env["builtin_opus"]:
- env["builtin_libogg"] = False # Needed to link against system opus
- env.ParseConfig("pkg-config opus opusfile --cflags --libs")
-
if not env["builtin_libogg"]:
env.ParseConfig("pkg-config ogg --cflags --libs")
diff --git a/platform/linuxbsd/display_server_x11.cpp b/platform/linuxbsd/display_server_x11.cpp
index f2cd336b39..5fe28935b9 100644
--- a/platform/linuxbsd/display_server_x11.cpp
+++ b/platform/linuxbsd/display_server_x11.cpp
@@ -124,6 +124,7 @@ bool DisplayServerX11::has_feature(Feature p_feature) const {
#ifdef DBUS_ENABLED
case FEATURE_KEEP_SCREEN_ON:
#endif
+ case FEATURE_CLIPBOARD_PRIMARY:
return true;
default: {
}
@@ -406,6 +407,20 @@ void DisplayServerX11::clipboard_set(const String &p_text) {
XSetSelectionOwner(x11_display, XInternAtom(x11_display, "CLIPBOARD", 0), windows[MAIN_WINDOW_ID].x11_window, CurrentTime);
}
+void DisplayServerX11::clipboard_set_primary(const String &p_text) {
+ _THREAD_SAFE_METHOD_
+ if (!p_text.is_empty()) {
+ {
+ // The clipboard content can be accessed while polling for events.
+ MutexLock mutex_lock(events_mutex);
+ internal_clipboard_primary = p_text;
+ }
+
+ XSetSelectionOwner(x11_display, XA_PRIMARY, windows[MAIN_WINDOW_ID].x11_window, CurrentTime);
+ XSetSelectionOwner(x11_display, XInternAtom(x11_display, "PRIMARY", 0), windows[MAIN_WINDOW_ID].x11_window, CurrentTime);
+ }
+}
+
Bool DisplayServerX11::_predicate_clipboard_selection(Display *display, XEvent *event, XPointer arg) {
if (event->type == SelectionNotify && event->xselection.requestor == *(Window *)arg) {
return True;
@@ -427,7 +442,12 @@ String DisplayServerX11::_clipboard_get_impl(Atom p_source, Window x11_window, A
Window selection_owner = XGetSelectionOwner(x11_display, p_source);
if (selection_owner == x11_window) {
- return internal_clipboard;
+ static const char *target_type = "PRIMARY";
+ if (p_source != None && String(XGetAtomName(x11_display, p_source)) == target_type) {
+ return internal_clipboard_primary;
+ } else {
+ return internal_clipboard;
+ }
}
if (selection_owner != None) {
@@ -580,6 +600,19 @@ String DisplayServerX11::clipboard_get() const {
return ret;
}
+String DisplayServerX11::clipboard_get_primary() const {
+ _THREAD_SAFE_METHOD_
+
+ String ret;
+ ret = _clipboard_get(XInternAtom(x11_display, "PRIMARY", 0), windows[MAIN_WINDOW_ID].x11_window);
+
+ if (ret.is_empty()) {
+ ret = _clipboard_get(XA_PRIMARY, windows[MAIN_WINDOW_ID].x11_window);
+ }
+
+ return ret;
+}
+
Bool DisplayServerX11::_predicate_clipboard_save_targets(Display *display, XEvent *event, XPointer arg) {
if (event->xany.window == *(Window *)arg) {
return (event->type == SelectionRequest) ||
@@ -2417,7 +2450,7 @@ void DisplayServerX11::_handle_key_event(WindowID p_window, XKeyEvent *p_event,
Input::get_singleton()->parse_input_event(k);
}
-Atom DisplayServerX11::_process_selection_request_target(Atom p_target, Window p_requestor, Atom p_property) const {
+Atom DisplayServerX11::_process_selection_request_target(Atom p_target, Window p_requestor, Atom p_property, Atom p_selection) const {
if (p_target == XInternAtom(x11_display, "TARGETS", 0)) {
// Request to list all supported targets.
Atom data[9];
@@ -2459,7 +2492,13 @@ Atom DisplayServerX11::_process_selection_request_target(Atom p_target, Window p
p_target == XInternAtom(x11_display, "text/plain", 0)) {
// Directly using internal clipboard because we know our window
// is the owner during a selection request.
- CharString clip = internal_clipboard.utf8();
+ CharString clip;
+ static const char *target_type = "PRIMARY";
+ if (p_selection != None && String(XGetAtomName(x11_display, p_selection)) == target_type) {
+ clip = internal_clipboard_primary.utf8();
+ } else {
+ clip = internal_clipboard.utf8();
+ }
XChangeProperty(x11_display,
p_requestor,
p_property,
@@ -2497,7 +2536,7 @@ void DisplayServerX11::_handle_selection_request_event(XSelectionRequestEvent *p
for (uint64_t i = 0; i < len; i += 2) {
Atom target = targets[i];
Atom &property = targets[i + 1];
- property = _process_selection_request_target(target, p_event->requestor, property);
+ property = _process_selection_request_target(target, p_event->requestor, property, p_event->selection);
}
XChangeProperty(x11_display,
@@ -2515,7 +2554,7 @@ void DisplayServerX11::_handle_selection_request_event(XSelectionRequestEvent *p
}
} else {
// Request for target conversion.
- respond.xselection.property = _process_selection_request_target(p_event->target, p_event->requestor, p_event->property);
+ respond.xselection.property = _process_selection_request_target(p_event->target, p_event->requestor, p_event->property, p_event->selection);
}
respond.xselection.type = SelectionNotify;
@@ -2686,27 +2725,34 @@ void DisplayServerX11::_poll_events() {
{
MutexLock mutex_lock(events_mutex);
- // Non-blocking wait for next event and remove it from the queue.
- XEvent ev;
- while (XCheckIfEvent(x11_display, &ev, _predicate_all_events, nullptr)) {
- // Check if the input manager wants to process the event.
- if (XFilterEvent(&ev, None)) {
- // Event has been filtered by the Input Manager,
- // it has to be ignored and a new one will be received.
- continue;
- }
+ _check_pending_events(polled_events);
+ }
+ }
+}
- // Handle selection request events directly in the event thread, because
- // communication through the x server takes several events sent back and forth
- // and we don't want to block other programs while processing only one each frame.
- if (ev.type == SelectionRequest) {
- _handle_selection_request_event(&(ev.xselectionrequest));
- continue;
- }
+void DisplayServerX11::_check_pending_events(LocalVector<XEvent> &r_events) {
+ // Flush to make sure to gather all pending events.
+ XFlush(x11_display);
- polled_events.push_back(ev);
- }
+ // Non-blocking wait for next event and remove it from the queue.
+ XEvent ev;
+ while (XCheckIfEvent(x11_display, &ev, _predicate_all_events, nullptr)) {
+ // Check if the input manager wants to process the event.
+ if (XFilterEvent(&ev, None)) {
+ // Event has been filtered by the Input Manager,
+ // it has to be ignored and a new one will be received.
+ continue;
}
+
+ // Handle selection request events directly in the event thread, because
+ // communication through the x server takes several events sent back and forth
+ // and we don't want to block other programs while processing only one each frame.
+ if (ev.type == SelectionRequest) {
+ _handle_selection_request_event(&(ev.xselectionrequest));
+ continue;
+ }
+
+ r_events.push_back(ev);
}
}
@@ -2759,6 +2805,9 @@ void DisplayServerX11::process_events() {
MutexLock mutex_lock(events_mutex);
events = polled_events;
polled_events.clear();
+
+ // Check for more pending events to avoid an extra frame delay.
+ _check_pending_events(events);
}
for (uint32_t event_index = 0; event_index < events.size(); ++event_index) {
diff --git a/platform/linuxbsd/display_server_x11.h b/platform/linuxbsd/display_server_x11.h
index 1887c7105b..eb7725b768 100644
--- a/platform/linuxbsd/display_server_x11.h
+++ b/platform/linuxbsd/display_server_x11.h
@@ -155,6 +155,7 @@ class DisplayServerX11 : public DisplayServer {
WindowID _create_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect);
String internal_clipboard;
+ String internal_clipboard_primary;
Window xdnd_source_window;
::Display *x11_display;
char *xmbstring;
@@ -205,7 +206,7 @@ class DisplayServerX11 : public DisplayServer {
void _handle_key_event(WindowID p_window, XKeyEvent *p_event, LocalVector<XEvent> &p_events, uint32_t &p_event_index, bool p_echo = false);
- Atom _process_selection_request_target(Atom p_target, Window p_requestor, Atom p_property) const;
+ Atom _process_selection_request_target(Atom p_target, Window p_requestor, Atom p_property, Atom p_selection) const;
void _handle_selection_request_event(XSelectionRequestEvent *p_event) const;
String _clipboard_get_impl(Atom p_source, Window x11_window, Atom target) const;
@@ -267,6 +268,7 @@ class DisplayServerX11 : public DisplayServer {
static void _poll_events_thread(void *ud);
bool _wait_for_events() const;
void _poll_events();
+ void _check_pending_events(LocalVector<XEvent> &r_events);
static Bool _predicate_all_events(Display *display, XEvent *event, XPointer arg);
static Bool _predicate_clipboard_selection(Display *display, XEvent *event, XPointer arg);
@@ -290,6 +292,8 @@ public:
virtual void clipboard_set(const String &p_text) override;
virtual String clipboard_get() const override;
+ virtual void clipboard_set_primary(const String &p_text) override;
+ virtual String clipboard_get_primary() const override;
virtual int get_screen_count() const override;
virtual Point2i screen_get_position(int p_screen = SCREEN_OF_MAIN_WINDOW) const override;
diff --git a/platform/linuxbsd/freedesktop_screensaver.cpp b/platform/linuxbsd/freedesktop_screensaver.cpp
index a6a3b27d76..3973d43d49 100644
--- a/platform/linuxbsd/freedesktop_screensaver.cpp
+++ b/platform/linuxbsd/freedesktop_screensaver.cpp
@@ -50,6 +50,7 @@ void FreeDesktopScreenSaver::inhibit() {
DBusConnection *bus = dbus_bus_get(DBUS_BUS_SESSION, &error);
if (dbus_error_is_set(&error)) {
+ dbus_error_free(&error);
unsupported = true;
return;
}
@@ -72,6 +73,7 @@ void FreeDesktopScreenSaver::inhibit() {
DBusMessage *reply = dbus_connection_send_with_reply_and_block(bus, message, 50, &error);
dbus_message_unref(message);
if (dbus_error_is_set(&error)) {
+ dbus_error_free(&error);
dbus_connection_unref(bus);
unsupported = false;
return;
@@ -96,6 +98,7 @@ void FreeDesktopScreenSaver::uninhibit() {
DBusConnection *bus = dbus_bus_get(DBUS_BUS_SESSION, &error);
if (dbus_error_is_set(&error)) {
+ dbus_error_free(&error);
unsupported = true;
return;
}
@@ -110,6 +113,7 @@ void FreeDesktopScreenSaver::uninhibit() {
DBusMessage *reply = dbus_connection_send_with_reply_and_block(bus, message, 50, &error);
if (dbus_error_is_set(&error)) {
+ dbus_error_free(&error);
dbus_connection_unref(bus);
unsupported = true;
return;
diff --git a/platform/linuxbsd/os_linuxbsd.cpp b/platform/linuxbsd/os_linuxbsd.cpp
index 2c9801f512..69474c6dec 100644
--- a/platform/linuxbsd/os_linuxbsd.cpp
+++ b/platform/linuxbsd/os_linuxbsd.cpp
@@ -463,7 +463,10 @@ Error OS_LinuxBSD::move_to_trash(const String &p_path) {
// The trash can is successfully created, now we check that we don't exceed our file name length limit.
// If the file name is too long trim it so we can add the identifying number and ".trashinfo".
// Assumes that the file name length limit is 255 characters.
- String file_name = basename(p_path.utf8().get_data());
+ String file_name = p_path.get_file();
+ if (file_name.length() == 0) {
+ file_name = p_path.get_base_dir().get_file();
+ }
if (file_name.length() > 240) {
file_name = file_name.substr(0, file_name.length() - 15);
}