adding some access control features

This commit is contained in:
ilsimo 2005-12-15 20:41:03 +00:00
parent e91c34f803
commit 721ca9efae
8 changed files with 308 additions and 20 deletions

View File

@ -1,6 +1,6 @@
# sesman makefile # sesman makefile
SESMANOBJ = sesman.o config.o tcp.o sig.o session.o env.o \ SESMANOBJ = sesman.o config.o tcp.o sig.o session.o env.o \
os_calls.o d3des.o list.o file.o log.o os_calls.o d3des.o list.o file.o log.o access.o
SESRUNOBJ = sesrun.o config.o tcp.o \ SESRUNOBJ = sesrun.o config.o tcp.o \
os_calls.o d3des.o list.o file.o log.o os_calls.o d3des.o list.o file.o log.o
@ -15,7 +15,7 @@ DEFINES = -DSESMAN_CFG_FILE=\"$(CFGDIR)/sesman.ini\" \
-DSESMAN_PID_FILE=\"$(PIDDIR)/sesman.pid\" -DSESMAN_PID_FILE=\"$(PIDDIR)/sesman.pid\"
CFLAGS = -Wall -O2 -I../common $(DEFINES) CFLAGS = -Wall -O2 -I../common $(DEFINES)
LDFLAGS = -L /usr/gnu/lib LDFLAGS = -L /usr/gnu/lib $(DEFINES)
C_OS_FLAGS = $(CFLAGS) -c C_OS_FLAGS = $(CFLAGS) -c
CC = gcc CC = gcc

86
sesman/access.c Normal file
View File

@ -0,0 +1,86 @@
/*
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program 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 General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
xrdp: A Remote Desktop Protocol server.
Copyright (C) Jay Sorg 2005
authenticate user
*/
#include "sesman.h"
#define _XOPEN_SOURCE
#include <sys/types.h>
#include <pwd.h>
#include <grp.h>
//#include <unistd.h>
//#include <pwd.h>
extern struct config_sesman g_cfg;
/******************************************************************************/
int DEFAULT_CC
access_login_allowed(char* user)
{
int i;
struct group* groups;
struct passwd* pwd;
if ((0==g_strncmp(user, "root",5)) && (0==g_cfg.sec.allow_root))
{
log_message(LOG_LEVEL_WARNING, "ROOT login attempted, but root login is disabled");
return 0;
}
if (0==g_cfg.sec.ts_users_enable)
{
LOG_DBG("Terminal Server Users group is disabled, allowing authentication",1);
return 1;
}
groups = getgrgid(g_cfg.sec.ts_users);
if (0==groups)
{
log_message(LOG_LEVEL_ERROR,"Cannot read group info! - login denied");
return 0;
}
pwd = getpwnam(user);
if (0==pwd)
{
log_message(LOG_LEVEL_ERROR, "Cannot read user info! - login denied");
return 0;
}
if (g_cfg.sec.ts_users==pwd->pw_gid)
{
LOG_DBG("ts_users is user's primary group",1);
return 1;
}
i=0;
while (0!=groups->gr_mem[i])
{
LOG_DBG("user: %s", groups->gr_mem[i]);
if (0==strcmp(groups->gr_mem[i], user)) return 1;
i++;
}
log_message(LOG_LEVEL_INFO, "login denied for user %s", user);
return 0;
}

33
sesman/access.h Normal file
View File

@ -0,0 +1,33 @@
/*
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program 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 General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
xrdp: A Remote Desktop Protocol server.
Copyright (C) Jay Sorg 2005
session manager - access control header
*/
#ifndef ACCESS_H
#define ACCESS_H
/**
*
*
*
*/
int DEFAULT_CC
access_login_allowed(char* user);
#endif

View File

