From 5d9ff0f5446574de420ebf516a79da509867cbc1 Mon Sep 17 00:00:00 2001 From: Koichiro IWAO Date: Thu, 12 Jul 2018 18:04:32 +0900 Subject: [PATCH 01/15] docs: fix xrdp's LogFile path in man --- docs/man/xrdp.ini.5.in | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/man/xrdp.ini.5.in b/docs/man/xrdp.ini.5.in index 743a5072..b43c6aa1 100644 --- a/docs/man/xrdp.ini.5.in +++ b/docs/man/xrdp.ini.5.in @@ -206,7 +206,7 @@ The highest value is 255 (hex FF). The following parameters can be used in the \fB[Logging]\fR section: .TP -\fBLogFile\fR=\fI@localstatedir@/log/sesman.log\fR +\fBLogFile\fR=\fI@localstatedir@/log/xrdp.log\fR This options contains the path to logfile. It can be either absolute or relative.\fR .TP From c467ba6b0437efa44325c73ec974e848b0be96a8 Mon Sep 17 00:00:00 2001 From: matt335672 <30179339+matt335672@users.noreply.github.com> Date: Thu, 19 Jul 2018 08:04:28 +0100 Subject: [PATCH 02/15] Add handler for fatal X server conditions Unless X server failures are caught, these can cause a premature exit of chansrv, giving it no chance to clean up. This is currently a particular problem for fuser mounts. --- sesman/chansrv/chansrv.c | 13 +++++++++++++ sesman/chansrv/xcommon.c | 25 ++++++++++++++++++++----- sesman/chansrv/xcommon.h | 4 ++++ 3 files changed, 37 insertions(+), 5 deletions(-) diff --git a/sesman/chansrv/chansrv.c b/sesman/chansrv/chansrv.c index 34aa3f51..6ec05e53 100644 --- a/sesman/chansrv/chansrv.c +++ b/sesman/chansrv/chansrv.c @@ -1278,6 +1278,16 @@ segfault_signal_handler(int sig) exit(0); } +/*****************************************************************************/ +static void +x_server_fatal_handler(void) +{ + LOGM((LOG_LEVEL_INFO, "xserver_fatal_handler: entered.......")); + /* At this point the X server has gone away. Dont make any X calls. */ + xfuse_deinit(); + exit(0); +} + /*****************************************************************************/ static int get_display_num_from_display(char *display_text) @@ -1576,6 +1586,9 @@ main(int argc, char **argv) g_signal_child_stop(child_signal_handler); /* SIGCHLD */ g_signal_segfault(segfault_signal_handler); + /* Cater for the X server exiting unexpectedly */ + xcommon_set_x_server_fatal_handler(x_server_fatal_handler); + LOGM((LOG_LEVEL_INFO, "main: DISPLAY env var set to %s", display_text)); if (g_display_num == 0) diff --git a/sesman/chansrv/xcommon.c b/sesman/chansrv/xcommon.c index 8abc27f7..a995b3fc 100644 --- a/sesman/chansrv/xcommon.c +++ b/sesman/chansrv/xcommon.c @@ -28,6 +28,7 @@ #include "log.h" #include "clipboard.h" #include "rail.h" +#include "xcommon.h" /* #undef LOG_LEVEL @@ -50,6 +51,9 @@ Atom g_utf8_string = 0; Atom g_net_wm_name = 0; Atom g_wm_state = 0; +static x_server_fatal_cb_type x_server_fatal_handler = 0; + + /*****************************************************************************/ static int xcommon_error_handler(Display *dis, XErrorEvent *xer) @@ -64,16 +68,27 @@ xcommon_error_handler(Display *dis, XErrorEvent *xer) } /*****************************************************************************/ -/* The X server had an internal error. This is the last function called. - Do any cleanup that needs to be done on exit, like removing temporary files. +/* Allow the caller to be notified on X server failure + Specified callback can do any cleanup that needs to be done on exit, + like removing temporary files. This is the last function called. Don't worry about memory leaks */ -#if 0 +void +xcommon_set_x_server_fatal_handler(x_server_fatal_cb_type handler) +{ + x_server_fatal_handler = handler; +} + +/*****************************************************************************/ +/* The X server had an internal error */ static int xcommon_fatal_handler(Display *dis) { + if (x_server_fatal_handler) + { + x_server_fatal_handler(); + } return 0; } -#endif /*****************************************************************************/ /* returns time in milliseconds @@ -110,7 +125,7 @@ xcommon_init(void) /* setting the error handlers can cause problem when shutting down chansrv on some xlibs */ XSetErrorHandler(xcommon_error_handler); - //XSetIOErrorHandler(xcommon_fatal_handler); + XSetIOErrorHandler(xcommon_fatal_handler); g_x_socket = XConnectionNumber(g_display); diff --git a/sesman/chansrv/xcommon.h b/sesman/chansrv/xcommon.h index ea74b89f..540abe74 100644 --- a/sesman/chansrv/xcommon.h +++ b/sesman/chansrv/xcommon.h @@ -26,6 +26,8 @@ #define FORMAT_TO_BYTES(_format) \ (_format) == 32 ? sizeof(long) : (_format) / 8 +typedef void (*x_server_fatal_cb_type)(void); + int xcommon_get_local_time(void); int @@ -34,5 +36,7 @@ int xcommon_get_wait_objs(tbus* objs, int* count, int* timeout); int xcommon_check_wait_objs(void); +void +xcommon_set_x_server_fatal_handler(x_server_fatal_cb_type handler); #endif From 8427c3601bcf5bebedef149eae7cb8d6854bcfbb Mon Sep 17 00:00:00 2001 From: Brandon Wooldridge Date: Thu, 2 Aug 2018 15:24:46 -0700 Subject: [PATCH 03/15] Corrected spacing between arguments to `cc` for Pulseaudio chanserv Makefile --- sesman/chansrv/pulse/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sesman/chansrv/pulse/Makefile b/sesman/chansrv/pulse/Makefile index 74977221..de53ff69 100644 --- a/sesman/chansrv/pulse/Makefile +++ b/sesman/chansrv/pulse/Makefile @@ -4,7 +4,7 @@ # change this to your pulseaudio source directory PULSE_DIR = /tmp/pulseaudio-10.0 -CFLAGS = -Wall -O2 -I$(PULSE_DIR) -I$(PULSE_DIR)/src -DHAVE_CONFIG_H -fPIC +CFLAGS = -Wall -O2 -I $(PULSE_DIR) -I $(PULSE_DIR)/src -DHAVE_CONFIG_H -fPIC all: module-xrdp-sink.so module-xrdp-source.so From 5d2c5b1410e6c6c55500b583b9d80238bf3eee01 Mon Sep 17 00:00:00 2001 From: Idan Freiberg Date: Fri, 3 Aug 2018 05:12:05 +0300 Subject: [PATCH 04/15] chansrv: remove pulseaudio modules from xrdp source tree its actually an independent code which is not part of xrdp moved to its own repoistory: https://github.com/neutrinolabs/pulseaudio-modules Signed-off-by: Idan Freiberg --- sesman/chansrv/Makefile.am | 1 - sesman/chansrv/pulse/.gitignore | 1 - sesman/chansrv/pulse/Makefile | 18 - sesman/chansrv/pulse/README.md | 117 ---- .../chansrv/pulse/module-xrdp-sink-symdef.h | 29 - sesman/chansrv/pulse/module-xrdp-sink.c | 613 ------------------ .../chansrv/pulse/module-xrdp-source-symdef.h | 29 - sesman/chansrv/pulse/module-xrdp-source.c | 547 ---------------- 8 files changed, 1355 deletions(-) delete mode 100644 sesman/chansrv/pulse/.gitignore delete mode 100644 sesman/chansrv/pulse/Makefile delete mode 100644 sesman/chansrv/pulse/README.md delete mode 100644 sesman/chansrv/pulse/module-xrdp-sink-symdef.h delete mode 100644 sesman/chansrv/pulse/module-xrdp-sink.c delete mode 100644 sesman/chansrv/pulse/module-xrdp-source-symdef.h delete mode 100644 sesman/chansrv/pulse/module-xrdp-source.c diff --git a/sesman/chansrv/Makefile.am b/sesman/chansrv/Makefile.am index b46fa63d..35273283 100644 --- a/sesman/chansrv/Makefile.am +++ b/sesman/chansrv/Makefile.am @@ -1,7 +1,6 @@ EXTRA_DIST = \ clipboard-notes.txt \ pcsc \ - pulse \ wave-format-server.txt AM_CPPFLAGS = \ diff --git a/sesman/chansrv/pulse/.gitignore b/sesman/chansrv/pulse/.gitignore deleted file mode 100644 index 24600083..00000000 --- a/sesman/chansrv/pulse/.gitignore +++ /dev/null @@ -1 +0,0 @@ -!Makefile diff --git a/sesman/chansrv/pulse/Makefile b/sesman/chansrv/pulse/Makefile deleted file mode 100644 index de53ff69..00000000 --- a/sesman/chansrv/pulse/Makefile +++ /dev/null @@ -1,18 +0,0 @@ -# -# build xrdp pulseaudio modules -# - -# change this to your pulseaudio source directory -PULSE_DIR = /tmp/pulseaudio-10.0 -CFLAGS = -Wall -O2 -I $(PULSE_DIR) -I $(PULSE_DIR)/src -DHAVE_CONFIG_H -fPIC - -all: module-xrdp-sink.so module-xrdp-source.so - -module-xrdp-sink.so: module-xrdp-sink.o - $(CC) $(LDFLAGS) -shared -o module-xrdp-sink.so module-xrdp-sink.o - -module-xrdp-source.so: module-xrdp-source.o - $(CC) $(LDFLAGS) -shared -o module-xrdp-source.so module-xrdp-source.o - -clean: - rm -f module-xrdp-sink.o module-xrdp-sink.so module-xrdp-source.o module-xrdp-source.so diff --git a/sesman/chansrv/pulse/README.md b/sesman/chansrv/pulse/README.md deleted file mode 100644 index dbc89242..00000000 --- a/sesman/chansrv/pulse/README.md +++ /dev/null @@ -1,117 +0,0 @@ -The latest version of this document can be found at wiki. - -* https://github.com/neutrinolabs/xrdp/wiki/How-to-set-up-audio-redirection - - -# Overview -xrdp supports audio redirection using PulseAudio, which is a sound system for -POSIX operating systems. Server to client redirection is compliant to Remote -Desktop Procol standard [[MS-RDPEA]](https://msdn.microsoft.com/en-us/library/cc240933.aspx) -but client to server redirection implementation is proprietary. Accordingly, -server to client redirection is available with many of RDP clients including -Microsoft client but client to server redirection requires NeutrinoRDP client, -not available with other clients. - -Here is how to build pulseaudio modules for your distro, so you can have audio -support through xrdp. - -# Prerequisites -Prepare xrdp source in your home directory. Of course, you can choose another -directory. - - cd ~ - git clone https://github.com/neutrinolabs/xrdp.git - -In this instruction, pulseaudio version is **10.0**. Replace the version number -in this instruction if your environment has different versions. You can find -out your pulseaudio version executing the following command: - - pulseaudio --version - -# How to build - -## Debian 9 / Ubuntu - -This instruction also should be applicable to Ubuntu family. - -### Prerequisites - -Some build tools and package development tools are required. Make sure install -the tools. - - apt install build-essential dpkg-dev - -### Prepare & build - -Install pulseaudio and requisite packages to build pulseaudio. - - apt install pulseaudio - apt build-dep pulseaudio - -Fetch the pulseaudio source . You'll see `pulseaudio-10.0` directory in your -current directory. - - apt source pulseaudio - -Enter into the directory and build the pulseaudio package. - - cd pulseaudio-10.0 - ./configure - -Finally, let's make. You'll have two .so files `module-xrdp-sink.so` and -`module-xrdp-source.so`. - - cd ~/xrdp/sesman/chansrv/pulse - make PULSE_DIR="~/pulseaudio-10.0" - -## Other distro - -First off, find out your pulseaudio version using `pulseaudio --version` -command. Download the tarball of the pulseaudio version that you have. - -* https://freedesktop.org/software/pulseaudio/releases/ - -After downloading the tarball, extact the tarball and `cd` into the source -directory, then run `./configure`. - - wget https://freedesktop.org/software/pulseaudio/releases/pulseaudio-10.0.tar.xz - tar xf pulseaudio-10.0.tar.gz - cd pulseaudio-10.0 - ./configure - -If additional packages are required to run `./configure`, install requisite -packages depending on your environment. - -Finally, let's make. You'll have two .so files `module-xrdp-sink.so` and -`module-xrdp-source.so`. - - cd ~/xrdp/sesman/chansrv/pulse - make PULSE_DIR="~/pulseaudio-10.0" - -# Install - -Install process is not distro specific except for install destination. Install -built two .so files into the pulseaudio modules directory. Typically, -`/usr/lib/pulse-10.0/modules` for Debian, `/usr/lib64/pulse-10.0/modules` for -CentOS 7. Other distro might have different path. Find out the right path for -your distro. - -Look into the directory with `ls` command. You'll see lots of `module-*.so` -files. There's the place! - - cd ~/xrdp/sesman/chansrv/pulse - for f in *.so; do install -s -m 644 $f /usr/lib/pulse-10.0/modules; done - -This command is equivalent to following: - - install -s -m 644 module-xrdp-sink.so /usr/lib/pulse-10.0/modules - install -s -m 644 module-xrdp-source.so /usr/lib/pulse-10.0/modules - -Well done! Pulseaudio modules should be properly built and installed. - - -# See if it works - -To see if it works, run `pavumeter` in the xrdp session. Playback any YouTube -video in Firefox. You'll see "Showing signal levels of **xrdp sink**" and -volume meter moving. diff --git a/sesman/chansrv/pulse/module-xrdp-sink-symdef.h b/sesman/chansrv/pulse/module-xrdp-sink-symdef.h deleted file mode 100644 index 7001ba51..00000000 --- a/sesman/chansrv/pulse/module-xrdp-sink-symdef.h +++ /dev/null @@ -1,29 +0,0 @@ -#ifndef MODULE_XRDP_SINK_SYMDEF_H -#define MODULE_XRDP_SINK_SYMDEF_H - -#include -#include -#include - -#define pa__init module_xrdp_sink_LTX_pa__init -#define pa__done module_xrdp_sink_LTX_pa__done -#define pa__get_author module_xrdp_sink_LTX_pa__get_author -#define pa__get_description module_xrdp_sink_LTX_pa__get_description -#define pa__get_usage module_xrdp_sink_LTX_pa__get_usage -#define pa__get_version module_xrdp_sink_LTX_pa__get_version -#define pa__get_deprecated module_xrdp_sink_LTX_pa__get_deprecated -#define pa__load_once module_xrdp_sink_LTX_pa__load_once -#define pa__get_n_used module_xrdp_sink_LTX_pa__get_n_used - -int pa__init(pa_module*m); -void pa__done(pa_module*m); -int pa__get_n_used(pa_module*m); - -const char* pa__get_author(void); -const char* pa__get_description(void); -const char* pa__get_usage(void); -const char* pa__get_version(void); -const char* pa__get_deprecated(void); -pa_bool_t pa__load_once(void); - -#endif diff --git a/sesman/chansrv/pulse/module-xrdp-sink.c b/sesman/chansrv/pulse/module-xrdp-sink.c deleted file mode 100644 index 768b0795..00000000 --- a/sesman/chansrv/pulse/module-xrdp-sink.c +++ /dev/null @@ -1,613 +0,0 @@ -/** - * xrdp: A Remote Desktop Protocol server. - * pulse sink - * - * Copyright (C) Jay Sorg 2013 - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -/* - * see pulse-notes.txt -*/ - -#ifdef HAVE_CONFIG_H -#include -#endif - -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include - -#include -#include -#include -#include -#include -#include -#include -#include -#include - -/* defined in pulse/version.h */ -#if PA_PROTOCOL_VERSION > 28 -/* these used to be defined in pulsecore/macro.h */ -typedef bool pa_bool_t; -#define FALSE ((pa_bool_t) 0) -#define TRUE (!FALSE) -#else -#endif - -#include "module-xrdp-sink-symdef.h" -#include "../../../common/xrdp_sockets.h" - -PA_MODULE_AUTHOR("Jay Sorg"); -PA_MODULE_DESCRIPTION("xrdp sink"); -PA_MODULE_VERSION(PACKAGE_VERSION); -PA_MODULE_LOAD_ONCE(FALSE); -PA_MODULE_USAGE( - "sink_name= " - "sink_properties= " - "format= " - "rate= " - "channels= " - "channel_map="); - -#define DEFAULT_SINK_NAME "xrdp-sink" -#define BLOCK_USEC 30000 -//#define BLOCK_USEC (PA_USEC_PER_SEC * 2) - -struct userdata { - pa_core *core; - pa_module *module; - pa_sink *sink; - - pa_thread *thread; - pa_thread_mq thread_mq; - pa_rtpoll *rtpoll; - - pa_usec_t block_usec; - pa_usec_t timestamp; - pa_usec_t failed_connect_time; - pa_usec_t last_send_time; - - int fd; /* unix domain socket connection to xrdp chansrv */ - int display_num; - int skip_bytes; - int got_max_latency; - -}; - -static const char* const valid_modargs[] = { - "sink_name", - "sink_properties", - "format", - "rate", - "channels", - "channel_map", - NULL -}; - -static int close_send(struct userdata *u); - -static int sink_process_msg(pa_msgobject *o, int code, void *data, - int64_t offset, pa_memchunk *chunk) { - - struct userdata *u = PA_SINK(o)->userdata; - pa_usec_t now; - long lat; - - pa_log_debug("sink_process_msg: code %d", code); - - switch (code) { - - case PA_SINK_MESSAGE_SET_VOLUME: /* 3 */ - break; - - case PA_SINK_MESSAGE_SET_MUTE: /* 6 */ - break; - - case PA_SINK_MESSAGE_GET_LATENCY: /* 7 */ - now = pa_rtclock_now(); - lat = u->timestamp > now ? u->timestamp - now : 0ULL; - pa_log_debug("sink_process_msg: lat %ld", lat); - *((pa_usec_t*) data) = lat; - return 0; - - case PA_SINK_MESSAGE_GET_REQUESTED_LATENCY: /* 8 */ - break; - - case PA_SINK_MESSAGE_SET_STATE: /* 9 */ - if (PA_PTR_TO_UINT(data) == PA_SINK_RUNNING) /* 0 */ { - pa_log("sink_process_msg: running"); - - u->timestamp = pa_rtclock_now(); - } else { - pa_log("sink_process_msg: not running"); - close_send(u); - } - break; - - } - - return pa_sink_process_msg(o, code, data, offset, chunk); -} - -static void sink_update_requested_latency_cb(pa_sink *s) { - struct userdata *u; - size_t nbytes; - - pa_sink_assert_ref(s); - pa_assert_se(u = s->userdata); - - u->block_usec = BLOCK_USEC; - //u->block_usec = pa_sink_get_requested_latency_within_thread(s); - pa_log("1 block_usec %llu", (unsigned long long) u->block_usec); - - u->got_max_latency = 0; - if (u->block_usec == (pa_usec_t) -1) { - u->block_usec = s->thread_info.max_latency; - pa_log_debug("2 block_usec %llu", (unsigned long long) u->block_usec); - u->got_max_latency = 1; - } - - nbytes = pa_usec_to_bytes(u->block_usec, &s->sample_spec); - pa_sink_set_max_rewind_within_thread(s, nbytes); - pa_sink_set_max_request_within_thread(s, nbytes); -} - -static void process_rewind(struct userdata *u, pa_usec_t now) { - size_t rewind_nbytes, in_buffer; - pa_usec_t delay; - - pa_assert(u); - - /* Figure out how much we shall rewind and reset the counter */ - rewind_nbytes = u->sink->thread_info.rewind_nbytes; - u->sink->thread_info.rewind_nbytes = 0; - - pa_assert(rewind_nbytes > 0); - pa_log_debug("Requested to rewind %lu bytes.", - (unsigned long) rewind_nbytes); - - if (u->timestamp <= now) - goto do_nothing; - - delay = u->timestamp - now; - in_buffer = pa_usec_to_bytes(delay, &u->sink->sample_spec); - - if (in_buffer <= 0) - goto do_nothing; - - if (rewind_nbytes > in_buffer) - rewind_nbytes = in_buffer; - - pa_sink_process_rewind(u->sink, rewind_nbytes); - u->timestamp -= pa_bytes_to_usec(rewind_nbytes, &u->sink->sample_spec); - u->skip_bytes += rewind_nbytes; - - pa_log_debug("Rewound %lu bytes.", (unsigned long) rewind_nbytes); - return; - -do_nothing: - - pa_sink_process_rewind(u->sink, 0); -} - -struct header { - int code; - int bytes; -}; - -static int get_display_num_from_display(char *display_text) { - int index; - int mode; - int host_index; - int disp_index; - int scre_index; - int display_num; - char host[256]; - char disp[256]; - char scre[256]; - - if (display_text == NULL) { - return 0; - } - memset(host, 0, 256); - memset(disp, 0, 256); - memset(scre, 0, 256); - - index = 0; - host_index = 0; - disp_index = 0; - scre_index = 0; - mode = 0; - - while (display_text[index] != 0) { - if (display_text[index] == ':') { - mode = 1; - } else if (display_text[index] == '.') { - mode = 2; - } else if (mode == 0) { - host[host_index] = display_text[index]; - host_index++; - } else if (mode == 1) { - disp[disp_index] = display_text[index]; - disp_index++; - } else if (mode == 2) { - scre[scre_index] = display_text[index]; - scre_index++; - } - index++; - } - - host[host_index] = 0; - disp[disp_index] = 0; - scre[scre_index] = 0; - display_num = atoi(disp); - return display_num; -} - -static int lsend(int fd, char *data, int bytes) { - int sent = 0; - int error; - while (sent < bytes) { - error = send(fd, data + sent, bytes - sent, 0); - if (error < 1) { - return error; - } - sent += error; - } - return sent; -} - -static int data_send(struct userdata *u, pa_memchunk *chunk) { - char *data; - char *socket_dir; - int bytes; - int sent; - int fd; - struct header h; - struct sockaddr_un s; - - if (u->fd == 0) { - if (u->failed_connect_time != 0) { - if (pa_rtclock_now() - u->failed_connect_time < 1000000) { - return 0; - } - } - fd = socket(PF_LOCAL, SOCK_STREAM, 0); - memset(&s, 0, sizeof(s)); - s.sun_family = AF_UNIX; - bytes = sizeof(s.sun_path) - 1; - socket_dir = getenv("XRDP_SOCKET_PATH"); - if (socket_dir == NULL || socket_dir[0] == '\0') - { - socket_dir = "/tmp/.xrdp"; - } - snprintf(s.sun_path, bytes, "%s/" CHANSRV_PORT_OUT_BASE_STR, - socket_dir, u->display_num); - pa_log_debug("trying to connect to %s", s.sun_path); - if (connect(fd, (struct sockaddr *)&s, - sizeof(struct sockaddr_un)) != 0) { - u->failed_connect_time = pa_rtclock_now(); - pa_log_debug("Connected failed"); - close(fd); - return 0; - } - u->failed_connect_time = 0; - pa_log("Connected ok fd %d", fd); - u->fd = fd; - } - - bytes = chunk->length; - pa_log_debug("bytes %d", bytes); - - /* from rewind */ - if (u->skip_bytes > 0) { - if (bytes > u->skip_bytes) { - bytes -= u->skip_bytes; - u->skip_bytes = 0; - } else { - u->skip_bytes -= bytes; - return bytes; - } - } - - h.code = 0; - h.bytes = bytes + 8; - if (lsend(u->fd, (char*)(&h), 8) != 8) { - pa_log("data_send: send failed"); - close(u->fd); - u->fd = 0; - return 0; - } else { - pa_log_debug("data_send: sent header ok bytes %d", bytes); - } - - data = (char*)pa_memblock_acquire(chunk->memblock); - data += chunk->index; - sent = lsend(u->fd, data, bytes); - pa_memblock_release(chunk->memblock); - - if (sent != bytes) { - pa_log("data_send: send failed sent %d bytes %d", sent, bytes); - close(u->fd); - u->fd = 0; - return 0; - } - - return sent; -} - -static int close_send(struct userdata *u) { - struct header h; - - pa_log("close_send:"); - if (u->fd == 0) { - return 0; - } - h.code = 1; - h.bytes = 8; - if (lsend(u->fd, (char*)(&h), 8) != 8) { - pa_log("close_send: send failed"); - close(u->fd); - u->fd = 0; - return 0; - } else { - pa_log_debug("close_send: sent header ok"); - } - return 8; -} - -static void process_render(struct userdata *u, pa_usec_t now) { - pa_memchunk chunk; - int request_bytes; - - pa_assert(u); - if (u->got_max_latency) { - return; - } - pa_log_debug("process_render: u->block_usec %llu", (unsigned long long) u->block_usec); - while (u->timestamp < now + u->block_usec) { - request_bytes = u->sink->thread_info.max_request; - request_bytes = MIN(request_bytes, 16 * 1024); - pa_sink_render(u->sink, request_bytes, &chunk); - data_send(u, &chunk); - pa_memblock_unref(chunk.memblock); - u->timestamp += pa_bytes_to_usec(chunk.length, &u->sink->sample_spec); - } -} - -static void thread_func(void *userdata) { - - struct userdata *u = userdata; - int ret; - pa_usec_t now; - - pa_assert(u); - - pa_log_debug("Thread starting up"); - - pa_thread_mq_install(&u->thread_mq); - - u->timestamp = pa_rtclock_now(); - - for (;;) { - - if (u->sink->thread_info.state == PA_SINK_RUNNING) { - - now = pa_rtclock_now(); - - if (u->sink->thread_info.rewind_requested) { - if (u->sink->thread_info.rewind_nbytes > 0) { - process_rewind(u, now); - } else { - pa_sink_process_rewind(u->sink, 0); - } - } - - if (u->timestamp <= now) { - pa_log_debug("thread_func: calling process_render"); - process_render(u, now); - } - - pa_rtpoll_set_timer_absolute(u->rtpoll, u->timestamp); - - } else { - pa_rtpoll_set_timer_disabled(u->rtpoll); - } - -#if defined(PA_CHECK_VERSION) && PA_CHECK_VERSION(6, 0, 0) - if ((ret = pa_rtpoll_run(u->rtpoll)) < 0) { -#else - if ((ret = pa_rtpoll_run(u->rtpoll, TRUE)) < 0) { -#endif - goto fail; - } - - if (ret == 0) { - goto finish; - } - } - -fail: - /* If this was no regular exit from the loop we have to continue - * processing messages until we received PA_MESSAGE_SHUTDOWN */ - pa_asyncmsgq_post(u->thread_mq.outq, PA_MSGOBJECT(u->core), - PA_CORE_MESSAGE_UNLOAD_MODULE, u->module, 0, - NULL, NULL); - pa_asyncmsgq_wait_for(u->thread_mq.inq, PA_MESSAGE_SHUTDOWN); - -finish: - pa_log_debug("Thread shutting down"); -} - -int pa__init(pa_module*m) { - struct userdata *u = NULL; - pa_sample_spec ss; - pa_channel_map map; - pa_modargs *ma = NULL; - pa_sink_new_data data; - size_t nbytes; - - pa_assert(m); - - if (!(ma = pa_modargs_new(m->argument, valid_modargs))) { - pa_log("Failed to parse module arguments."); - goto fail; - } - - ss = m->core->default_sample_spec; - map = m->core->default_channel_map; - if (pa_modargs_get_sample_spec_and_channel_map(ma, &ss, &map, - PA_CHANNEL_MAP_DEFAULT) < 0) { - pa_log("Invalid sample format specification or channel map"); - goto fail; - } - - m->userdata = u = pa_xnew0(struct userdata, 1); - u->core = m->core; - u->module = m; - u->rtpoll = pa_rtpoll_new(); - pa_thread_mq_init(&u->thread_mq, m->core->mainloop, u->rtpoll); - - pa_sink_new_data_init(&data); - data.driver = __FILE__; - data.module = m; - pa_sink_new_data_set_name(&data, - pa_modargs_get_value(ma, "sink_name", DEFAULT_SINK_NAME)); - pa_sink_new_data_set_sample_spec(&data, &ss); - pa_sink_new_data_set_channel_map(&data, &map); - pa_proplist_sets(data.proplist, PA_PROP_DEVICE_DESCRIPTION, "xrdp sink"); - pa_proplist_sets(data.proplist, PA_PROP_DEVICE_CLASS, "abstract"); - - if (pa_modargs_get_proplist(ma, "sink_properties", data.proplist, - PA_UPDATE_REPLACE) < 0) { - pa_log("Invalid properties"); - pa_sink_new_data_done(&data); - goto fail; - } - - u->sink = pa_sink_new(m->core, &data, - PA_SINK_LATENCY | PA_SINK_DYNAMIC_LATENCY); - pa_sink_new_data_done(&data); - - if (!u->sink) { - pa_log("Failed to create sink object."); - goto fail; - } - - u->sink->parent.process_msg = sink_process_msg; - u->sink->update_requested_latency = sink_update_requested_latency_cb; - u->sink->userdata = u; - - pa_sink_set_asyncmsgq(u->sink, u->thread_mq.inq); - pa_sink_set_rtpoll(u->sink, u->rtpoll); - - u->block_usec = BLOCK_USEC; - pa_log_debug("3 block_usec %llu", (unsigned long long) u->block_usec); - nbytes = pa_usec_to_bytes(u->block_usec, &u->sink->sample_spec); - pa_sink_set_max_rewind(u->sink, nbytes); - pa_sink_set_max_request(u->sink, nbytes); - - u->display_num = get_display_num_from_display(getenv("DISPLAY")); - -#if defined(PA_CHECK_VERSION) -#if PA_CHECK_VERSION(0, 9, 22) - if (!(u->thread = pa_thread_new("xrdp-sink", thread_func, u))) { -#else - if (!(u->thread = pa_thread_new(thread_func, u))) { -#endif -#else - if (!(u->thread = pa_thread_new(thread_func, u))) { -#endif - pa_log("Failed to create thread."); - goto fail; - } - - pa_sink_put(u->sink); - - pa_modargs_free(ma); - - return 0; - -fail: - if (ma) { - pa_modargs_free(ma); - } - - pa__done(m); - - return -1; -} - -int pa__get_n_used(pa_module *m) { - struct userdata *u; - - pa_assert(m); - pa_assert_se(u = m->userdata); - - return pa_sink_linked_by(u->sink); -} - -void pa__done(pa_module*m) { - struct userdata *u; - - pa_assert(m); - - if (!(u = m->userdata)) { - return; - } - - if (u->sink) { - pa_sink_unlink(u->sink); - } - - if (u->thread) { - pa_asyncmsgq_send(u->thread_mq.inq, NULL, PA_MESSAGE_SHUTDOWN, - NULL, 0, NULL); - pa_thread_free(u->thread); - } - - pa_thread_mq_done(&u->thread_mq); - - if (u->sink) { - pa_sink_unref(u->sink); - } - - if (u->rtpoll) { - pa_rtpoll_free(u->rtpoll); - } - - pa_xfree(u); -} diff --git a/sesman/chansrv/pulse/module-xrdp-source-symdef.h b/sesman/chansrv/pulse/module-xrdp-source-symdef.h deleted file mode 100644 index 41e364ce..00000000 --- a/sesman/chansrv/pulse/module-xrdp-source-symdef.h +++ /dev/null @@ -1,29 +0,0 @@ -#ifndef MODULE_XRDP_SOURCE_SYMDEF_H -#define MODULE_XRDP_SOURCE_SYMDEF_H - -#include -#include -#include - -#define pa__init module_xrdp_source_LTX_pa__init -#define pa__done module_xrdp_source_LTX_pa__done -#define pa__get_author module_xrdp_source_LTX_pa__get_author -#define pa__get_description module_xrdp_source_LTX_pa__get_description -#define pa__get_usage module_xrdp_source_LTX_pa__get_usage -#define pa__get_version module_xrdp_source_LTX_pa__get_version -#define pa__get_deprecated module_xrdp_source_LTX_pa__get_deprecated -#define pa__load_once module_xrdp_source_LTX_pa__load_once -#define pa__get_n_used module_xrdp_source_LTX_pa__get_n_used - -int pa__init(pa_module*m); -void pa__done(pa_module*m); -int pa__get_n_used(pa_module*m); - -const char* pa__get_author(void); -const char* pa__get_description(void); -const char* pa__get_usage(void); -const char* pa__get_version(void); -const char* pa__get_deprecated(void); -pa_bool_t pa__load_once(void); - -#endif diff --git a/sesman/chansrv/pulse/module-xrdp-source.c b/sesman/chansrv/pulse/module-xrdp-source.c deleted file mode 100644 index a7dd19c9..00000000 --- a/sesman/chansrv/pulse/module-xrdp-source.c +++ /dev/null @@ -1,547 +0,0 @@ -/*** - This file is part of PulseAudio. - - Copyright 2004-2008 Lennart Poettering - Copyright (C) 2008 Nokia Corporation and/or its subsidiary(-ies). - - PulseAudio is free software; you can redistribute it and/or modify - it under the terms of the GNU Lesser General Public License as published - by the Free Software Foundation; either version 2 of the License, - or (at your option) any later version. - - PulseAudio is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - General Public License for more details. - - You should have received a copy of the GNU Lesser General Public License - along with PulseAudio; if not, write to the Free Software - Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - USA. -***/ - -#ifdef HAVE_CONFIG_H -#include -#endif - -#include -#include -#include -#include -#include -#include - -#include -#include -#include - -#include -#include -#include -#include -#include -#include -#include -#include -#include - -/* defined in pulse/version.h */ -#if PA_PROTOCOL_VERSION > 28 -/* these used to be defined in pulsecore/macro.h */ -typedef bool pa_bool_t; -#define FALSE ((pa_bool_t) 0) -#define TRUE (!FALSE) -#else -#endif - -#include "module-xrdp-source-symdef.h" -#include "../../../common/xrdp_sockets.h" - -PA_MODULE_AUTHOR("Laxmikant Rashinkar"); -PA_MODULE_DESCRIPTION("xrdp source"); -PA_MODULE_VERSION(PACKAGE_VERSION); -PA_MODULE_LOAD_ONCE(FALSE); -PA_MODULE_USAGE( - "format= " - "channels= " - "rate= " - "source_name= " - "channel_map= " - "description= " - "latency_time="); - -#define DEFAULT_SOURCE_NAME "xrdp-source" -#define DEFAULT_LATENCY_TIME 10 -#define MAX_LATENCY_USEC 1000 - -struct userdata { - pa_core *core; - pa_module *module; - pa_source *source; - - pa_thread *thread; - pa_thread_mq thread_mq; - pa_rtpoll *rtpoll; - - size_t block_size; - - pa_usec_t block_usec; - pa_usec_t timestamp; - pa_usec_t latency_time; - - /* xrdp stuff */ - int fd; /* UDS connection to xrdp chansrv */ - int display_num; /* X display number */ - int want_src_data; -}; - -static const char* const valid_modargs[] = { - "rate", - "format", - "channels", - "source_name", - "channel_map", - "description", - "latency_time", - NULL -}; - -static int get_display_num_from_display(char *display_text) ; - -static int source_process_msg(pa_msgobject *o, int code, void *data, - int64_t offset, pa_memchunk *chunk) { - - struct userdata *u = PA_SOURCE(o)->userdata; - - switch (code) { - case PA_SOURCE_MESSAGE_SET_STATE: - - if (PA_PTR_TO_UINT(data) == PA_SOURCE_RUNNING) - u->timestamp = pa_rtclock_now(); - - break; - - case PA_SOURCE_MESSAGE_GET_LATENCY: { - pa_usec_t now; - - now = pa_rtclock_now(); - *((pa_usec_t*) data) = u->timestamp > now ? u->timestamp - now : 0; - - return 0; - } - } - - return pa_source_process_msg(o, code, data, offset, chunk); -} - -static void source_update_requested_latency_cb(pa_source *s) { - struct userdata *u; - - pa_source_assert_ref(s); - u = s->userdata; - pa_assert(u); - - u->block_usec = pa_source_get_requested_latency_within_thread(s); -} - -static int lsend(int fd, char *data, int bytes) { - int sent = 0; - int error; - while (sent < bytes) { - error = send(fd, data + sent, bytes - sent, 0); - if (error < 1) { - return error; - } - sent += error; - } - return sent; -} - -static int lrecv(int fd, char *data, int bytes) { - int recved = 0; - int error; - while (recved < bytes) { - error = recv(fd, data + recved, bytes - recved, 0); - if (error < 1) { - return error; - } - recved += error; - } - return recved; -} - -static int data_get(struct userdata *u, pa_memchunk *chunk) { - - int fd; - int bytes; - int read_bytes; - struct sockaddr_un s; - char *data; - char *socket_dir; - char buf[11]; - unsigned char ubuf[10]; - - if (u->fd == 0) { - /* connect to xrdp unix domain socket */ - fd = socket(PF_LOCAL, SOCK_STREAM, 0); - memset(&s, 0, sizeof(s)); - s.sun_family = AF_UNIX; - bytes = sizeof(s.sun_path) - 1; - socket_dir = getenv("XRDP_SOCKET_PATH"); - if (socket_dir == NULL || socket_dir[0] == '\0') - { - socket_dir = "/tmp/.xrdp"; - } - snprintf(s.sun_path, bytes, "%s/" CHANSRV_PORT_IN_BASE_STR, - socket_dir, u->display_num); - pa_log_debug("Trying to connect to %s", s.sun_path); - - if (connect(fd, (struct sockaddr *) &s, sizeof(struct sockaddr_un)) != 0) { - pa_log_debug("Connect failed"); - close(fd); - return -1; - } - - pa_log("Connected ok, fd=%d", fd); - pa_log_debug("###### connected to xrdp audio_in socket"); - u->fd = fd; - } - - data = (char *) pa_memblock_acquire(chunk->memblock); - - if (!u->want_src_data) { - char buf[12]; - - buf[0] = 0; - buf[1] = 0; - buf[2] = 0; - buf[3] = 0; - buf[4] = 11; - buf[5] = 0; - buf[6] = 0; - buf[7] = 0; - buf[8] = 1; - buf[9] = 0; - buf[10] = 0; - - if (lsend(u->fd, buf, 11) != 11) { - close(u->fd); - u->fd = 0; - pa_memblock_release(chunk->memblock); - return -1; - } - u->want_src_data = 1; - pa_log_debug("###### started recording"); - } - - /* ask for more data */ - buf[0] = 0; - buf[1] = 0; - buf[2] = 0; - buf[3] = 0; - buf[4] = 11; - buf[5] = 0; - buf[6] = 0; - buf[7] = 0; - buf[8] = 3; - buf[9] = (unsigned char) chunk->length; - buf[10] = (unsigned char) ((chunk->length >> 8) & 0xff); - - if (lsend(u->fd, buf, 11) != 11) { - close(u->fd); - u->fd = 0; - pa_memblock_release(chunk->memblock); - u->want_src_data = 0; - return -1; - } - - /* read length of data available */ - if (lrecv(u->fd, (char *) ubuf, 2) != 2) { - close(u->fd); - u->fd = 0; - pa_memblock_release(chunk->memblock); - u->want_src_data = 0; - return -1; - } - bytes = ((ubuf[1] << 8) & 0xff00) | (ubuf[0] & 0xff); - - if (bytes == 0) { - pa_memblock_release(chunk->memblock); - return 0; - } - - /* get data */ - read_bytes = lrecv(u->fd, data, bytes); - if (read_bytes != bytes) { - close(u->fd); - u->fd = 0; - pa_memblock_release(chunk->memblock); - u->want_src_data = 0; - return -1; - } - pa_memblock_release(chunk->memblock); - - return read_bytes; -} - -static void thread_func(void *userdata) { - struct userdata *u = userdata; - int bytes; - - pa_assert(u); - pa_thread_mq_install(&u->thread_mq); - u->timestamp = pa_rtclock_now(); - - for (;;) { - int ret; - - /* Generate some null data */ - if (u->source->thread_info.state == PA_SOURCE_RUNNING) { - pa_usec_t now; - pa_memchunk chunk; - - now = pa_rtclock_now(); - - if ((chunk.length = pa_usec_to_bytes(now - u->timestamp, &u->source->sample_spec)) > 0) { - chunk.length *= 4; - chunk.memblock = pa_memblock_new(u->core->mempool, chunk.length); - chunk.index = 0; - bytes = data_get(u, &chunk); - if (bytes > 0) - { - chunk.length = bytes; - pa_source_post(u->source, &chunk); - } - pa_memblock_unref(chunk.memblock); - u->timestamp = now; - } - - pa_rtpoll_set_timer_absolute(u->rtpoll, u->timestamp + u->latency_time * PA_USEC_PER_MSEC); - } else { - if (u->want_src_data) - { - /* we don't want source data anymore */ - char buf[12]; - - buf[0] = 0; - buf[1] = 0; - buf[2] = 0; - buf[3] = 0; - buf[4] = 11; - buf[5] = 0; - buf[6] = 0; - buf[7] = 0; - buf[8] = 2; - buf[9] = 0; - buf[10] = 0; - - if (lsend(u->fd, buf, 11) != 11) { - close(u->fd); - u->fd = 0; - } - u->want_src_data = 0; - pa_log_debug("###### stopped recording"); - } - pa_rtpoll_set_timer_disabled(u->rtpoll); - } - - /* Hmm, nothing to do. Let's sleep */ -#if defined(PA_CHECK_VERSION) && PA_CHECK_VERSION(6, 0, 0) - if ((ret = pa_rtpoll_run(u->rtpoll)) < 0) { -#else - if ((ret = pa_rtpoll_run(u->rtpoll, TRUE)) < 0) { -#endif - goto fail; - } - - if (ret == 0) - goto finish; - } - -fail: - /* If this was no regular exit from the loop we have to continue - * processing messages until we received PA_MESSAGE_SHUTDOWN */ - pa_asyncmsgq_post(u->thread_mq.outq, PA_MSGOBJECT(u->core), PA_CORE_MESSAGE_UNLOAD_MODULE, u->module, 0, NULL, NULL); - pa_asyncmsgq_wait_for(u->thread_mq.inq, PA_MESSAGE_SHUTDOWN); - -finish: - pa_log_debug("###### thread shutting down"); -} - -int pa__init(pa_module *m) { - struct userdata *u = NULL; - pa_sample_spec ss; - pa_channel_map map; - pa_modargs *ma = NULL; - pa_source_new_data data; - uint32_t latency_time = DEFAULT_LATENCY_TIME; - - pa_assert(m); - - if (!(ma = pa_modargs_new(m->argument, valid_modargs))) { - pa_log("Failed to parse module arguments."); - goto fail; - } - -#if 1 - ss = m->core->default_sample_spec; -#else - ss.format = PA_SAMPLE_S16LE; - ss.rate = 22050; - ss.channels = 2; -#endif - - map = m->core->default_channel_map; - if (pa_modargs_get_sample_spec_and_channel_map(ma, &ss, &map, PA_CHANNEL_MAP_DEFAULT) < 0) { - pa_log("Invalid sample format specification or channel map"); - goto fail; - } - - m->userdata = u = pa_xnew0(struct userdata, 1); - u->core = m->core; - u->module = m; - u->rtpoll = pa_rtpoll_new(); - pa_thread_mq_init(&u->thread_mq, m->core->mainloop, u->rtpoll); - - pa_source_new_data_init(&data); - data.driver = __FILE__; - data.module = m; - pa_source_new_data_set_name(&data, pa_modargs_get_value(ma, "source_name", DEFAULT_SOURCE_NAME)); - pa_source_new_data_set_sample_spec(&data, &ss); - pa_source_new_data_set_channel_map(&data, &map); - pa_proplist_sets(data.proplist, PA_PROP_DEVICE_DESCRIPTION, pa_modargs_get_value(ma, "description", "xrdp source")); - pa_proplist_sets(data.proplist, PA_PROP_DEVICE_CLASS, "abstract"); - - u->source = pa_source_new(m->core, &data, PA_SOURCE_LATENCY | PA_SOURCE_DYNAMIC_LATENCY); - pa_source_new_data_done(&data); - - if (!u->source) { - pa_log("Failed to create source object."); - goto fail; - } - - u->latency_time = DEFAULT_LATENCY_TIME; - if (pa_modargs_get_value_u32(ma, "latency_time", &latency_time) < 0) { - pa_log("Failed to parse latency_time value."); - goto fail; - } - u->latency_time = latency_time; - - u->source->parent.process_msg = source_process_msg; - u->source->update_requested_latency = source_update_requested_latency_cb; - u->source->userdata = u; - - pa_source_set_asyncmsgq(u->source, u->thread_mq.inq); - pa_source_set_rtpoll(u->source, u->rtpoll); - - pa_source_set_latency_range(u->source, 0, MAX_LATENCY_USEC); - u->block_usec = u->source->thread_info.max_latency; - - u->source->thread_info.max_rewind = - pa_usec_to_bytes(u->block_usec, &u->source->sample_spec); - - #if defined(PA_CHECK_VERSION) - #if PA_CHECK_VERSION(0, 9, 22) - if (!(u->thread = pa_thread_new("xrdp-source", thread_func, u))) { - #else - if (!(u->thread = pa_thread_new(thread_func, u))) { - #endif - #else - if (!(u->thread = pa_thread_new(thread_func, u))) - #endif - pa_log("Failed to create thread."); - goto fail; - } - - pa_source_put(u->source); - - pa_modargs_free(ma); - - u->display_num = get_display_num_from_display(getenv("DISPLAY")); - - return 0; - -fail: - if (ma) - pa_modargs_free(ma); - - pa__done(m); - - return -1; -} - -void pa__done(pa_module*m) { - struct userdata *u; - - pa_assert(m); - - if (!(u = m->userdata)) - return; - - if (u->source) - pa_source_unlink(u->source); - - if (u->thread) { - pa_asyncmsgq_send(u->thread_mq.inq, NULL, PA_MESSAGE_SHUTDOWN, NULL, 0, NULL); - pa_thread_free(u->thread); - } - - pa_thread_mq_done(&u->thread_mq); - - if (u->source) - pa_source_unref(u->source); - - if (u->rtpoll) - pa_rtpoll_free(u->rtpoll); - - pa_xfree(u); -} - -static int get_display_num_from_display(char *display_text) { - int index; - int mode; - int host_index; - int disp_index; - int scre_index; - int display_num; - char host[256]; - char disp[256]; - char scre[256]; - - if (display_text == NULL) { - return 0; - } - memset(host, 0, 256); - memset(disp, 0, 256); - memset(scre, 0, 256); - - index = 0; - host_index = 0; - disp_index = 0; - scre_index = 0; - mode = 0; - - while (display_text[index] != 0) { - if (display_text[index] == ':') { - mode = 1; - } else if (display_text[index] == '.') { - mode = 2; - } else if (mode == 0) { - host[host_index] = display_text[index]; - host_index++; - } else if (mode == 1) { - disp[disp_index] = display_text[index]; - disp_index++; - } else if (mode == 2) { - scre[scre_index] = display_text[index]; - scre_index++; - } - index++; - } - - host[host_index] = 0; - disp[disp_index] = 0; - scre[scre_index] = 0; - display_num = atoi(disp); - return display_num; -} From e189be9d2e5174d8b88362733be1571bd023ae5a Mon Sep 17 00:00:00 2001 From: Jay Sorg Date: Sun, 12 Aug 2018 22:36:05 -0700 Subject: [PATCH 05/15] .gitignore, change configure_params.h to xrdp_configure_options.h --- .gitignore | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.gitignore b/.gitignore index 38b5d55e..659fa108 100644 --- a/.gitignore +++ b/.gitignore @@ -43,4 +43,4 @@ sesman/sesman.ini stamp-h1 xrdp/xrdp xrdp/xrdp.ini -configure_params.h +xrdp_configure_options.h From 59f3a79fe430de3979c99a1bcdc74ee5b1990224 Mon Sep 17 00:00:00 2001 From: Koichiro IWAO Date: Mon, 27 Aug 2018 10:47:05 +0900 Subject: [PATCH 06/15] sesman: pass pulse socket name via environment variable --- sesman/env.c | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/sesman/env.c b/sesman/env.c index c897f1b3..46d261d4 100644 --- a/sesman/env.c +++ b/sesman/env.c @@ -30,6 +30,7 @@ #include +#include "xrdp_sockets.h" #include "list.h" #include "sesman.h" #include "ssl_calls.h" @@ -143,6 +144,12 @@ env_set_user(const char *username, char **passwd_file, int display, g_setenv("XRDP_SESSION", "1", 1); /* XRDP_SOCKET_PATH should be set even here, chansrv uses this */ g_setenv("XRDP_SOCKET_PATH", XRDP_SOCKET_PATH, 1); + /* pulse sink socket */ + g_snprintf(text, sizeof(text) - 1, CHANSRV_PORT_OUT_BASE_STR, display); + g_setenv("CHANSRV_PULSE_SINK_SOCKET", text, 1); + /* pulse source socket */ + g_snprintf(text, sizeof(text) - 1, CHANSRV_PORT_IN_BASE_STR, display); + g_setenv("CHANSRV_PULSE_SOURCE_SOCKET", text, 1); if ((env_names != 0) && (env_values != 0) && (env_names->count == env_values->count)) { From d6992cf62d505ceca712993e3854cd0289698d9e Mon Sep 17 00:00:00 2001 From: Koichiro IWAO Date: Mon, 27 Aug 2018 15:19:14 +0900 Subject: [PATCH 07/15] sesman: add XRDP_ prefix to xrdp related environment variable and remove CHANSRV, use the shorter name --- sesman/env.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/sesman/env.c b/sesman/env.c index 46d261d4..b097f38c 100644 --- a/sesman/env.c +++ b/sesman/env.c @@ -146,10 +146,10 @@ env_set_user(const char *username, char **passwd_file, int display, g_setenv("XRDP_SOCKET_PATH", XRDP_SOCKET_PATH, 1); /* pulse sink socket */ g_snprintf(text, sizeof(text) - 1, CHANSRV_PORT_OUT_BASE_STR, display); - g_setenv("CHANSRV_PULSE_SINK_SOCKET", text, 1); + g_setenv("XRDP_PULSE_SINK_SOCKET", text, 1); /* pulse source socket */ g_snprintf(text, sizeof(text) - 1, CHANSRV_PORT_IN_BASE_STR, display); - g_setenv("CHANSRV_PULSE_SOURCE_SOCKET", text, 1); + g_setenv("XRDP_PULSE_SOURCE_SOCKET", text, 1); if ((env_names != 0) && (env_values != 0) && (env_names->count == env_values->count)) { From fadbd20baf37bcd56176113e193c110bc473b965 Mon Sep 17 00:00:00 2001 From: jsane Date: Wed, 15 Aug 2018 14:59:55 +0200 Subject: [PATCH 08/15] xrdp: Use configured values instead of hardcoded ones in login_wnd inputs. Configured ls_label_width and ls_input_width currently only apply to the combo l abel and dropdown. Other labels and inputs (username, password, port, ...) use hardcoded defaults. Also had to change the default label width; for the previous value of 60, "username" ends up just a few pixels too wide. --- xrdp/xrdp.ini.in | 2 +- xrdp/xrdp_login_wnd.c | 6 +++--- xrdp/xrdp_types.h | 2 -- 3 files changed, 4 insertions(+), 6 deletions(-) diff --git a/xrdp/xrdp.ini.in b/xrdp/xrdp.ini.in index fb09bbd9..94a60f2b 100644 --- a/xrdp/xrdp.ini.in +++ b/xrdp/xrdp.ini.in @@ -96,7 +96,7 @@ ls_logo_y_pos=50 ; for positioning labels such as username, password etc ls_label_x_pos=30 -ls_label_width=60 +ls_label_width=65 ; for positioning text and combo boxes next to above labels ls_input_x_pos=110 diff --git a/xrdp/xrdp_login_wnd.c b/xrdp/xrdp_login_wnd.c index 262f1bbb..c09f8002 100644 --- a/xrdp/xrdp_login_wnd.c +++ b/xrdp/xrdp_login_wnd.c @@ -386,7 +386,7 @@ xrdp_wm_show_edits(struct xrdp_wm *self, struct xrdp_bitmap *combo) else if (g_strncmp(ASK, value, ASK_LEN) == 0) { /* label */ - b = xrdp_bitmap_create(95, DEFAULT_EDIT_H, self->screen->bpp, + b = xrdp_bitmap_create(globals->ls_label_width, DEFAULT_EDIT_H, self->screen->bpp, WND_TYPE_LABEL, self); list_insert_item(self->login_window->child_list, insert_index, (long)b); @@ -401,7 +401,7 @@ xrdp_wm_show_edits(struct xrdp_wm *self, struct xrdp_bitmap *combo) set_string(&b->caption1, name); /* edit */ - b = xrdp_bitmap_create(DEFAULT_EDIT_W, DEFAULT_EDIT_H, self->screen->bpp, + b = xrdp_bitmap_create(globals->ls_input_width, DEFAULT_EDIT_H, self->screen->bpp, WND_TYPE_EDIT, self); list_insert_item(self->login_window->child_list, insert_index, (long)b); @@ -859,7 +859,7 @@ load_xrdp_config(struct xrdp_config *config, int bpp) globals->ls_logo_x_pos = 63; globals->ls_logo_y_pos = 50; globals->ls_label_x_pos = 30; - globals->ls_label_width = 60; + globals->ls_label_width = 65; globals->ls_input_x_pos = 110; globals->ls_input_width = 210; globals->ls_input_y_pos = 150; diff --git a/xrdp/xrdp_types.h b/xrdp/xrdp_types.h index 75c70ee7..e317f584 100644 --- a/xrdp/xrdp_types.h +++ b/xrdp/xrdp_types.h @@ -496,9 +496,7 @@ struct xrdp_bitmap #define DEFAULT_ELEMENT_TOP 35 #define DEFAULT_BUTTON_W 60 #define DEFAULT_BUTTON_H 23 -#define DEFAULT_COMBO_W 210 #define DEFAULT_COMBO_H 21 -#define DEFAULT_EDIT_W 210 #define DEFAULT_EDIT_H 21 #define DEFAULT_WND_LOGIN_W 425 #define DEFAULT_WND_LOGIN_H 475 From 2a85a65d0843b8c0b3ca3169b6cd41246aaaabe2 Mon Sep 17 00:00:00 2001 From: Koichiro IWAO Date: Tue, 11 Sep 2018 11:22:15 +0900 Subject: [PATCH 09/15] show more helpful message if xrdp-dis failed --- sesman/tools/dis.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/sesman/tools/dis.c b/sesman/tools/dis.c index 408027ca..728be4a9 100644 --- a/sesman/tools/dis.c +++ b/sesman/tools/dis.c @@ -26,6 +26,7 @@ #include #include #include +#include #include "xrdp_sockets.h" @@ -76,6 +77,10 @@ int main(int argc, char **argv) { printf("message sent ok\n"); } + else + { + printf("message send failed: %s\n", strerror(errno)); + } return 0; } From 74497752dc062d1c2dc9594654a3770e23d989ec Mon Sep 17 00:00:00 2001 From: Koichiro IWAO Date: Thu, 16 Aug 2018 11:31:35 +0900 Subject: [PATCH 10/15] Add TLSv1.3 support Actually, TLSv1.3 will be enabled without this change if xrdp is compiled with OpenSSL or alternatives which support TLSv1.3. This commit makes to enable or disable TLSv1.3 explicitly. Also, this commit adds a log "TLSv1.3 enabled by config, but not supported by system OpenSSL". if xrdp installation doesn't support TLSv1.3. It should be user-friendly. --- common/ssl_calls.c | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/common/ssl_calls.c b/common/ssl_calls.c index cb13825e..d1003b8a 100644 --- a/common/ssl_calls.c +++ b/common/ssl_calls.c @@ -1004,8 +1004,23 @@ ssl_get_protocols_from_string(const char *str, long *ssl_protocols) #endif #if defined(SSL_OP_NO_TLSv1_2) protocols |= SSL_OP_NO_TLSv1_2; +#endif +#if defined(SSL_OP_NO_TLSv1_3) + protocols |= SSL_OP_NO_TLSv1_3; #endif bad_protocols = protocols; + if (g_pos(str, ",TLSv1.3,") >= 0) + { +#if defined(SSL_OP_NO_TLSv1_3) + log_message(LOG_LEVEL_DEBUG, "TLSv1.3 enabled"); + protocols &= ~SSL_OP_NO_TLSv1_3; +#else + log_message(LOG_LEVEL_WARNING, + "TLSv1.3 enabled by config, " + "but not supported by system OpenSSL"); + rv |= (1 << 6); +#endif + } if (g_pos(str, ",TLSv1.2,") >= 0) { #if defined(SSL_OP_NO_TLSv1_2) From 1ad8cbb2a0f8e54e518dcda4bcfe43db90488964 Mon Sep 17 00:00:00 2001 From: Koichiro IWAO Date: Thu, 16 Aug 2018 11:42:46 +0900 Subject: [PATCH 11/15] Document TLSv1.3 support --- docs/man/xrdp.ini.5.in | 2 +- xrdp/xrdp.ini.in | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/docs/man/xrdp.ini.5.in b/docs/man/xrdp.ini.5.in index b43c6aa1..834f258b 100644 --- a/docs/man/xrdp.ini.5.in +++ b/docs/man/xrdp.ini.5.in @@ -144,7 +144,7 @@ Negotiate these security methods with clients. .RE .TP -\fBssl_protocols\fP=\fI[SSLv3] [TLSv1] [TLSv1.1] [TLSv1.2]\fP +\fBssl_protocols\fP=\fI[SSLv3] [TLSv1] [TLSv1.1] [TLSv1.2] [TLSv1.3]\fP Enables the specified SSL/TLS protocols. Each value should be separated by comma. SSLv2 is always disabled. At least one protocol should be given to accept TLS connections. This parameter is effective only if \fBsecurity_layer\fP is set to \fBtls\fP or \fBnegotiate\fP. diff --git a/xrdp/xrdp.ini.in b/xrdp/xrdp.ini.in index fb09bbd9..97fc81f9 100644 --- a/xrdp/xrdp.ini.in +++ b/xrdp/xrdp.ini.in @@ -28,8 +28,8 @@ crypt_level=high certificate= key_file= ; set SSL protocols -; can be comma separated list of 'SSLv3', 'TLSv1', 'TLSv1.1', 'TLSv1.2' -ssl_protocols=TLSv1, TLSv1.1, TLSv1.2 +; can be comma separated list of 'SSLv3', 'TLSv1', 'TLSv1.1', 'TLSv1.2', 'TLSv1.3' +ssl_protocols=TLSv1, TLSv1.1, TLSv1.2, TLSv1.3 ; set TLS cipher suites #tls_ciphers=HIGH From 171f8e79ed76113bdfb8fa6d89822647ab31b297 Mon Sep 17 00:00:00 2001 From: Koichiro IWAO Date: Fri, 14 Sep 2018 00:41:09 +0900 Subject: [PATCH 12/15] xrdp: deprecate TLSv1 and TLSv1.1 Most websites disabled TLSv1 (1.0) and TLSv1.1 since March 2018 [1][2][3]. It is HTTPS context but there's few differences between HTTPS and other TLS connections. Users can whenever re-enable these deprecated TLS versions by editing xrdp.ini but not enabled by default. [1] https://www.globalsign.com/en/blog/disable-tls-10-and-all-ssl-versions/ [2] https://www.thesslstore.com/blog/deprecation-tls-1-0-1-1-underway/ [3] https://www.digicert.com/blog/depreciating-tls-1-0-and-1-1/ --- xrdp/xrdp.ini.in | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/xrdp/xrdp.ini.in b/xrdp/xrdp.ini.in index 97fc81f9..76da53b5 100644 --- a/xrdp/xrdp.ini.in +++ b/xrdp/xrdp.ini.in @@ -29,7 +29,7 @@ certificate= key_file= ; set SSL protocols ; can be comma separated list of 'SSLv3', 'TLSv1', 'TLSv1.1', 'TLSv1.2', 'TLSv1.3' -ssl_protocols=TLSv1, TLSv1.1, TLSv1.2, TLSv1.3 +ssl_protocols=TLSv1.2, TLSv1.3 ; set TLS cipher suites #tls_ciphers=HIGH From 7b7d2288f164dc2701ed0b17923183276b19b855 Mon Sep 17 00:00:00 2001 From: Koichiro IWAO Date: Tue, 25 Sep 2018 13:49:50 +0900 Subject: [PATCH 13/15] Update NEWS for v0.9.8 --- NEWS.md | 27 +++++++++++++++++++++++++++ 1 file changed, 27 insertions(+) diff --git a/NEWS.md b/NEWS.md index af16d6d9..5809efc4 100644 --- a/NEWS.md +++ b/NEWS.md @@ -1,3 +1,30 @@ +# Release notes for xrdp v0.9.8 (2018/XX/XX) + +## Deprecation notice +We removed TLSv1 and TLSv1.1 from the default config. The current default is TLSv1.2 +and TLSv1.3. Users can whenever re-enable these early TLS versions by editing xrdp. +To use TLSv1.3, OpenSSL or LibreSSL must support TLSv1.3. You can know the OpenSSL +or LibreSSL version by `xrdp --version` command that compiled with xrdp. + +## Other topics + +Pulseaudio modules has been removed from xrdp source tree since it is actually +independent and not part of xrdp. The repository has been moved to: +https://github.com/neutrinolabs/pulseaudio-module-xrdp + +If you want to use audio redirection, make sure install the module separately. + +## New features +* Add TLSv1.3 support #1193 + +## Bug fixes +* Ensure unmount redirected drive on fatal X error #1140 + +## Other changes +* Show more helpful message if xrdp-dis failed #1206 +* Pass pulse socket name via environment variable #1198 +* Fix xrdp's log path in man page #1168 + # Release notes for xrdp v0.9.7 (2018/06/29) ## Deprecation notice From 7672014d4eaf101ca8bc1f3c233b6918379265d0 Mon Sep 17 00:00:00 2001 From: Koichiro IWAO Date: Tue, 25 Sep 2018 13:49:55 +0900 Subject: [PATCH 14/15] Bump version to v0.9.8 --- README.md | 2 +- configure.ac | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 382d40a4..3f1d4a9b 100644 --- a/README.md +++ b/README.md @@ -2,7 +2,7 @@ [![Gitter](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/neutrinolabs/xrdp) ![Apache-License](https://img.shields.io/badge/License-Apache%202.0-blue.svg) -*Current Version:* 0.9.7 +*Current Version:* 0.9.8 # xrdp - an open source RDP server diff --git a/configure.ac b/configure.ac index fdac5e00..3aa14db6 100644 --- a/configure.ac +++ b/configure.ac @@ -1,7 +1,7 @@ # Process this file with autoconf to produce a configure script AC_PREREQ(2.65) -AC_INIT([xrdp], [0.9.7], [xrdp-devel@googlegroups.com]) +AC_INIT([xrdp], [0.9.8], [xrdp-devel@googlegroups.com]) AC_CONFIG_HEADERS(config_ac.h:config_ac-h.in) AM_INIT_AUTOMAKE([1.7.2 foreign]) AC_CONFIG_MACRO_DIR([m4]) From 6bbb2b2e2df12fcbb75892aac3e377e3374d1261 Mon Sep 17 00:00:00 2001 From: Koichiro IWAO Date: Tue, 25 Sep 2018 14:32:27 +0900 Subject: [PATCH 15/15] Update release date --- NEWS.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/NEWS.md b/NEWS.md index 5809efc4..e496291f 100644 --- a/NEWS.md +++ b/NEWS.md @@ -1,4 +1,4 @@ -# Release notes for xrdp v0.9.8 (2018/XX/XX) +# Release notes for xrdp v0.9.8 (2018/09/25) ## Deprecation notice We removed TLSv1 and TLSv1.1 from the default config. The current default is TLSv1.2