diff --git a/Makefile.am b/Makefile.am index 613c2471..9e0e42bd 100644 --- a/Makefile.am +++ b/Makefile.am @@ -8,6 +8,7 @@ endif SUBDIRS = \ common \ + raptorsmiface \ vnc \ rdp \ xup \ diff --git a/configure.ac b/configure.ac index dddd5a07..73a472ad 100644 --- a/configure.ac +++ b/configure.ac @@ -72,6 +72,7 @@ localstatedir="/var"; fi AC_CONFIG_FILES([Makefile common/Makefile + raptorsmiface/Makefile vnc/Makefile rdp/Makefile libxrdp/Makefile diff --git a/raptorsmiface/Makefile.am b/raptorsmiface/Makefile.am new file mode 100644 index 00000000..acf3e233 --- /dev/null +++ b/raptorsmiface/Makefile.am @@ -0,0 +1,34 @@ +EXTRA_DIST = libraptorsmiface.h + +EXTRA_DEFINES = +EXTRA_INCLUDES = +EXTRA_LIBS = +EXTRA_FLAGS = + +if GOT_PREFIX +EXTRA_INCLUDES += -I$(prefix)/include +EXTRA_FLAGS += -L$(prefix)/lib -Wl,-rpath -Wl,$(prefix)/lib +endif + +AM_CFLAGS = \ + -DXRDP_CFG_PATH=\"${sysconfdir}/xrdp\" \ + -DXRDP_SBIN_PATH=\"${sbindir}\" \ + -DXRDP_SHARE_PATH=\"${datadir}/xrdp\" \ + -DXRDP_PID_PATH=\"${localstatedir}/run\" \ + $(EXTRA_DEFINES) + +INCLUDES = \ + -I$(top_srcdir)/common \ + $(EXTRA_INCLUDES) + +lib_LTLIBRARIES = \ + libraptorsmiface.la + +libraptorsmiface_la_SOURCES = \ + libraptorsmiface.c + +libraptorsmiface_la_LDFLAGS = \ + $(EXTRA_FLAGS) -lmysqlclient + +libraptorsmiface_la_LIBADD = \ + $(EXTRA_LIBS) diff --git a/raptorsmiface/libraptorsmiface.c b/raptorsmiface/libraptorsmiface.c new file mode 100644 index 00000000..4d3db02c --- /dev/null +++ b/raptorsmiface/libraptorsmiface.c @@ -0,0 +1,568 @@ +// (c) 2012 Timothy Pearson +// (c) 2012 Raptor Engineering +// ALL RIGHTS RESERVED + +#define _GNU_SOURCE + +#include +#include +#include +#include +#include + +#include +#include +#include +#include + +#include +#include +#include + +#include + +#include "libraptorsmiface.h" + +MYSQL *conn = 0; + +char *server = "localhost"; +char *user = "remotelab"; +char *password = "rlpass123"; /* set me first */ +char *database = "remotelab_sm"; + +void dprint(const char *fmt, ...) +{ + va_list argp; + va_start(argp, fmt); + +#if 0 + vprintf(fmt, argp); +#else + char debug[1024]; + vsprintf(debug, fmt, argp); + FILE *fp = fopen("/raptorsmiface.debug", "a"); + if (fp != NULL) + { + fputs(debug, fp); + fclose(fp); + } +#endif + + va_end(argp); +} + +void connect_if_needed() { + if (!conn) { + conn = mysql_init(NULL); + if (!mysql_real_connect(conn, server, user, password, database, 0, NULL, 0)) { + dprint("[ERROR] MySQL connection FAILED [%s]\n\r", mysql_error(conn)); + conn = 0; + } + } +} + +char* get_mysql_escaped_string(MYSQL *sqlcn, char* rawstr) { + unsigned int minlen = strlen(rawstr); + unsigned int maxlen = ((minlen*2)+1); + char* escstr = malloc(maxlen*sizeof(char)); + mysql_real_escape_string(sqlcn, escstr, rawstr, minlen); + return escstr; +} + +char* get_group_for_user(char* username) { + struct passwd* pwd; + pwd = getpwnam(username); + if (!pwd) { + return true; + } + gid_t groupid = pwd->pw_gid; + struct group* primarygroup; + primarygroup = getgrgid(groupid); + if (!primarygroup) { + return true; + } + + return strdup(primarygroup->gr_name); +} + +char raptor_sm_deallocate_session(char* username) { + MYSQL_RES *res; + MYSQL_ROW row; + MYSQL_RES *svr_res; + MYSQL_ROW svr_row; + MYSQL_RES *cnt_res; + MYSQL_ROW cnt_row; + char* query; + + connect_if_needed(); + if (!conn) { + return 1; + } + + // Remove the user from the system + char* safe_username = get_mysql_escaped_string(conn, username); + asprintf(&query, "DELETE FROM sessions WHERE username='%s'", safe_username); + free(safe_username); + if (mysql_query(conn, query)) { + // Server error + free(query); + return 2; + } + else { + free(query); + return 0; + } +} + +char* raptor_sm_allocate_session(char* username) { + MYSQL_RES *res; + MYSQL_ROW row; + MYSQL_RES *svr_res; + MYSQL_ROW svr_row; + MYSQL_RES *cnt_res; + MYSQL_ROW cnt_row; + char* query; + + connect_if_needed(); + if (!conn) { + return strdup("SQLERR001"); + } + + // Verify that this user is not already on the system + char* safe_username = get_mysql_escaped_string(conn, username); + asprintf(&query, "SELECT servername FROM sessions WHERE username='%s'", safe_username); + free(safe_username); + if (mysql_query(conn, query)) { + // Server error + free(query); + return strdup("SQLERR002"); + } + else { + free(query); + res = mysql_store_result(conn); + if ((row = mysql_fetch_row(res)) == NULL) { + // User is not on a system + // Find the least utilized node + if (mysql_query(conn, "SELECT name FROM servers")) { + // Server error + mysql_free_result(res); + return strdup("SQLERR003"); + } + else { + svr_res = mysql_store_result(conn); + char* bestserver = strdup(""); + int bestusage = INT_MAX; + while ((svr_row = mysql_fetch_row(svr_res)) != NULL) { + char* safe_servername = get_mysql_escaped_string(conn, svr_row[0]); + asprintf(&query, "SELECT username FROM sessions WHERE servername='%s'", safe_servername); + free(safe_servername); + if (mysql_query(conn, query)) { + // Server error + free(query); + free(bestserver); + mysql_free_result(res); + mysql_free_result(svr_res); + return strdup("SQLERR004"); + } + else { + free(query); + cnt_res = mysql_store_result(conn); + int usagecount = 0; + while ((cnt_row = mysql_fetch_row(cnt_res)) != NULL) { + usagecount++; + } + mysql_free_result(cnt_res); + if (usagecount < bestusage) { + free(bestserver); + bestserver = strdup(svr_row[0]); + bestusage = usagecount; + } + } + } + mysql_free_result(res); + mysql_free_result(svr_res); + + // Insert new information into the sessions database and set status to ALLOCATED + char* safe_servername = get_mysql_escaped_string(conn, bestserver); + char* safe_username = get_mysql_escaped_string(conn, username); + asprintf(&query, "INSERT INTO sessions (username, servername, state) VALUES ('%s', '%s', '%d')", safe_username, safe_servername, SM_STATUS_ALLOCATED); + free(safe_servername); + free(safe_username); + if (mysql_query(conn, query)) { + // Server error + free(query); + return strdup("SQLERR005"); + } + else { + free(query); + return strdup(bestserver); + } + } + } + else { + char* ret = strdup(row[0]); + mysql_free_result(res); + return ret; + } + } +} + +char* raptor_sm_get_ip_for_hostname(char* hostname, char* error) { + struct addrinfo hints, *res; + struct in_addr addr; + int err; + + memset(&hints, 0, sizeof(hints)); + hints.ai_socktype = SOCK_STREAM; + hints.ai_family = AF_INET; + + if ((err = getaddrinfo(hostname, NULL, &hints, &res)) != 0) { + if (error) *error = 1; + return strdup(""); + } + + addr.s_addr = ((struct sockaddr_in *)(res->ai_addr))->sin_addr.s_addr; + + char* ret = strdup(inet_ntoa(addr)); + freeaddrinfo(res); + if (error) *error = 0; + return ret; +} + +char* raptor_sm_get_hostname_for_username(char* username, bool create) { + MYSQL_RES *res; + MYSQL_ROW row; + char* query; + + connect_if_needed(); + if (!conn) { + return strdup("SQLERR100"); + } + + char* safe_username = get_mysql_escaped_string(conn, username); + asprintf(&query, "SELECT servername FROM sessions WHERE username='%s'", safe_username); + free(safe_username); + if (mysql_query(conn, query)) { + // Server error + free(query); + return strdup("SQLERR101"); + } + else { + free(query); + res = mysql_store_result(conn); + while ((row = mysql_fetch_row(res)) != NULL) { + char* ret = strdup(row[0]); + mysql_free_result(res); + return ret; + } + // Nothing in the DB + mysql_free_result(res); + if (create) { + // Try to allocate a new session on a node + return raptor_sm_allocate_session(username); + } + else { + return strdup(""); + } + } +} + +char* raptor_sm_get_ip_for_username(char* username, bool create) { + char* hostname = raptor_sm_get_hostname_for_username(username, create); + char err; + char* ip = raptor_sm_get_ip_for_hostname(hostname, &err); + if (err) { + raptor_sm_deallocate_session(username); + } + free(hostname); + return ip; +} + +bool raptor_sm_sesslimit_reached(char* username) { + MYSQL_RES *res; + MYSQL_ROW row; + char* query; + + connect_if_needed(); + if (!conn) { + return true; + } + + // Respect maximum session number for the group for this user + int sesslimit = 0; // Default to denying all sessions + + // Get group for user + char* groupname = get_group_for_user(username); + char* safe_groupname = get_mysql_escaped_string(conn, groupname); + free(groupname); + asprintf(&query, "SELECT sesslimit FROM groups WHERE groupname='%s'", safe_groupname); + free(safe_groupname); + if (mysql_query(conn, query)) { + // Server error + free(query); + return true; + } + else { + free(query); + res = mysql_store_result(conn); + row = mysql_fetch_row(res); + if (row[0]) { + sesslimit = atoi(row[0]); + } + mysql_free_result(res); + } + + // Figure out how many users are online from this group + int sesscount = 0; + asprintf(&query, "SELECT username FROM sessions WHERE state<>'%d'", SM_STATUS_ALLOCATED); + if (mysql_query(conn, query)) { + // Server error + free(query); + return true; + } + else { + free(query); + res = mysql_store_result(conn); + while ((row = mysql_fetch_row(res)) != NULL) { + if (row[0]) { + char* test_groupname = get_group_for_user(row[0]); + if (strcmp(groupname, test_groupname) == 0) { + sesscount++; + } + free(test_groupname); + } + } + mysql_free_result(res); + + if (sesscount < sesslimit) { + return false; + } + return true; + } + + // We should never end up here! + return true; +} + +pid_t raptor_sm_run_remote_server(char* username, char *const argv[]) { + MYSQL_RES *res; + MYSQL_ROW row; + char* query; + + connect_if_needed(); + if (!conn) { + return -1; + } + + // Respect maximum session number for the group for this user + if (raptor_sm_sesslimit_reached(username)) { + return -5; + } + + // Make sure a server is not already running for this user + // Return the existing PID if it is + char* safe_username = get_mysql_escaped_string(conn, username); + asprintf(&query, "SELECT pid FROM sessions WHERE username='%s' AND state<>'%d'", safe_username, SM_STATUS_ALLOCATED); + free(safe_username); + if (mysql_query(conn, query)) { + // Server error + free(query); + return -2; + } + else { + free(query); + res = mysql_store_result(conn); + while ((row = mysql_fetch_row(res)) != NULL) { + if (row[0]) { + int ret = atoi(row[0]); + if (ret >= 0) { + mysql_free_result(res); + return ret; + } + } + } + mysql_free_result(res); + } + + int i; + int n_commands; + + n_commands = 0; + while (argv[n_commands] != NULL) { + n_commands++; + } + + char* ipaddr = raptor_sm_get_ip_for_username(username, true); + + // This is HORRIBLY inefficient + char* command_string = strdup(""); + for (i=0; i + +#include + +typedef unsigned char bool; +#define true 1 +#define false 0 + +// SM_STATUS_ALLOCATED: Server is not yet started +// SM_STATUS_RUNNING: Server is up, but client is not connected +// SM_STATUS_CONNECTED: Server is up and client is connected +enum raptor_sm_status { + SM_STATUS_ALLOCATED, + SM_STATUS_RUNNING, + SM_STATUS_CONNECTED, + SM_STATUS_FORCEKILL +}; + +char* raptor_sm_get_ip_for_hostname(char* hostname, char* err); +char* raptor_sm_get_hostname_for_username(char* username, bool create); + +char* raptor_sm_get_ip_for_username(char* username, bool create); +pid_t raptor_sm_run_remote_server(char* username, char *const argv[]); +char* raptor_sm_server_started(char* username, pid_t pid, int display); +int raptor_sm_get_display_for_username(char* username); +void raptor_sm_wait_for_pid_exit(char* username, pid_t pid); +void raptor_sm_session_terminated(char* username); +int raptor_sm_get_new_unique_display(int mindisplay, int maxdisplay); +bool raptor_sm_sesslimit_reached(char* username); +char raptor_sm_set_session_state(int display, int state); \ No newline at end of file diff --git a/sesman/Makefile.am b/sesman/Makefile.am index 07fdf43a..c126059a 100644 --- a/sesman/Makefile.am +++ b/sesman/Makefile.am @@ -8,7 +8,8 @@ AM_CFLAGS = \ INCLUDES = \ -I$(top_srcdir)/common \ - -I$(top_srcdir)/sesman/libscp + -I$(top_srcdir)/sesman/libscp \ + -I$(top_srcdir)/raptorsmiface if SESMAN_NOPAM AUTH_C = verify_user.c @@ -49,6 +50,7 @@ xrdp_sesman_SOURCES = \ xrdp_sesman_LDADD = \ $(top_srcdir)/common/libcommon.la \ $(top_srcdir)/sesman/libscp/libscp.la \ + $(top_srcdir)/raptorsmiface/libraptorsmiface.la \ $(AUTH_LIB) \ -lpthread diff --git a/sesman/chansrv/Makefile.am b/sesman/chansrv/Makefile.am index 7cd1fa6c..486d49a8 100644 --- a/sesman/chansrv/Makefile.am +++ b/sesman/chansrv/Makefile.am @@ -7,7 +7,8 @@ AM_CFLAGS = \ -DXRDP_PID_PATH=\"${localstatedir}/run\" INCLUDES = \ - -I$(top_srcdir)/common + -I$(top_srcdir)/common \ + -I$(top_srcdir)/raptorsmiface sbin_PROGRAMS = \ xrdp-chansrv @@ -21,4 +22,5 @@ xrdp_chansrv_SOURCES = \ xrdp_chansrv_LDADD = \ -L/usr/X11R6/lib \ $(top_srcdir)/common/libcommon.la \ + $(top_srcdir)/raptorsmiface/libraptorsmiface.la \ -lX11 -lXfixes diff --git a/sesman/chansrv/chansrv.c b/sesman/chansrv/chansrv.c index f2ca961d..6d09a701 100644 --- a/sesman/chansrv/chansrv.c +++ b/sesman/chansrv/chansrv.c @@ -30,6 +30,8 @@ #include "file.h" #include "file_loc.h" +#include "libraptorsmiface.h" + static struct trans* g_lis_trans = 0; static struct trans* g_con_trans = 0; static struct chan_item g_chan_items[32]; @@ -48,6 +50,32 @@ int g_cliprdr_chan_id = -1; /* cliprdr */ int g_rdpsnd_chan_id = -1; /* rdpsnd */ int g_rdpdr_chan_id = -1; /* rdpdr */ +#if 0 +#include +#include +#include +void dprint(const char *fmt, ...) +{ + va_list argp; + va_start(argp, fmt); + char debug[1024]; + vsprintf(debug, fmt, argp); + FILE *fp = fopen("/chansrv.debug", "a"); + if (fp != NULL) + { + fputs(debug, fp); + fclose(fp); + } + va_end(argp); +} +#undef LOG +#define LOG(_a, _params) \ +{ \ + dprint _params; \ + dprint("\n"); \ +} +#endif + /*****************************************************************************/ /* returns error */ int APP_CC @@ -231,6 +259,8 @@ process_message_channel_setup(struct stream* s) { dev_redir_init(); } + // Use the display number to mark session connected in the Raptor session management database + raptor_sm_set_session_state(g_display_num, SM_STATUS_CONNECTED); return rv; } @@ -477,6 +507,9 @@ channel_thread_loop(void* in_val) /* delete g_con_trans */ trans_delete(g_con_trans); g_con_trans = 0; + // Use the display number to mark session disconnected in the Raptor session management database + raptor_sm_set_session_state(g_display_num, SM_STATUS_RUNNING); + exit(0); // RAPTOR session management /* create new listener */ error = setup_listen(); if (error != 0) @@ -678,6 +711,8 @@ main(int argc, char** argv) break; } } + // Use the display number to mark session disconnected in the Raptor session management database + raptor_sm_set_session_state(g_display_num, SM_STATUS_RUNNING); /* cleanup */ main_cleanup(); LOG(1, ("main: app exiting pid %d(0x%8.8x)", pid, pid)); diff --git a/sesman/sesman.ini b/sesman/sesman.ini index 9aa58581..1d1d16bf 100644 --- a/sesman/sesman.ini +++ b/sesman/sesman.ini @@ -13,7 +13,7 @@ TerminalServerAdmins=tsadmins [Sessions] X11DisplayOffset=10 -MaxSessions=10 +MaxSessions=1000000 KillDisconnected=0 IdleTimeLimit=0 DisconnectedTimeLimit=0 @@ -24,12 +24,18 @@ LogLevel=DEBUG EnableSyslog=0 SyslogLevel=DEBUG +#[X11rdp] +#param1=-bs +#param2=-ac +#param3=-nolisten +#param4=tcp +#param5=-uds + [X11rdp] param1=-bs param2=-ac param3=-nolisten param4=tcp -param5=-uds [Xvnc] param1=-bs diff --git a/sesman/session.c b/sesman/session.c index 2960a7f7..cc91e7d6 100644 --- a/sesman/session.c +++ b/sesman/session.c @@ -31,6 +31,8 @@ #include //#include +#include "libraptorsmiface.h" + extern tbus g_sync_event; extern unsigned char g_fixedkey[8]; extern struct config_sesman* g_cfg; /* in sesman.c */ @@ -368,7 +370,21 @@ session_start_fork(int width, int height, int bpp, char* username, "item - user %s", username); return 0; } - display = session_get_aval_display_from_chain(); + char session_was_already_running = 0; + int allocdisplay = raptor_sm_get_display_for_username(username); + if (allocdisplay >= 0) { + session_was_already_running = 1; + display = allocdisplay; + } + else { + int allocdisplay = raptor_sm_get_new_unique_display(g_cfg->sess.x11_display_offset, g_cfg->sess.max_sessions); + if (allocdisplay < 0) { + display = 0; + } + else { + display = allocdisplay; + } + } if (display == 0) { g_free(temp->item); @@ -393,6 +409,9 @@ session_start_fork(int width, int height, int bpp, char* username, { wait_for_xserver(display); env_set_user(username, 0, display); + if (session_was_already_running) { + g_exit(0); + } if (x_server_running(display)) { auth_set_env(data); @@ -512,6 +531,8 @@ session_start_fork(int width, int height, int bpp, char* username, list_add_item(xserver_params, (long)g_strdup(geometry)); list_add_item(xserver_params, (long)g_strdup("-depth")); list_add_item(xserver_params, (long)g_strdup(depth)); + list_add_item(xserver_params, (long)g_strdup("-reset")); + list_add_item(xserver_params, (long)g_strdup("-terminate")); /* additional parameters from sesman.ini file */ //config_read_xserver_params(SESMAN_SESSION_TYPE_XRDP, @@ -521,7 +542,30 @@ session_start_fork(int width, int height, int bpp, char* username, /* make sure it ends with a zero */ list_add_item(xserver_params, 0); pp1 = (char**)xserver_params->items; - g_execvp("X11rdp", pp1); + + pid_t serverpid; + serverpid = raptor_sm_run_remote_server(username, pp1); + + if (serverpid >= 0) { + if (!session_was_already_running) { + char *friendlyscreen = g_strdup(screen); + friendlyscreen[0] = ' '; + raptor_sm_server_started(username, serverpid, atoi(friendlyscreen)); + g_free(friendlyscreen); + + // Wait for PID exit and remove information from the session database + raptor_sm_wait_for_pid_exit(username, serverpid); + raptor_sm_session_terminated(username); + } + } + else { + raptor_sm_session_terminated(username); + log_message(&(g_cfg->log), LOG_LEVEL_ALWAYS, "max concurrent session limit " + "exceeded in group. login for user %s denied", username); + g_exit(1); + } + + g_exit(0); } else { diff --git a/xorg/X11R7.6/x11_file_list.txt b/xorg/X11R7.6/x11_file_list.txt index 6d6de97c..bb518d3d 100644 --- a/xorg/X11R7.6/x11_file_list.txt +++ b/xorg/X11R7.6/x11_file_list.txt @@ -92,7 +92,6 @@ libXpm-3.5.9.tar.bz2 : libXpm-3.5.9 libXaw-1.0.8.tar.bz2 : libXaw-1.0.8 : mkfontdir-1.0.6.tar.bz2 : mkfontdir-1.0.6 : xkbcomp-1.2.0.tar.bz2 : xkbcomp-1.2.0 : -xdriinfo-1.0.4.tar.bz2 : xdriinfo-1.0.4 : xorg-server-1.9.3.tar.bz2 : xorg-server-1.9.3 : --with-sha1=libcrypto applewmproto-1.4.1.tar.bz2 : applewmproto-1.4.1 : bdftopcf-1.0.3.tar.bz2 : bdftopcf-1.0.3 : diff --git a/xrdp/Makefile.am b/xrdp/Makefile.am index 4fe6f6a5..618b40e1 100644 --- a/xrdp/Makefile.am +++ b/xrdp/Makefile.am @@ -15,7 +15,8 @@ AM_CFLAGS = \ INCLUDES = \ -I$(top_srcdir)/common \ - -I$(top_srcdir)/libxrdp + -I$(top_srcdir)/libxrdp \ + -I$(top_srcdir)/raptorsmiface sbin_PROGRAMS = \ xrdp @@ -37,7 +38,8 @@ xrdp_SOURCES = \ xrdp_LDADD = \ $(top_srcdir)/common/libcommon.la \ - $(top_srcdir)/libxrdp/libxrdp.la + $(top_srcdir)/libxrdp/libxrdp.la \ + $(top_srcdir)/raptorsmiface/libraptorsmiface.la xrdpsysconfdir=$(sysconfdir)/xrdp diff --git a/xrdp/xrdp.ini b/xrdp/xrdp.ini index ee4652a9..ee1543d6 100644 --- a/xrdp/xrdp.ini +++ b/xrdp/xrdp.ini @@ -19,52 +19,6 @@ max_bpp=24 #hidelogwindow=yes [xrdp1] -name=sesman-Xvnc -lib=libvnc.so -username=ask -password=ask -ip=127.0.0.1 -port=-1 - -[xrdp2] -name=console -lib=libvnc.so -ip=127.0.0.1 -port=5900 -username=na -password=ask - -[xrdp3] -name=vnc-any -lib=libvnc.so -ip=ask -port=ask5900 -username=na -password=ask - -[xrdp4] -name=sesman-any -lib=libvnc.so -ip=ask -port=-1 -username=ask -password=ask - -[xrdp5] -name=rdp-any -lib=librdp.so -ip=ask -port=ask3389 - -[xrdp6] -name=freerdp-any -lib=libxrdpfreerdp1.so -ip=ask -port=ask3389 -username=ask -password=ask - -[xrdp7] name=sesman-X11rdp lib=libxup.so username=ask diff --git a/xrdp/xrdp_mm.c b/xrdp/xrdp_mm.c index a41208eb..be2d9cd8 100644 --- a/xrdp/xrdp_mm.c +++ b/xrdp/xrdp_mm.c @@ -22,6 +22,8 @@ #include "xrdp.h" +#include "libraptorsmiface.h" + /*****************************************************************************/ struct xrdp_mm* APP_CC xrdp_mm_create(struct xrdp_wm* owner) @@ -34,6 +36,7 @@ xrdp_mm_create(struct xrdp_wm* owner) self->login_names->auto_free = 1; self->login_values = list_create(); self->login_values->auto_free = 1; + self->login_username = 0; return self; } @@ -130,6 +133,7 @@ xrdp_mm_send_login(struct xrdp_mm* self) if (g_strcasecmp(name, "username") == 0) { username = value; + self->login_username = g_strdup(username); } else if (g_strcasecmp(name, "password") == 0) { @@ -396,21 +400,40 @@ xrdp_mm_setup_mod2(struct xrdp_mm* self) } else if (self->code == 10) /* X11rdp */ { - use_uds = 1; - if (xrdp_mm_get_value(self, "ip", text, 255) == 0) - { - if (g_strcmp(text, "127.0.0.1") != 0) - { + char* rsmip = raptor_sm_get_ip_for_username(self->login_username, true); + int allocdisplay = raptor_sm_get_display_for_username(self->login_username); + if ((raptor_sm_sesslimit_reached(self->login_username)) && (allocdisplay < 0)) { + g_snprintf(text, 255, "[LICENSE] Maximum concurrent session"); + xrdp_wm_log_msg(self->wm, text); + g_snprintf(text, 255, "[LICENSE] limit exceeded for group."); + xrdp_wm_log_msg(self->wm, text); + g_snprintf(text, 255, "[LICENSE] Login for user %s denied.", self->login_username); + xrdp_wm_log_msg(self->wm, text); + raptor_sm_session_terminated(self->login_username); + return 1; + } + else { + if (allocdisplay >= 0) { + self->display = allocdisplay; + } + self->mod->mod_set_param(self->mod, "ip", rsmip); + use_uds = 1; + if (g_strcmp(rsmip, "127.0.0.1") != 0) { use_uds = 0; } - } - if (use_uds) - { - g_snprintf(text, 255, "/tmp/.xrdp/xrdp_display_%d", self->display); - } - else - { - g_snprintf(text, 255, "%d", 6200 + self->display); + g_free(rsmip); +g_snprintf(text, 255, "[RAJA DEBUG 200.0] uds: %d username %s\n\r", use_uds, self->login_username); +xrdp_wm_log_msg(self->wm, text); +g_snprintf(text, 255, "[RAJA DEBUG 200.1] allocdisplay: %d\n\r", allocdisplay); +xrdp_wm_log_msg(self->wm, text); + if (use_uds) + { + g_snprintf(text, 255, "/tmp/.xrdp/xrdp_display_%d", self->display); + } + else + { + g_snprintf(text, 255, "%d", 6200 + self->display); + } } } else @@ -442,7 +465,9 @@ xrdp_mm_setup_mod2(struct xrdp_mm* self) { name = (char*)list_get_item(self->login_names, i); value = (char*)list_get_item(self->login_values, i); - self->mod->mod_set_param(self->mod, name, value); + if (strcmp(name, "ip") != 0) { + self->mod->mod_set_param(self->mod, name, value); + } } /* connect */ if (self->mod->mod_connect(self->mod) == 0) @@ -757,14 +782,15 @@ xrdp_mm_process_login_response(struct xrdp_mm* self, struct stream* s) if (ok) { self->display = display; - g_snprintf(text, 255, "xrdp_mm_process_login_response: login successful " - "for display %d", display); + g_snprintf(text, 255, "login successful on display %d", display); xrdp_wm_log_msg(self->wm, text); if (xrdp_mm_setup_mod1(self) == 0) { if (xrdp_mm_setup_mod2(self) == 0) { xrdp_mm_get_value(self, "ip", ip, 255); +g_snprintf(text, 255, "[RAJA DEBUG 300.0] atctsa IP %s [username %s]\n\r", ip, self->login_username); +xrdp_wm_log_msg(self->wm, text); xrdp_wm_set_login_mode(self->wm, 10); self->wm->dragging = 0; /* connect channel redir */ diff --git a/xrdp/xrdp_types.h b/xrdp/xrdp_types.h index 3c5decf6..da9a062b 100644 --- a/xrdp/xrdp_types.h +++ b/xrdp/xrdp_types.h @@ -199,6 +199,7 @@ struct xrdp_mm int chan_trans_up; /* true once connected to chansrv */ int delete_chan_trans; /* boolean set when done with channel connection */ int usechansrv; /* true if chansrvport is set in xrdp.ini or using sesman */ + char* login_username; }; struct xrdp_key_info diff --git a/xup/xup.c b/xup/xup.c index 28c1b50c..ce646128 100644 --- a/xup/xup.c +++ b/xup/xup.c @@ -149,6 +149,9 @@ lib_mod_connect(struct mod* mod) LIB_DEBUG(mod, "out lib_mod_connect error"); return 1; } +char text[256]; +g_snprintf(text, 255, "[RAJA DEBUG 900.0] atctsa IP %s\n\r", mod->ip); +mod->server_msg(mod, text, 0); if (g_strcmp(mod->ip, "") == 0) { mod->server_msg(mod, "error - no ip set", 0); @@ -162,6 +165,8 @@ lib_mod_connect(struct mod* mod) { use_uds = 1; } +g_snprintf(text, 255, "[RAJA DEBUG 910.0] uds: %d port %s\n\r", use_uds, con_port); +mod->server_msg(mod, text, 0); mod->sck_closed = 0; i = 0; while (1) @@ -602,6 +607,9 @@ lib_mod_set_param(struct mod* mod, char* name, char* value) { if (g_strcasecmp(name, "username") == 0) { +char text[256]; +g_snprintf(text, 255, "[RAJA DEBUG 910.0] username set to %s\n\r", value); +mod->server_msg(mod, text, 0); g_strncpy(mod->username, value, 255); } else if (g_strcasecmp(name, "password") == 0) @@ -610,6 +618,9 @@ lib_mod_set_param(struct mod* mod, char* name, char* value) } else if (g_strcasecmp(name, "ip") == 0) { +char text[256]; +g_snprintf(text, 255, "[RAJA DEBUG 910.1] IP set to %s\n\r", value); +mod->server_msg(mod, text, 0); g_strncpy(mod->ip, value, 255); } else if (g_strcasecmp(name, "port") == 0)