@ -19,6 +19,9 @@
session manager - read config file session manager - read config file
*/ */
#include "sys/types.h"
#include "grp.h"
#include "arch.h" #include "arch.h"
#include "list.h" #include "list.h"
#include "file.h" #include "file.h"
@ -68,6 +71,9 @@ config_read(struct config_sesman* cfg)
/* read logging config */ /* read logging config */
config_read_logging(fd, &(cfg->log), param_n, param_v); config_read_logging(fd, &(cfg->log), param_n, param_v);
/* read security config */
config_read_security(fd, &(cfg->sec), param_n, param_v);
/* cleanup */ /* cleanup */
list_delete(sec); list_delete(sec);
list_delete(param_v); list_delete(param_v);
@ -85,6 +91,12 @@ config_read_globals(int file, struct config_sesman* cf, struct list* param_n,
list_clear(param_v); list_clear(param_v);
list_clear(param_n); list_clear(param_n);
/* resetting the struct */
cf->listen_port[0]='\0';
cf->enable_user_wm=0;
cf->user_wm[0]='\0';
cf->default_wm[0]='\0';
file_read_section(file, SESMAN_CFG_GLOBALS, param_n, param_v); file_read_section(file, SESMAN_CFG_GLOBALS, param_n, param_v);
for (i = 0; i < param_n->count; i++) for (i = 0; i < param_n->count; i++)
@ -108,6 +120,21 @@ config_read_globals(int file, struct config_sesman* cf, struct list* param_n,
} }
} }
/* checking for missing required parameters */
if ('\0'==cf->listen_port[0])
{
g_strncpy(cf->listen_port, "3350", 5);
}
if ('\0'==cf->user_wm[0])
{
cf->enable_user_wm=0;
}
if ('\0'==cf->default_wm[0])
{
g_strncpy(cf->default_wm, "startwm.sh", 11);
}
/* showing read config */
g_printf("sesman config:\r\n"); g_printf("sesman config:\r\n");
g_printf("\tListenPort: %s\r\n", cf->listen_port); g_printf("\tListenPort: %s\r\n", cf->listen_port);
g_printf("\tEnableUserWindowManager: %i\r\n", cf->enable_user_wm); g_printf("\tEnableUserWindowManager: %i\r\n", cf->enable_user_wm);
@ -158,6 +185,11 @@ config_read_logging(int file, struct log_config* lc, struct list* param_n,
} }
} }
if (0==lc->log_file)
{
lc->log_file=g_strdup("./sesman.log");
}
g_printf("logging configuration:\r\n"); g_printf("logging configuration:\r\n");
g_printf("\tLogFile: %s\r\n",lc->log_file); g_printf("\tLogFile: %s\r\n",lc->log_file);
g_printf("\tLogLevel: %i\r\n", lc->log_level); g_printf("\tLogLevel: %i\r\n", lc->log_level);
@ -167,3 +199,62 @@ config_read_logging(int file, struct log_config* lc, struct list* param_n,
return 0; return 0;
} }
/******************************************************************************/
int DEFAULT_CC
config_read_security(int file, struct config_security* sc, struct list* param_n,
struct list* param_v)
{
int i;
char* buf;
list_clear(param_v);
list_clear(param_n);
/* setting defaults */
sc->allow_root=0;
sc->ts_users_enable=0;
sc->ts_admins_enable=0;
file_read_section(file, SESMAN_CFG_SECURITY, param_n, param_v);
for (i = 0; i < param_n->count; i++)
{
buf = (char*)list_get_item(param_n, i);
if (0 == g_strncasecmp(buf, SESMAN_CFG_SEC_ALLOW_ROOT, 20))
{
sc->allow_root = text2bool((char*)list_get_item(param_v, i));
}
if (0 == g_strncasecmp(buf, SESMAN_CFG_SEC_USR_GROUP, 20))
{
sc->ts_users_enable=1;
sc->ts_users=(getgrnam((char*)list_get_item(param_v, i))->gr_gid);
}
if (0 == g_strncasecmp(buf, SESMAN_CFG_SEC_ADM_GROUP, 20))
{
sc->ts_admins_enable=1;
sc->ts_admins=(getgrnam((char*)list_get_item(param_v, i))->gr_gid);
}
}
/* printing security config */
g_printf("security configuration:\r\n");
g_printf("\tAllowRootLogin: %i\r\n",sc->allow_root);
if (sc->ts_users_enable)
{
g_printf("\tTSUsersGroup: %i\r\n", sc->ts_users);
}
else
{
g_printf("\tNo TSUsersGroup defined\r\n");
}
if (sc->ts_admins_enable)
{
g_printf("\tTSAdminsGroup: %i\r\n", sc->ts_admins);
}
else
{
g_printf("\tNo TSAdminsGroup defined\r\n");
}
return 0;
}

View File

