1
0
mirror of https://github.com/InfrastructureServices/vsftpd.git synced 2025-04-19 01:24:02 +03:00

Updated to v3.0.1

This commit is contained in:
Dag Wieers 2012-09-18 00:00:00 +02:00
parent 8ab4684483
commit 48344724c6
24 changed files with 220 additions and 80 deletions

View File

@ -1323,3 +1323,17 @@ protocol synchronization issues.
At this point: v3.0.0 released!
===============================
- Fix some seccomp related build errors on certain CentOS and Debian versions.
- Seccomp filter sandbox: missing munmap() -- oops. Did you know that qsort()
opens and maps /proc/meminfo but only for larger item counts?
- Seccomp filter sandbox: deny socket() gracefully for text_userdb_names.
- Fix various NULL crashes with nonsensical config settings. Noted by Tianyin Xu
<tixu@cs.ucsd.edu>.
- Force cast to unsigned char in is* char functions.
- Fix harmless integer issues in strlist.c.
- Started on a (possibly ill-advised?) crusade to compile cleanly with
Wconversion. Decided to suspend the effort half-way through.
At this point: v3.0.1 released!
===============================

2
README
View File

@ -1,4 +1,4 @@
This is vsftpd, version 3.0.0
This is vsftpd, version 3.0.1
Author: Chris Evans
Contact: scarybeasts@gmail.com
Website: http://vsftpd.beasts.org/

View File

@ -53,8 +53,11 @@ vsf_banner_dir_changed(struct vsf_session* p_sess, int ftpcode)
*/
{
struct mystr msg_file_str = INIT_MYSTR;
(void) str_fileread(&msg_file_str, tunable_message_file,
VSFTP_MAX_MSGFILE_SIZE);
if (tunable_message_file)
{
(void) str_fileread(&msg_file_str, tunable_message_file,
VSFTP_MAX_MSGFILE_SIZE);
}
vsf_banner_write(p_sess, &msg_file_str, ftpcode);
str_free(&msg_file_str);
}

View File

@ -50,7 +50,7 @@ str_fileread(struct mystr* p_str, const char* p_filename, unsigned int maxsize)
{
die("read size mismatch");
}
str_alloc_memchunk(p_str, p_sec_buf, size);
str_alloc_memchunk(p_str, p_sec_buf, (unsigned int) size);
}
free_out:
vsf_sysutil_free(p_stat);

2
hash.c
View File

