diff --git a/common/string_calls.c b/common/string_calls.c index 18b6acf4..a53a4d9d 100644 --- a/common/string_calls.c +++ b/common/string_calls.c @@ -24,6 +24,8 @@ #include #include #include +#include + #include "log.h" #include "os_calls.h" @@ -140,6 +142,36 @@ g_text2bool(const char *s) return 0; } +/*****************************************************************************/ +int +g_get_display_num_from_display(const char *display_text) +{ + int rv = -1; + const char *p; + + /* Skip over the hostname part of the DISPLAY */ + if (display_text != NULL && (p = strchr(display_text, ':')) != NULL) + { + ++p; /* Skip the ':' */ + + /* Cater for the (still supported) double-colon. See + * https://www.x.org/releases/X11R7.7/doc/libX11/libX11/libX11.html */ + if (*p == ':') + { + ++p; + } + + /* Check it starts with a digit, to avoid oddities like DISPLAY=":zz.0" + * being parsed successfully */ + if (isdigit(*p)) + { + rv = g_atoi(p); + } + } + + return rv; +} + /*****************************************************************************/ /* returns length of text */ int @@ -774,4 +806,3 @@ g_strtrim(char *str, int trim_flags) free(text1); return 0; } - diff --git a/common/string_calls.h b/common/string_calls.h index 4918b840..02876fca 100644 --- a/common/string_calls.h +++ b/common/string_calls.h @@ -103,6 +103,16 @@ g_text2bool(const char *s); char * g_bytes_to_hexdump(const char *src, int len); +/** + * Extracts the display number from an X11 display string + * + * @param Display string (i.e. g_getenv("DISPLAY")) + * + * @result <0 if the string could not be parsed, or >=0 for a display number + */ +int +g_get_display_num_from_display(const char *display_text); + int g_strlen(const char *text); const char *g_strchr(const char *text, int c); char *g_strcpy(char *dest, const char *src); diff --git a/sesman/chansrv/chansrv.c b/sesman/chansrv/chansrv.c index 5a96f9b8..4452d998 100644 --- a/sesman/chansrv/chansrv.c +++ b/sesman/chansrv/chansrv.c @@ -17,8 +17,6 @@ * limitations under the License. */ -#include - #if defined(HAVE_CONFIG_H) #include #endif @@ -1559,34 +1557,6 @@ x_server_fatal_handler(void) exit(0); } -/*****************************************************************************/ -static int -get_display_num_from_display(const char *display_text) -{ - int rv = -1; - const char *p; - - /* Skip over the hostname part of the DISPLAY */ - if ((p = g_strchr(display_text, ':')) != NULL) - { - ++p; /* Skip the ':' */ - - /* Cater for the (still supported) double-colon. See - * https://www.x.org/releases/X11R7.7/doc/libX11/libX11/libX11.html */ - if (*p == ':') - { - ++p; - } - - if (isdigit(*p)) - { - rv = g_atoi(p); - } - } - - return rv; -} - /*****************************************************************************/ int main_cleanup(void) @@ -1721,7 +1691,7 @@ main(int argc, char **argv) main_cleanup(); return 1; } - g_display_num = get_display_num_from_display(display_text); + g_display_num = g_get_display_num_from_display(display_text); if (g_display_num < 0) { g_writeln("Unable to get display from DISPLAY='%s'", display_text); diff --git a/sesman/chansrv/pcsc/xrdp_pcsc.c b/sesman/chansrv/pcsc/xrdp_pcsc.c index cf958dbb..252212c0 100644 --- a/sesman/chansrv/pcsc/xrdp_pcsc.c +++ b/sesman/chansrv/pcsc/xrdp_pcsc.c @@ -11,6 +11,8 @@ #include #include +#include "string_calls.h" + #define PCSC_API typedef unsigned char BYTE; @@ -153,70 +155,6 @@ lhexdump(void *p, int len) } } -/*****************************************************************************/ -static int -get_display_num_from_display(const char *display_text) -{ - int rv; - int index; - int mode; - int host_index; - int disp_index; - int scre_index; - char host[256]; - char disp[256]; - char scre[256]; - - 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) - { - if (display_text[index] < '0' || display_text[index] > '9') - { - return -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; - LLOGLN(10, ("get_display_num_from_display: host [%s] disp [%s] scre [%s]", - host, disp, scre)); - rv = (disp_index== 0) ? -1 : atoi(disp); - return rv; -} - /*****************************************************************************/ static int connect_to_chansrv(void) @@ -256,7 +194,7 @@ connect_to_chansrv(void) LLOGLN(0, ("connect_to_chansrv: error, home not set")); return 1; } - dis = get_display_num_from_display(xrdp_display); + dis = g_get_display_num_from_display(xrdp_display); if (dis < 0) { LLOGLN(0, ("connect_to_chansrv: error, don't understand DISPLAY='%s'", diff --git a/sesman/tools/Makefile.am b/sesman/tools/Makefile.am index 2f8be440..ae5d80cd 100644 --- a/sesman/tools/Makefile.am +++ b/sesman/tools/Makefile.am @@ -38,6 +38,9 @@ xrdp_sesadmin_SOURCES = \ xrdp_dis_SOURCES = \ dis.c +xrdp_dis_LDADD = \ + $(top_builddir)/common/libcommon.la + xrdp_xcon_SOURCES = \ xcon.c diff --git a/sesman/tools/dis.c b/sesman/tools/dis.c index 728be4a9..cc06e870 100644 --- a/sesman/tools/dis.c +++ b/sesman/tools/dis.c @@ -29,6 +29,7 @@ #include #include "xrdp_sockets.h" +#include "string_calls.h" int main(int argc, char **argv) { @@ -36,7 +37,6 @@ int main(int argc, char **argv) int dis; struct sockaddr_un sa; size_t len; - char *p; char *display; if (argc != 1) @@ -54,7 +54,12 @@ int main(int argc, char **argv) return 1; } - dis = strtol(display + 1, &p, 10); + dis = g_get_display_num_from_display(display); + if (dis < 0) + { + printf("Can't parse DISPLAY='%s'\n", display); + return 1; + } memset(&sa, 0, sizeof(sa)); sa.sun_family = AF_UNIX; sprintf(sa.sun_path, XRDP_DISCONNECT_STR, dis); diff --git a/xrdpapi/xrdpapi.c b/xrdpapi/xrdpapi.c index 11198e28..1eeabdac 100644 --- a/xrdpapi/xrdpapi.c +++ b/xrdpapi/xrdpapi.c @@ -35,6 +35,7 @@ #include "log.h" #include "xrdp_sockets.h" +#include "string_calls.h" #include "xrdpapi.h" struct wts_obj @@ -45,8 +46,6 @@ struct wts_obj /* helper functions used by WTSxxx API - do not invoke directly */ static int -get_display_num_from_display(char *display_text); -static int can_send(int sck, int millis); static int can_recv(int sck, int millis); @@ -93,7 +92,6 @@ WTSVirtualChannelOpenEx(unsigned int SessionId, const char *pVirtualName, unsigned int flags) { struct wts_obj *wts; - char *display_text; int bytes; unsigned long long1; struct sockaddr_un s; @@ -113,13 +111,7 @@ WTSVirtualChannelOpenEx(unsigned int SessionId, const char *pVirtualName, return 0; } wts->fd = -1; - display_text = getenv("DISPLAY"); - - if (display_text != 0) - { - wts->display_num = get_display_num_from_display(display_text); - } - + wts->display_num = g_get_display_num_from_display(getenv("DISPLAY")); if (wts->display_num < 0) { LOG(LOG_LEVEL_ERROR, "WTSVirtualChannelOpenEx: fatal error; invalid DISPLAY"); @@ -526,42 +518,3 @@ can_recv(int sck, int millis) return 0; } - -/*****************************************************************************/ -static int -get_display_num_from_display(char *display_text) -{ - int index; - int mode; - int disp_index; - char disp[256]; - - index = 0; - disp_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 == 1) - { - if (display_text[index] < '0' || display_text[index] > '9') - { - return -1; - } - disp[disp_index] = display_text[index]; - disp_index++; - } - index++; - } - - disp[disp_index] = 0; - return (disp_index== 0) ? -1 : atoi(disp); -}