@ -22,6 +22,7 @@
#ifndef CONFIG_H #ifndef CONFIG_H
#define CONFIG_H #define CONFIG_H
#include "sys/types.h"
#include "arch.h" #include "arch.h"
#include "list.h" #include "list.h"
#include "log.h" #include "log.h"
@ -41,6 +42,7 @@
#define SESMAN_CFG_PORT "ListenPort" #define SESMAN_CFG_PORT "ListenPort"
#define SESMAN_CFG_ENABLE_USERWM "EnableUserWindowManager" #define SESMAN_CFG_ENABLE_USERWM "EnableUserWindowManager"
#define SESMAN_CFG_USERWM "UserWindowManager" #define SESMAN_CFG_USERWM "UserWindowManager"
#define SESMAN_CFG_MAX_SESSION "MaxSessions"
#define SESMAN_CFG_LOGGING "Logging" #define SESMAN_CFG_LOGGING "Logging"
#define SESMAN_CFG_LOG_FILE "LogFile" #define SESMAN_CFG_LOG_FILE "LogFile"
@ -48,6 +50,47 @@
#define SESMAN_CFG_LOG_ENABLE_SYSLOG "EnableSyslog" #define SESMAN_CFG_LOG_ENABLE_SYSLOG "EnableSyslog"
#define SESMAN_CFG_LOG_SYSLOG_LEVEL "SyslogLevel" #define SESMAN_CFG_LOG_SYSLOG_LEVEL "SyslogLevel"
#define SESMAN_CFG_SECURITY "Security"
#define SESMAN_CFG_SEC_ALLOW_ROOT "AllowRootLogin"
#define SESMAN_CFG_SEC_USR_GROUP "TerminalServerUsers"
#define SESMAN_CFG_SEC_ADM_GROUP "TerminalServerAdmins"
#define SESMAN_CFG_SESSIONS "Sessions"
#define SESMAN_CFG_SESS_MAX "MaxSessions"
#define SESMAN_CFG_SESS_KILL_DISC "KillDisconnected"
#define SESMAN_CFG_SESS_IDLE_LIMIT "IdleTimeLimit"
/**
*
* @struct config_sesman
* @brief \t struct that contains \t sesman configuration
*
* This \t struct contains all of \t sesman configuration parameters\n
* Every parameter in \t [globals] is a member of this struct, other
* sections options are embedded in this \t struct as member structures
*
*/
struct config_security
{
/**
* @var allow_root
* @brief
*/
int allow_root;
/**
* @var ts_users
* @brief Terminal Server Users group
*/
int ts_users_enable;
gid_t ts_users;
/**
* @var ts_admins
* @brief Terminal Server Adminnistrators group
*/
int ts_admins_enable;
gid_t ts_admins;
};
/** /**
* *
* @struct config_sesman * @struct config_sesman
@ -85,6 +128,11 @@ struct config_sesman
* @brief Log configuration \t struct * @brief Log configuration \t struct
*/ */
struct log_config log; struct log_config log;
/**
* @var sec
* @brief Security configuration options \t struct
*/
struct config_security sec;
}; };
/** /**
@ -123,4 +171,16 @@ config_read_globals(int file, struct config_sesman* cf, struct list* param_n, st
int DEFAULT_CC int DEFAULT_CC
config_read_logging(int file, struct log_config* lc, struct list* param_n, struct list* param_v); config_read_logging(int file, struct log_config* lc, struct list* param_n, struct list* param_v);
/**
*
* @brief Reads sesman [iSecurity] configuration section
*
* @param cfg pointer to configuration object to be replaced
*
* @return 0 on success, 1 on failure
*
*/
int DEFAULT_CC
config_read_security(int file, struct config_security* sc, struct list* param_n, struct list* param_v);
#endif #endif

View File

