1package ProFTPD::Tests::Config::RLimitMemory; 2 3use lib qw(t/lib); 4use base qw(ProFTPD::TestSuite::Child); 5use strict; 6 7use File::Spec; 8use IO::Handle; 9 10use ProFTPD::TestSuite::FTP; 11use ProFTPD::TestSuite::Utils qw(:auth :config :running :test :testsuite); 12 13$| = 1; 14 15my $order = 0; 16 17my $TESTS = { 18 rlimitmemory_max_bug3571 => { 19 order => ++$order, 20 test_class => [qw(bug forking)], 21 }, 22 23 rlimitmemory_session_max_bug3571 => { 24 order => ++$order, 25 test_class => [qw(bug forking)], 26 }, 27 28 rlimitmemory_daemon_max => { 29 order => ++$order, 30 test_class => [qw(bug forking)], 31 }, 32 33}; 34 35sub new { 36 return shift()->SUPER::new(@_); 37} 38 39sub list_tests { 40 return testsuite_get_runnable_tests($TESTS); 41} 42 43sub rlimitmemory_max_bug3571 { 44 my $self = shift; 45 my $tmpdir = $self->{tmpdir}; 46 47 my $config_file = "$tmpdir/config.conf"; 48 my $pid_file = File::Spec->rel2abs("$tmpdir/config.pid"); 49 my $scoreboard_file = File::Spec->rel2abs("$tmpdir/config.scoreboard"); 50 51 my $log_file = test_get_logfile(); 52 53 my $auth_user_file = File::Spec->rel2abs("$tmpdir/config.passwd"); 54 my $auth_group_file = File::Spec->rel2abs("$tmpdir/config.group"); 55 56 my $user = 'proftpd'; 57 my $passwd = 'test'; 58 my $group = 'ftpd'; 59 my $home_dir = File::Spec->rel2abs($tmpdir); 60 my $uid = 500; 61 my $gid = 500; 62 63 # Make sure that, if we're running as root, that the home directory has 64 # permissions/privs set for the account we create 65 if ($< == 0) { 66 unless (chmod(0755, $home_dir)) { 67 die("Can't set perms on $home_dir to 0755: $!"); 68 } 69 70 unless (chown($uid, $gid, $home_dir)) { 71 die("Can't set owner of $home_dir to $uid/$gid: $!"); 72 } 73 } 74 75 auth_user_write($auth_user_file, $user, $passwd, $uid, $gid, $home_dir, 76 '/bin/bash'); 77 auth_group_write($auth_group_file, $group, $gid, $user); 78 79 my $config = { 80 PidFile => $pid_file, 81 ScoreboardFile => $scoreboard_file, 82 SystemLog => $log_file, 83 84 AuthUserFile => $auth_user_file, 85 AuthGroupFile => $auth_group_file, 86 87 RLimitMemory => 'max', 88 89 IfModules => { 90 'mod_delay.c' => { 91 DelayEngine => 'off', 92 }, 93 }, 94 }; 95 96 my ($port, $config_user, $config_group) = config_write($config_file, $config); 97 98 # Open pipes, for use between the parent and child processes. Specifically, 99 # the child will indicate when it's done with its test by writing a message 100 # to the parent. 101 my ($rfh, $wfh); 102 unless (pipe($rfh, $wfh)) { 103 die("Can't open pipe: $!"); 104 } 105 106 my $ex; 107 108 # Fork child 109 $self->handle_sigchld(); 110 defined(my $pid = fork()) or die("Can't fork: $!"); 111 if ($pid) { 112 eval { 113 my $client = ProFTPD::TestSuite::FTP->new('127.0.0.1', $port); 114 $client->login($user, $passwd); 115 $client->quit(); 116 }; 117 118 if ($@) { 119 $ex = $@; 120 } 121 122 $wfh->print("done\n"); 123 $wfh->flush(); 124 125 } else { 126 eval { server_wait($config_file, $rfh) }; 127 if ($@) { 128 warn($@); 129 exit 1; 130 } 131 132 exit 0; 133 } 134 135 # Stop server 136 server_stop($pid_file); 137 138 $self->assert_child_ok($pid); 139 140 if ($ex) { 141 test_append_logfile($log_file, $ex); 142 unlink($log_file); 143 144 die($ex); 145 } 146 147 unlink($log_file); 148} 149 150sub rlimitmemory_session_max_bug3571 { 151 my $self = shift; 152 my $tmpdir = $self->{tmpdir}; 153 154 my $config_file = "$tmpdir/config.conf"; 155 my $pid_file = File::Spec->rel2abs("$tmpdir/config.pid"); 156 my $scoreboard_file = File::Spec->rel2abs("$tmpdir/config.scoreboard"); 157 158 my $log_file = test_get_logfile(); 159 160 my $auth_user_file = File::Spec->rel2abs("$tmpdir/config.passwd"); 161 my $auth_group_file = File::Spec->rel2abs("$tmpdir/config.group"); 162 163 my $user = 'proftpd'; 164 my $passwd = 'test'; 165 my $group = 'ftpd'; 166 my $home_dir = File::Spec->rel2abs($tmpdir); 167 my $uid = 500; 168 my $gid = 500; 169 170 # Make sure that, if we're running as root, that the home directory has 171 # permissions/privs set for the account we create 172 if ($< == 0) { 173 unless (chmod(0755, $home_dir)) { 174 die("Can't set perms on $home_dir to 0755: $!"); 175 } 176 177 unless (chown($uid, $gid, $home_dir)) { 178 die("Can't set owner of $home_dir to $uid/$gid: $!"); 179 } 180 } 181 182 auth_user_write($auth_user_file, $user, $passwd, $uid, $gid, $home_dir, 183 '/bin/bash'); 184 auth_group_write($auth_group_file, $group, $gid, $user); 185 186 my $config = { 187 PidFile => $pid_file, 188 ScoreboardFile => $scoreboard_file, 189 SystemLog => $log_file, 190 191 AuthUserFile => $auth_user_file, 192 AuthGroupFile => $auth_group_file, 193 194 RLimitMemory => 'session max', 195 196 IfModules => { 197 'mod_delay.c' => { 198 DelayEngine => 'off', 199 }, 200 }, 201 }; 202 203 my ($port, $config_user, $config_group) = config_write($config_file, $config); 204 205 # Open pipes, for use between the parent and child processes. Specifically, 206 # the child will indicate when it's done with its test by writing a message 207 # to the parent. 208 my ($rfh, $wfh); 209 unless (pipe($rfh, $wfh)) { 210 die("Can't open pipe: $!"); 211 } 212 213 my $ex; 214 215 # Fork child 216 $self->handle_sigchld(); 217 defined(my $pid = fork()) or die("Can't fork: $!"); 218 if ($pid) { 219 eval { 220 my $client = ProFTPD::TestSuite::FTP->new('127.0.0.1', $port); 221 $client->login($user, $passwd); 222 $client->quit(); 223 }; 224 225 if ($@) { 226 $ex = $@; 227 } 228 229 $wfh->print("done\n"); 230 $wfh->flush(); 231 232 } else { 233 eval { server_wait($config_file, $rfh) }; 234 if ($@) { 235 warn($@); 236 exit 1; 237 } 238 239 exit 0; 240 } 241 242 # Stop server 243 server_stop($pid_file); 244 245 $self->assert_child_ok($pid); 246 247 if ($ex) { 248 test_append_logfile($log_file, $ex); 249 unlink($log_file); 250 251 die($ex); 252 } 253 254 unlink($log_file); 255} 256 257sub rlimitmemory_daemon_max { 258 my $self = shift; 259 my $tmpdir = $self->{tmpdir}; 260 261 my $config_file = "$tmpdir/config.conf"; 262 my $pid_file = File::Spec->rel2abs("$tmpdir/config.pid"); 263 my $scoreboard_file = File::Spec->rel2abs("$tmpdir/config.scoreboard"); 264 265 my $log_file = test_get_logfile(); 266 267 my $auth_user_file = File::Spec->rel2abs("$tmpdir/config.passwd"); 268 my $auth_group_file = File::Spec->rel2abs("$tmpdir/config.group"); 269 270 my $user = 'proftpd'; 271 my $passwd = 'test'; 272 my $group = 'ftpd'; 273 my $home_dir = File::Spec->rel2abs($tmpdir); 274 my $uid = 500; 275 my $gid = 500; 276 277 # Make sure that, if we're running as root, that the home directory has 278 # permissions/privs set for the account we create 279 if ($< == 0) { 280 unless (chmod(0755, $home_dir)) { 281 die("Can't set perms on $home_dir to 0755: $!"); 282 } 283 284 unless (chown($uid, $gid, $home_dir)) { 285 die("Can't set owner of $home_dir to $uid/$gid: $!"); 286 } 287 } 288 289 auth_user_write($auth_user_file, $user, $passwd, $uid, $gid, $home_dir, 290 '/bin/bash'); 291 auth_group_write($auth_group_file, $group, $gid, $user); 292 293 my $config = { 294 PidFile => $pid_file, 295 ScoreboardFile => $scoreboard_file, 296 SystemLog => $log_file, 297 298 AuthUserFile => $auth_user_file, 299 AuthGroupFile => $auth_group_file, 300 301 RLimitMemory => 'daemon max', 302 303 IfModules => { 304 'mod_delay.c' => { 305 DelayEngine => 'off', 306 }, 307 }, 308 }; 309 310 my ($port, $config_user, $config_group) = config_write($config_file, $config); 311 312 # Open pipes, for use between the parent and child processes. Specifically, 313 # the child will indicate when it's done with its test by writing a message 314 # to the parent. 315 my ($rfh, $wfh); 316 unless (pipe($rfh, $wfh)) { 317 die("Can't open pipe: $!"); 318 } 319 320 my $ex; 321 322 # Fork child 323 $self->handle_sigchld(); 324 defined(my $pid = fork()) or die("Can't fork: $!"); 325 if ($pid) { 326 eval { 327 my $client = ProFTPD::TestSuite::FTP->new('127.0.0.1', $port); 328 $client->login($user, $passwd); 329 $client->quit(); 330 }; 331 332 if ($@) { 333 $ex = $@; 334 } 335 336 $wfh->print("done\n"); 337 $wfh->flush(); 338 339 } else { 340 eval { server_wait($config_file, $rfh) }; 341 if ($@) { 342 warn($@); 343 exit 1; 344 } 345 346 exit 0; 347 } 348 349 # Stop server 350 server_stop($pid_file); 351 352 $self->assert_child_ok($pid); 353 354 if ($ex) { 355 test_append_logfile($log_file, $ex); 356 unlink($log_file); 357 358 die($ex); 359 } 360 361 unlink($log_file); 362} 363 3641; 365