@ -42,7 +42,7 @@ hash_alloc(unsigned int buckets, unsigned int key_size,
p_hash->key_size = key_size;
p_hash->value_size = value_size;
p_hash->hash_func = hash_func;
size = sizeof(struct hash_node*) * buckets;
size = (unsigned int) sizeof(struct hash_node*) * buckets;
p_hash->p_nodes = vsf_sysutil_malloc(size);
vsf_sysutil_memclr(p_hash->p_nodes, size);
return p_hash;

View File

@ -30,7 +30,6 @@ static void vsf_log_do_log_to_file(int fd, struct mystr* p_str);
void
vsf_log_init(struct vsf_session* p_sess)
{
int retval;
if (tunable_syslog_enable || tunable_tcp_wrappers)
{
vsf_sysutil_openlog(1);
@ -41,7 +40,12 @@ vsf_log_init(struct vsf_session* p_sess)
}
if (tunable_dual_log_enable || tunable_xferlog_std_format)
{
retval = vsf_sysutil_create_or_open_file_append(tunable_xferlog_file, 0600);
int retval = -1;
if (tunable_xferlog_file)
{
retval = vsf_sysutil_create_or_open_file_append(tunable_xferlog_file,
0600);
}
if (vsf_sysutil_retval_is_error(retval))
{
die2("failed to open xferlog log file:", tunable_xferlog_file);
@ -52,8 +56,12 @@ vsf_log_init(struct vsf_session* p_sess)
{
if (!tunable_syslog_enable)
{
retval = vsf_sysutil_create_or_open_file_append(tunable_vsftpd_log_file,
0600);
int retval = -1;
if (tunable_vsftpd_log_file)
{
retval = vsf_sysutil_create_or_open_file_append(tunable_vsftpd_log_file,
0600);
}
if (vsf_sysutil_retval_is_error(retval))
{
die2("failed to open vsftpd log file:", tunable_vsftpd_log_file);

23
ls.c
View File

@ -88,7 +88,6 @@ vsf_ls_populate_dir_list(struct mystr_list* p_list,
}
while (1)
{
int len;
static struct mystr s_next_filename_str;
static struct mystr s_next_path_and_filename_str;
static struct vsf_sysutil_statbuf* s_p_statbuf;
@ -97,18 +96,20 @@ vsf_ls_populate_dir_list(struct mystr_list* p_list,
{
break;
}
len = str_getlen(&s_next_filename_str);
if (len > 0 && str_get_char_at(&s_next_filename_str, 0) == '.')
{
if (!a_option && !tunable_force_dot_files)
unsigned int len = str_getlen(&s_next_filename_str);
if (len > 0 && str_get_char_at(&s_next_filename_str, 0) == '.')
{
continue;
}
if (!a_option &&
((len == 2 && str_get_char_at(&s_next_filename_str, 1) == '.') ||
len == 1))
{
continue;
if (!a_option && !tunable_force_dot_files)
{
continue;
}
if (!a_option &&
((len == 2 && str_get_char_at(&s_next_filename_str, 1) == '.') ||
len == 1))
{
continue;
}
}
}
/* Don't show hidden directory entries */

39
main.c
View File

@ -200,8 +200,12 @@ main(int argc, const char* argv[])
}
if (tunable_deny_email_enable)
{
int retval = str_fileread(&the_session.banned_email_str,
tunable_banned_email_file, VSFTP_CONF_FILE_MAX);
int retval = -1;
if (tunable_banned_email_file)
{
retval = str_fileread(&the_session.banned_email_str,
tunable_banned_email_file, VSFTP_CONF_FILE_MAX);
}
if (vsf_sysutil_retval_is_error(retval))
{
die2("cannot read anon e-mail list file:", tunable_banned_email_file);
@ -218,9 +222,13 @@ main(int argc, const char* argv[])
}
if (tunable_secure_email_list_enable)
{
int retval = str_fileread(&the_session.email_passwords_str,
tunable_email_password_file,
VSFTP_CONF_FILE_MAX);
int retval = -1;
if (tunable_email_password_file)
{
retval = str_fileread(&the_session.email_passwords_str,
tunable_email_password_file,
VSFTP_CONF_FILE_MAX);
}
if (vsf_sysutil_retval_is_error(retval))
{
die2("cannot read email passwords file:", tunable_email_password_file);
@ -329,8 +337,11 @@ session_init(struct vsf_session* p_sess)
/* If anonymous mode is active, fetch the uid of the anonymous user */
if (tunable_anonymous_enable)
{
const struct vsf_sysutil_user* p_user =
vsf_sysutil_getpwnam(tunable_ftp_username);
const struct vsf_sysutil_user* p_user = 0;
if (tunable_ftp_username)
{
p_user = vsf_sysutil_getpwnam(tunable_ftp_username);
}
if (p_user == 0)
{
die2("vsftpd: cannot locate user specified in 'ftp_username':",
@ -340,8 +351,11 @@ session_init(struct vsf_session* p_sess)
}
if (tunable_guest_enable)
{
const struct vsf_sysutil_user* p_user =
vsf_sysutil_getpwnam(tunable_guest_username);
const struct vsf_sysutil_user* p_user = 0;
if (tunable_guest_username)
{
p_user = vsf_sysutil_getpwnam(tunable_guest_username);
}
if (p_user == 0)
{
die2("vsftpd: cannot locate user specified in 'guest_username':",
@ -351,8 +365,11 @@ session_init(struct vsf_session* p_sess)
}
if (tunable_chown_uploads)
{
const struct vsf_sysutil_user* p_user =
vsf_sysutil_getpwnam(tunable_chown_username);
const struct vsf_sysutil_user* p_user = 0;
if (tunable_chown_username)
{
p_user = vsf_sysutil_getpwnam(tunable_chown_username);
}
if (p_user == 0)
{
die2("vsftpd: cannot locate user specified in 'chown_username':",

View File

@ -76,7 +76,10 @@ one_process_start(void* p_arg)
{
struct mystr user_name = INIT_MYSTR;
struct mystr chdir_str = INIT_MYSTR;
str_alloc_text(&user_name, tunable_ftp_username);
if (tunable_ftp_username)
{
str_alloc_text(&user_name, tunable_ftp_username);
}
if (tunable_anon_root)
{
str_alloc_text(&chdir_str, tunable_anon_root);

View File

@ -344,7 +344,8 @@ vsf_parseconf_load_setting(const char* p_setting, int errs_fatal)
}
else
{
*(p_uint_setting->p_variable) = str_atoi(&s_value_str);
/* TODO: we could reject negatives instead of converting them? */
*(p_uint_setting->p_variable) = (unsigned int) str_atoi(&s_value_str);
}
return;
}

View File

@ -974,8 +974,7 @@ handle_port(struct vsf_session* p_sess)
vsf_cmdio_write(p_sess, FTP_BADCMD, "Illegal PORT command.");
return;
}
the_port = vals[4] << 8;
the_port |= vals[5];
the_port = (unsigned short) ((vals[4] << 8) | vals[5]);
vsf_sysutil_sockaddr_clone(&p_sess->p_port_sockaddr, p_sess->p_local_addr);
vsf_sysutil_sockaddr_set_ipv4addr(p_sess->p_port_sockaddr, vals);
vsf_sysutil_sockaddr_set_port(p_sess->p_port_sockaddr, the_port);
@ -1736,7 +1735,7 @@ handle_eprt(struct vsf_session* p_sess)
{
if (!vsf_sysutil_sockaddr_addr_equal(p_sess->p_remote_addr,
p_sess->p_port_sockaddr) ||
vsf_sysutil_is_port_reserved(port))
vsf_sysutil_is_port_reserved((unsigned short) port))
{
vsf_cmdio_write(p_sess, FTP_BADCMD, "Illegal EPRT command.");
port_cleanup(p_sess);

View File

@ -96,8 +96,14 @@ minimize_privilege(struct vsf_session* p_sess)
unsigned int caps = 0;
struct mystr user_str = INIT_MYSTR;
struct mystr dir_str = INIT_MYSTR;
str_alloc_text(&user_str, tunable_nopriv_user);
str_alloc_text(&dir_str, tunable_secure_chroot_dir);
if (tunable_nopriv_user)
{
str_alloc_text(&user_str, tunable_nopriv_user);
}
if (tunable_secure_chroot_dir)
{
str_alloc_text(&dir_str, tunable_secure_chroot_dir);
}
if (tunable_chown_uploads)
{
caps |= kCapabilityCAP_CHOWN;

View File

@ -41,7 +41,7 @@ vsf_privop_get_ftp_port_sock(struct vsf_session* p_sess,
int retval;
int i;
int s = vsf_sysutil_get_ipsock(p_sess->p_local_addr);
int port = 0;
unsigned short port = 0;
if (p_sess->pasv_listen_fd != -1)
{
die("listed fd is active?");
@ -52,7 +52,7 @@ vsf_privop_get_ftp_port_sock(struct vsf_session* p_sess,
}
if (tunable_connect_from_port_20)
{
port = tunable_ftp_data_port;
port = (unsigned short) tunable_ftp_data_port;
}
vsf_sysutil_activate_reuseaddr(s);
/* A report of failure here on Solaris, presumably buggy address reuse
@ -133,11 +133,11 @@ vsf_privop_pasv_listen(struct vsf_session* p_sess)
if (tunable_pasv_min_port > min_port && tunable_pasv_min_port <= max_port)
{
min_port = tunable_pasv_min_port;
min_port = (unsigned short) tunable_pasv_min_port;
}
if (tunable_pasv_max_port >= min_port && tunable_pasv_max_port < max_port)
{
max_port = tunable_pasv_max_port;
max_port = (unsigned short) tunable_pasv_max_port;
}
while (--bind_retries)
@ -145,8 +145,8 @@ vsf_privop_pasv_listen(struct vsf_session* p_sess)
int retval;
double scaled_port;
the_port = vsf_sysutil_get_random_byte();
the_port <<= 8;
the_port |= vsf_sysutil_get_random_byte();
the_port = (unsigned short) (the_port << 8);
the_port = (unsigned short) (the_port | vsf_sysutil_get_random_byte());
scaled_port = (double) min_port;
scaled_port += ((double) the_port / (double) 65536) *
((double) max_port - min_port + 1);
@ -367,7 +367,10 @@ handle_anonymous_login(struct vsf_session* p_sess,
str_replace_char(&p_sess->anon_pass_str, '\n', '?');
{
struct mystr ftp_username_str = INIT_MYSTR;
str_alloc_text(&ftp_username_str, tunable_ftp_username);
if (tunable_ftp_username)
{
str_alloc_text(&ftp_username_str, tunable_ftp_username);
}
setup_username_globals(p_sess, &ftp_username_str);
str_free(&ftp_username_str);
}

View File

@ -33,6 +33,10 @@
/* #define DEBUG_SIGSYS 1 */
#ifndef PR_SET_SECCOMP
#define PR_SET_SECCOMP 22
#endif
#ifndef PR_SET_NO_NEW_PRIVS
#define PR_SET_NO_NEW_PRIVS 38
#endif
@ -45,6 +49,14 @@
#define O_LARGEFILE 00100000
#endif
#ifndef O_DIRECTORY
#define O_DIRECTORY 00200000
#endif
#ifndef O_CLOEXEC
#define O_CLOEXEC 002000000
#endif
#define kMaxSyscalls 100
#ifdef DEBUG_SIGSYS
@ -67,6 +79,7 @@ static size_t s_1_arg_validations;
static size_t s_2_arg_validations;
static size_t s_3_arg_validations;
static int s_syscalls[kMaxSyscalls];
static int s_errnos[kMaxSyscalls];
static int s_args_1[kMaxSyscalls];
static int s_vals_1[kMaxSyscalls];
static int s_args_2[kMaxSyscalls];
@ -85,6 +98,26 @@ allow_nr(int nr)
{
bug("negative syscall");
}
s_errnos[s_syscall_index] = 0;
s_syscalls[s_syscall_index++] = nr;
}
static void
reject_nr(int nr, int errcode)
{
if (s_syscall_index >= kMaxSyscalls)
{
bug("out of syscall space");
}
if (nr < 0)
{
bug("negative syscall");
}
if (errcode < 0 || errcode > 255)
{
bug("bad errcode");
}
s_errnos[s_syscall_index] = errcode;
s_syscalls[s_syscall_index++] = nr;
}
@ -105,6 +138,7 @@ allow_nr_1_arg_match(int nr, int arg, int val)
}
s_args_1[s_syscall_index] = arg;
s_vals_1[s_syscall_index] = val;
s_errnos[s_syscall_index] = 0;
s_syscalls[s_syscall_index++] = nr;
s_1_arg_validations++;
}
@ -126,6 +160,7 @@ allow_nr_1_arg_mask(int nr, int arg, int val)
}
s_args_1[s_syscall_index] = 100 + arg;
s_vals_1[s_syscall_index] = val;
s_errnos[s_syscall_index] = 0;
s_syscalls[s_syscall_index++] = nr;
s_1_arg_validations++;
}
@ -153,6 +188,7 @@ allow_nr_2_arg_match(int nr, int arg1, int val1, int arg2, int val2)
s_vals_1[s_syscall_index] = val1;
s_args_2[s_syscall_index] = arg2;
s_vals_2[s_syscall_index] = val2;
s_errnos[s_syscall_index] = 0;
s_syscalls[s_syscall_index++] = nr;
s_2_arg_validations++;
}
@ -180,6 +216,7 @@ allow_nr_2_arg_mask_match(int nr, int arg1, int val1, int arg2, int val2)
s_vals_1[s_syscall_index] = val1;
s_args_2[s_syscall_index] = arg2;
s_vals_2[s_syscall_index] = val2;
s_errnos[s_syscall_index] = 0;
s_syscalls[s_syscall_index++] = nr;
s_2_arg_validations++;
}
@ -214,6 +251,7 @@ allow_nr_3_arg_match(int nr, int arg1, int val1, int arg2, int val2, int arg3,
s_vals_2[s_syscall_index] = val2;
s_args_3[s_syscall_index] = arg3;
s_vals_3[s_syscall_index] = val3;
s_errnos[s_syscall_index] = 0;
s_syscalls[s_syscall_index++] = nr;
s_3_arg_validations++;
}
@ -256,6 +294,7 @@ seccomp_sandbox_setup_base()
3, PROT_READ|PROT_WRITE,
4, MAP_PRIVATE|MAP_ANON);
allow_nr_1_arg_mask(__NR_mprotect, 3, PROT_READ);
allow_nr(__NR_munmap);
allow_nr(__NR_brk);
/* Misc simple low-risk calls. */
@ -402,8 +441,8 @@ seccomp_sandbox_setup_postlogin(const struct vsf_session* p_sess)
if (tunable_text_userdb_names)
{
reject_nr(__NR_socket, EACCES);
allow_nr_2_arg_match(__NR_mmap, 3, PROT_READ, 4, MAP_SHARED);
allow_nr(__NR_munmap);
}
if (tunable_write_enable)
@ -565,8 +604,16 @@ seccomp_sandbox_lockdown()
p_filter->code = BPF_RET+BPF_K;
p_filter->jt = 0;
p_filter->jf = 0;
/* SECCOMP_RET_ALLOW */
p_filter->k = 0x7fff0000;
if (!s_errnos[i])
{
/* SECCOMP_RET_ALLOW */
p_filter->k = 0x7fff0000;
}
else
{
/* SECCOMP_RET_ERRNO */
p_filter->k = 0x00050000 + s_errnos[i];
}
p_filter++;
if (s_args_1[i])
{

View File

@ -80,7 +80,8 @@ vsf_standalone_main(void)
{
struct vsf_sysutil_sockaddr* p_sockaddr = 0;
vsf_sysutil_sockaddr_alloc_ipv4(&p_sockaddr);
vsf_sysutil_sockaddr_set_port(p_sockaddr, tunable_listen_port);
vsf_sysutil_sockaddr_set_port(p_sockaddr,
(unsigned short) tunable_listen_port);
if (!tunable_listen_address)
{
vsf_sysutil_sockaddr_set_any(p_sockaddr);
@ -103,7 +104,8 @@ vsf_standalone_main(void)
{
struct vsf_sysutil_sockaddr* p_sockaddr = 0;
vsf_sysutil_sockaddr_alloc_ipv6(&p_sockaddr);
vsf_sysutil_sockaddr_set_port(p_sockaddr, tunable_listen_port);
vsf_sysutil_sockaddr_set_port(p_sockaddr,
(unsigned short) tunable_listen_port);
if (!tunable_listen_address6)
{
vsf_sysutil_sockaddr_set_any(p_sockaddr);
@ -272,7 +274,7 @@ hash_ip(unsigned int buckets, void* p_key)
unsigned int i;
for (i = 0; i < s_ipaddr_size; ++i)
{
val ^= p_raw_ip[i] << shift;
val = val ^ (unsigned int) (p_raw_ip[i] << shift);
shift -= 8;
if (shift < 0)
{

2
str.c
View File

@ -289,7 +289,7 @@ str_upper(struct mystr* p_str)
unsigned int i;
for (i=0; i < p_str->len; i++)
{
p_str->p_buf[i] = vsf_sysutil_toupper(p_str->p_buf[i]);
p_str->p_buf[i] = (char) vsf_sysutil_toupper(p_str->p_buf[i]);
}
}

View File

@ -22,6 +22,8 @@ struct mystr_list_node
};
/* File locals */
static const unsigned int kMaxStrlist = 10 * 1000 * 1000;
static struct mystr s_null_str;
static int sort_compare_func(const void* p1, const void* p2);
@ -46,7 +48,7 @@ str_list_free(struct mystr_list* p_list)
}
}
int
unsigned int
str_list_get_length(const struct mystr_list* p_list)
{
return p_list->list_len;
@ -78,15 +80,19 @@ str_list_add(struct mystr_list* p_list, const struct mystr* p_str,
if (p_list->alloc_len == 0)
{
p_list->alloc_len = 32;
p_list->p_nodes = vsf_sysutil_malloc(p_list->alloc_len *
sizeof(struct mystr_list_node));
p_list->p_nodes = vsf_sysutil_malloc(
p_list->alloc_len * (unsigned int) sizeof(struct mystr_list_node));
}
else
{
p_list->alloc_len *= 2;
p_list->p_nodes = vsf_sysutil_realloc(p_list->p_nodes,
p_list->alloc_len *
sizeof(struct mystr_list_node));
if (p_list->alloc_len > kMaxStrlist)
{
die("excessive strlist");
}
p_list->p_nodes = vsf_sysutil_realloc(
p_list->p_nodes,
p_list->alloc_len * (unsigned int) sizeof(struct mystr_list_node));
}
}
p_node = &p_list->p_nodes[p_list->list_len];

View File

@ -21,7 +21,7 @@ void str_list_add(struct mystr_list* p_list, const struct mystr* p_str,
const struct mystr* p_sort_key_str);
void str_list_sort(struct mystr_list* p_list, int reverse);
int str_list_get_length(const struct mystr_list* p_list);
unsigned int str_list_get_length(const struct mystr_list* p_list);
int str_list_contains_str(const struct mystr_list* p_list,
const struct mystr* p_str);

View File

@ -322,7 +322,7 @@ vsf_sysdep_check_auth(struct mystr* p_user_str,
const struct mystr* p_pass_str,
const struct mystr* p_remote_host)
{
int retval;
int retval = -1;
pam_item_t item;
const char* pam_user_name = 0;
struct pam_conv the_conv =
@ -335,8 +335,11 @@ vsf_sysdep_check_auth(struct mystr* p_user_str,
bug("vsf_sysdep_check_auth");
}
str_copy(&s_pword_str, p_pass_str);
retval = pam_start(tunable_pam_service_name,
str_getbuf(p_user_str), &the_conv, &s_pamh);
if (tunable_pam_service_name)
{
retval = pam_start(tunable_pam_service_name,
str_getbuf(p_user_str), &the_conv, &s_pamh);
}
if (retval != PAM_SUCCESS)
{
s_pamh = 0;

View File

@ -909,13 +909,13 @@ vsf_sysutil_octal_to_uint(const char* p_str)
int
vsf_sysutil_toupper(int the_char)
{
return toupper(the_char);
return toupper((unsigned char) the_char);
}
int
vsf_sysutil_isspace(int the_char)
{
return isspace(the_char);
return isspace((unsigned char) the_char);
}
int
@ -943,13 +943,13 @@ vsf_sysutil_isprint(int the_char)
int
vsf_sysutil_isalnum(int the_char)
{
return isalnum(the_char);
return isalnum((unsigned char) the_char);
}
int
vsf_sysutil_isdigit(int the_char)
{
return isdigit(the_char);
return isdigit((unsigned char) the_char);
}
char*
@ -2790,7 +2790,7 @@ vsf_sysutil_getuid(void)
}
void
vsf_sysutil_set_address_space_limit(long bytes)
vsf_sysutil_set_address_space_limit(unsigned long bytes)
{
/* Unfortunately, OpenBSD is missing RLIMIT_AS. */
#ifdef RLIMIT_AS

View File

@ -344,7 +344,7 @@ void vsf_sysutil_sleep(double seconds);
int vsf_sysutil_setmodtime(const char* p_file, long the_time, int is_localtime);
/* Limits */
void vsf_sysutil_set_address_space_limit(long bytes);
void vsf_sysutil_set_address_space_limit(unsigned long bytes);
void vsf_sysutil_set_no_fds(void);
void vsf_sysutil_set_no_procs(void);

View File

@ -124,8 +124,12 @@ vsf_two_process_start(struct vsf_session* p_sess)
}
if (tunable_local_enable && tunable_userlist_enable)
{
int retval = str_fileread(&p_sess->userlist_str, tunable_userlist_file,
VSFTP_CONF_FILE_MAX);
int retval = -1;
if (tunable_userlist_file)
{
retval = str_fileread(&p_sess->userlist_str, tunable_userlist_file,
VSFTP_CONF_FILE_MAX);
}
if (vsf_sysutil_retval_is_error(retval))
{
die2("cannot read user list file:", tunable_userlist_file);
@ -144,7 +148,7 @@ drop_all_privs(void)
{
struct mystr user_str = INIT_MYSTR;
struct mystr dir_str = INIT_MYSTR;
int option = VSF_SECUTIL_OPTION_CHROOT | VSF_SECUTIL_OPTION_NO_PROCS;
unsigned int option = VSF_SECUTIL_OPTION_CHROOT | VSF_SECUTIL_OPTION_NO_PROCS;
if (!tunable_ssl_enable)
{
/* Unfortunately, can only enable this if we can be sure of not using SSL.
@ -152,8 +156,14 @@ drop_all_privs(void)
*/
option |= VSF_SECUTIL_OPTION_NO_FDS;
}
str_alloc_text(&user_str, tunable_nopriv_user);
str_alloc_text(&dir_str, tunable_secure_chroot_dir);
if (tunable_nopriv_user)
{
str_alloc_text(&user_str, tunable_nopriv_user);
}
if (tunable_secure_chroot_dir)
{
str_alloc_text(&dir_str, tunable_secure_chroot_dir);
}
/* Be kind: give good error message if the secure dir is missing */
{
struct vsf_sysutil_statbuf* p_statbuf = 0;
@ -315,7 +325,11 @@ process_login_req(struct vsf_session* p_sess)
return;
break;
case kVSFLoginAnon:
str_alloc_text(&p_sess->user_str, tunable_ftp_username);
str_free(&p_sess->user_str);
if (tunable_ftp_username)
{
str_alloc_text(&p_sess->user_str, tunable_ftp_username);
}
common_do_login(p_sess, &p_sess->user_str, 1, 1);
break;
case kVSFLoginReal:
@ -328,9 +342,12 @@ process_login_req(struct vsf_session* p_sess)
if (tunable_chroot_list_enable)
{
struct mystr chroot_list_file = INIT_MYSTR;
int retval = str_fileread(&chroot_list_file,
tunable_chroot_list_file,
VSFTP_CONF_FILE_MAX);
int retval = -1;
if (tunable_chroot_list_file)
{
retval = str_fileread(&chroot_list_file, tunable_chroot_list_file,
VSFTP_CONF_FILE_MAX);
}
if (vsf_sysutil_retval_is_error(retval))
{
die2("could not read chroot() list file:",
@ -413,7 +430,10 @@ common_do_login(struct vsf_session* p_sess, const struct mystr* p_user_str,
{
p_sess->is_guest = 1;
/* Remap to the guest user */
str_alloc_text(&guest_user_str, tunable_guest_username);
if (tunable_guest_username)
{
str_alloc_text(&guest_user_str, tunable_guest_username);
}
p_user_str = &guest_user_str;
if (!tunable_virtual_use_local_privs)
{

View File

@ -26,7 +26,14 @@ die2(const char* p_text1, const char* p_text2)
{
struct mystr die_str = INIT_MYSTR;
str_alloc_text(&die_str, p_text1);
str_append_text(&die_str, p_text2);
if (p_text2)
{
str_append_text(&die_str, p_text2);
}
else
{
str_append_text(&die_str, "(null)");
}
die(str_getbuf(&die_str));
}

View File

@ -1,7 +1,7 @@
#ifndef VSF_VERSION_H
#define VSF_VERSION_H
#define VSF_VERSION "3.0.0"
#define VSF_VERSION "3.0.1"
#endif /* VSF_VERSION_H */