@ -142,8 +142,17 @@ sesman_main_loop()
} }
else else
{ {
display = session_start(width, height, bpp, user, pass, g_printf("pre auth");
data); if (1==access_login_allowed(user))
{
log_message(LOG_LEVEL_INFO, "granted TS access to user %s", user);
display = session_start(width, height, bpp, user, pass,
data);
}
else
{
display=0;
}
} }
if (display == 0) if (display == 0)
{ {
@ -227,7 +236,7 @@ main(int argc, char** argv)
/* check if sesman is running */ /* check if sesman is running */
if (!g_file_exist(SESMAN_PID_FILE)) if (!g_file_exist(SESMAN_PID_FILE))
{ {
g_printf("sesman is not running (pid file not found)\n"); g_printf("sesman is not running (pid file not found - %s)\n", SESMAN_PID_FILE);
g_exit(1); g_exit(1);
} }
@ -247,6 +256,10 @@ main(int argc, char** argv)
{ {
g_printf("error killing sesman: %s\n", strerror(errno)); g_printf("error killing sesman: %s\n", strerror(errno));
} }
else
{
g_file_delete(SESMAN_PID_FILE);
}
g_exit(error); g_exit(error);
} }
@ -260,7 +273,6 @@ main(int argc, char** argv)
} }
if (g_file_exist(SESMAN_PID_FILE)) if (g_file_exist(SESMAN_PID_FILE))
{ {
g_printf("sesman is already running.\n"); g_printf("sesman is already running.\n");
@ -338,7 +350,10 @@ main(int argc, char** argv)
sesman_main_loop(); sesman_main_loop();
log_end(); if (!daemon)
{
log_end();
}
return 0; return 0;
} }

View File

@ -33,6 +33,7 @@
#include "tcp.h" #include "tcp.h"
#include "sig.h" #include "sig.h"
#include "session.h" #include "session.h"
#include "access.h"
#ifndef SESMAN_PID_FILE #ifndef SESMAN_PID_FILE
#define SESMAN_PID_FILE "./sesman.pid" #define SESMAN_PID_FILE "./sesman.pid"

View File

@ -20,18 +20,19 @@
*/ */
#include "arch.h" #include "sesman.h"
#include "os_calls.h"
#define _XOPEN_SOURCE #define _XOPEN_SOURCE
#include <unistd.h> #include <sys/types.h>
#include <string.h> #include <crypt.h>
#include <shadow.h> #include <shadow.h>
#include <pwd.h> #include <pwd.h>
extern struct config_sesman g_cfg;
/******************************************************************************/ /******************************************************************************/
/* returns boolean */ /* returns boolean */
int DEFAULT_CC long DEFAULT_CC
auth_userpass(char* user, char* pass) auth_userpass(char* user, char* pass)
{ {
char salt[13] = "$1$"; char salt[13] = "$1$";
@ -46,7 +47,7 @@ auth_userpass(char* user, char* pass)
{ {
return 0; return 0;
} }
if (strncmp(spw->pw_passwd, "x", 3) == 0) if (g_strncmp(spw->pw_passwd, "x", 3) == 0)
{ {
/* the system is using shadow */ /* the system is using shadow */
stp = getspnam(user); stp = getspnam(user);
@ -54,15 +55,15 @@ auth_userpass(char* user, char* pass)
{ {
return 0; return 0;
} }
strncpy(hash, stp->sp_pwdp, 34); g_strncpy(hash, stp->sp_pwdp, 34);
} }
else else
{ {
/* old system with only passwd */ /* old system with only passwd */
strncpy(hash, spw->pw_passwd, 34); g_strncpy(hash, spw->pw_passwd, 34);
} }
hash[34] = '\0'; hash[34] = '\0';
if (strncmp(hash, "$1$", 3) == 0) if (g_strncmp(hash, "$1$", 3) == 0)
{ {
/* gnu style crypt(); */ /* gnu style crypt(); */
saltcnt = 3; saltcnt = 3;
@ -82,7 +83,7 @@ auth_userpass(char* user, char* pass)
salt[2] = '\0'; salt[2] = '\0';
} }
encr = crypt(pass,salt); encr = crypt(pass,salt);
if (strncmp(encr, hash, 34) != 0) if (g_strncmp(encr, hash, 34) != 0)
{ {
return 0; return 0;
} }
@ -92,21 +93,22 @@ auth_userpass(char* user, char* pass)
/******************************************************************************/ /******************************************************************************/
/* returns error */ /* returns error */
int DEFAULT_CC int DEFAULT_CC
auth_start_session(void) auth_start_session(long in_val, int in_display)
{ {
return 0; return 0;
} }
/******************************************************************************/ /******************************************************************************/
int DEFAULT_CC int DEFAULT_CC
auth_end(void) auth_end(long in_val)
{ {
return 0; return 0;
} }
/******************************************************************************/ /******************************************************************************/
int DEFAULT_CC int DEFAULT_CC
auth_set_env(void) auth_set_env(long in_val)
{ {
return 0; return 0;
} }