14 if (! -c "/dev/null") {
15 print "1..0 # Skip: no /dev/null\n";
19 my $dev_tty = '/dev/tty';
20 $dev_tty = 'TT:' if ($^O eq 'VMS');
22 print "1..0 # Skip: no $dev_tty\n";
26 print "1..0 # Skip: \$ENV{PERL5DB} is already set to '$ENV{PERL5DB}'\n";
33 my $rc_filename = '.perldb';
36 open my $rc_fh, '>', $rc_filename
41 # overly permissive perms gives "Must not source insecure rcfile"
42 # and hangs at the DB(1> prompt
43 chmod 0644, $rc_filename;
50 open my $in, '<', $filename
51 or die "Cannot open '$filename' for slurping - $!";
61 my $out_fn = 'db.out';
65 return _slurp($out_fn);
69 my $target = '../lib/perl5db/t/eval-line-bug';
73 &parse_options("NonStop=0 TTY=db.out LineInfo=db.out");
83 "p \\\@{'main::_<$target'}",
91 local $ENV{PERLDB_OPTS} = "ReadLine=0";
92 runperl(switches => [ '-d' ], progfile => $target);
96 like(_out_contents(), qr/sub factorial/,
97 'The ${main::_<filename} variable in the debugger was not destroyed'
101 my $target = '../lib/perl5db/t/eval-line-bug';
105 &parse_options("NonStop=0 TTY=db.out LineInfo=db.out");
108 push(\@DB::typeahead,
112 'x "new_var = <\$new_var>\\n";',
120 local $ENV{PERLDB_OPTS} = "ReadLine=0";
121 runperl(switches => [ '-d' ], progfile => $target);
125 like(_out_contents(), qr/new_var = <Foo>/,
126 "no strict 'vars' in evaluated lines.",
130 local $ENV{PERLDB_OPTS} = "ReadLine=0";
131 my $output = runperl(switches => [ '-d' ], progfile => '../lib/perl5db/t/lvalue-bug');
132 like($output, qr/foo is defined/, 'lvalue subs work in the debugger');
136 local $ENV{PERLDB_OPTS} = "ReadLine=0 NonStop=1";
137 my $output = runperl(switches => [ '-d' ], progfile => '../lib/perl5db/t/symbol-table-bug');
138 like($output, qr/Undefined symbols 0/, 'there are no undefined values in the symbol table');
142 if ( $Config{usethreads} ) {
143 skip('This perl has threads, skipping non-threaded debugger tests');
145 my $error = 'This Perl not built to support threads';
146 my $output = runperl( switches => [ '-dt' ], stderr => 1 );
147 like($output, qr/$error/, 'Perl debugger correctly complains that it was not built with threads');
152 if ( $Config{usethreads} ) {
153 local $ENV{PERLDB_OPTS} = "ReadLine=0 NonStop=1";
154 my $output = runperl(switches => [ '-dt' ], progfile => '../lib/perl5db/t/symbol-table-bug');
155 like($output, qr/Undefined symbols 0/, 'there are no undefined values in the symbol table when running with thread support');
157 skip("This perl is not threaded, skipping threaded debugger tests");
164 local $ENV{PERLDB_OPTS};
167 &parse_options("NonStop=0 TTY=db.out LineInfo=db.out");
178 my $output = runperl(switches => [ '-d' ], stderr => 1, progfile => '../lib/perl5db/t/rt-61222');
179 unlike(_out_contents(), qr/INCORRECT/, "[perl #61222]");
184 # Test for Proxy constants
189 &parse_options("NonStop=0 ReadLine=0 TTY=db.out LineInfo=db.out");
201 my $output = runperl(switches => [ '-d' ], stderr => 1, progfile => '../lib/perl5db/t/proxy-constants');
202 is($output, "", "proxy constant subroutines");
205 # [perl #66110] Call a subroutine inside a regex
207 local $ENV{PERLDB_OPTS} = "ReadLine=0 NonStop=1";
208 my $output = runperl(switches => [ '-d' ], stderr => 1, progfile => '../lib/perl5db/t/rt-66110');
209 like($output, "All tests successful.", "[perl #66110]");
212 # [perl 104168] level option for tracing
215 &parse_options("NonStop=0 TTY=db.out LineInfo=db.out");
218 push (@DB::typeahead,
227 my $output = runperl(switches => [ '-d' ], stderr => 1, progfile => '../lib/perl5db/t/rt-104168');
228 my $contents = _out_contents();
229 like($contents, qr/level 2/, "[perl #104168]");
230 unlike($contents, qr/baz/, "[perl #104168]");
236 local $ENV{PERLDB_OPTS} = "ReadLine=0 NonStop=1";
237 my $output = runperl(switches => [ '-d', '-T' ], stderr => 1,
238 progfile => '../lib/perl5db/t/taint');
239 chomp $output if $^O eq 'VMS'; # newline guaranteed at EOF
240 is($output, '[$^X][done]', "taint");
248 my $self = bless {}, $class;
259 $self->{_cmds} = shift;
262 return $self->{_cmds};
269 $self->{_prog} = shift;
272 return $self->{_prog};
279 $self->{_output} = shift;
282 return $self->{_output};
291 $self->{_include_t} = shift;
294 return $self->{_include_t};
303 $self->{_contents} = shift;
306 return $self->{_contents};
311 my ($self, $args) = @_;
313 my $cmds = $args->{cmds};
315 if (ref($cmds) ne 'ARRAY') {
316 die "cmds must be an array of commands.";
321 my $prog = $args->{prog};
323 if (ref($prog) ne '' or !defined($prog)) {
324 die "prog should be a path to a program file.";
329 $self->_include_t($args->{include_t} ? 1 : 0);
338 my ($self, $str) = @_;
340 $str =~ s/(["\@\$\\])/\\$1/g;
350 my $rc = qq{&parse_options("NonStop=0 TTY=db.out LineInfo=db.out");\n};
355 q#push (@DB::typeahead,#,
356 (map { $self->_quote($_) . "," } @{$self->_cmds()}),
362 # I guess two objects like that cannot be used at the same time.
371 ($self->_include_t ? ('-I', '../lib/perl5db/t') : ())
374 progfile => $self->_prog()
377 $self->_output($output);
379 $self->_contents(::_out_contents());
385 my ($self, $re, $msg) = @_;
387 local $::Level = $::Level + 1;
388 ::like($self->_output(), $re, $msg);
392 my ($self, $re, $msg) = @_;
394 local $::Level = $::Level + 1;
395 ::like($self->_contents(), $re, $msg);
400 # Testing that we can set a line in the middle of the file.
402 my $wrapper = DebugWrap->new(
406 'b ../lib/perl5db/t/MyModule.pm:12',
408 q/do { use IO::Handle; STDOUT->autoflush(1); print "Var=$var\n"; }/,
413 prog => '../lib/perl5db/t/filename-line-breakpoint'
417 $wrapper->output_like(qr/
425 "Can set breakpoint in a line in the middle of the file.");
428 # Testing that we can set a breakpoint
430 my $wrapper = DebugWrap->new(
432 prog => '../lib/perl5db/t/breakpoint-bug',
437 q/do { use IO::Handle; STDOUT->autoflush(1); print "X={$x}\n"; }/,
444 $wrapper->output_like(
446 "Can set breakpoint in a line."
450 # Testing that we can disable a breakpoint at a numeric line.
452 my $wrapper = DebugWrap->new(
454 prog => '../lib/perl5db/t/disable-breakpoints-1',
461 q/print "X={$x}\n";/,
468 $wrapper->output_like(qr/X=\{SecondVal\}/ms,
469 "Can set breakpoint in a line.");
472 # Testing that we can re-enable a breakpoint at a numeric line.
474 my $wrapper = DebugWrap->new(
476 prog => '../lib/perl5db/t/disable-breakpoints-2',
485 q/print "X={$x}\n";/,
492 $wrapper->output_like(
494 X=\{SecondValOneHundred\}
496 "Can set breakpoint in a line."
501 # Disable and enable for breakpoints on outer files.
503 my $wrapper = DebugWrap->new(
508 'b ../lib/perl5db/t/EnableModule.pm:14',
509 'disable ../lib/perl5db/t/EnableModule.pm:14',
511 'enable ../lib/perl5db/t/EnableModule.pm:14',
513 q/print "X={$x}\n";/,
517 prog => '../lib/perl5db/t/disable-breakpoints-3',
522 $wrapper->output_like(qr/
523 X=\{SecondValTwoHundred\}
525 "Can set breakpoint in a line.");
528 # Testing that the prompt with the information appears.
530 my $wrapper = DebugWrap->new(
533 prog => '../lib/perl5db/t/disable-breakpoints-1',
537 $wrapper->contents_like(qr/
538 ^main::\([^\)]*\bdisable-breakpoints-1:2\):\n
539 2:\s+my\ \$x\ =\ "One";\n
541 "Prompt should display the first line of code.");
544 # Testing that R (restart) and "B *" work.
546 my $wrapper = DebugWrap->new(
556 q/print "X={$x};dummy={$dummy}\n";/,
559 prog => '../lib/perl5db/t/disable-breakpoints-1',
563 $wrapper->output_like(qr/
564 X=\{FirstVal\};dummy=\{1\}
566 "Restart and delete all breakpoints work properly.");
570 my $wrapper = DebugWrap->new(
575 q/print "X={$x}\n";/,
579 prog => '../lib/perl5db/t/disable-breakpoints-1',
583 $wrapper->output_like(qr/
586 "'c line_num' is working properly.");
590 my $wrapper = DebugWrap->new(
598 q/print "Exp={$exp}\n";/,
601 prog => '../lib/perl5db/t/break-on-dot',
605 $wrapper->output_like(qr/
608 "'b .' is working correctly.");
611 # Testing that the prompt with the information appears inside a subroutine call.
612 # See https://rt.perl.org/rt3/Ticket/Display.html?id=104820
614 my $wrapper = DebugWrap->new(
621 prog => '../lib/perl5db/t/with-subroutine',
625 $wrapper->contents_like(
627 ^main::back\([^\)\n]*\bwith-subroutine:15\):[\ \t]*\n
628 ^15:\s*print\ "hello\ back\\n";
630 "Prompt should display the line of code inside a subroutine.");
633 # Checking that the p command works.
635 my $wrapper = DebugWrap->new(
639 'p "<<<" . (4*6) . ">>>"',
642 prog => '../lib/perl5db/t/with-subroutine',
646 $wrapper->contents_like(
653 my $wrapper = DebugWrap->new(
660 prog => '../lib/perl5db/t/with-subroutine',
664 $wrapper->contents_like(
665 # qr/^0\s+HASH\([^\)]+\)\n\s+500 => 600\n/,
666 qr/^0\s+HASH\([^\)]+\)\n\s+500 => 600\n/ms,
671 # Tests for "T" (stack trace).
673 my $prog_fn = '../lib/perl5db/t/rt-104168';
674 my $wrapper = DebugWrap->new(
685 my $re_text = join('',
688 "%s = %s\\(\\) called from file " .
689 "'" . quotemeta($prog_fn) . "' line %s\\n",
690 (map { quotemeta($_) } @$_)
694 ['.', 'main::baz', 14,],
695 ['.', 'main::bar', 9,],
696 ['.', 'main::foo', 6]
699 $wrapper->contents_like(
700 # qr/^0\s+HASH\([^\)]+\)\n\s+500 => 600\n/,
708 my $wrapper = DebugWrap->new(
715 q/print "X={$x};dummy={$dummy}\n";/,
718 prog => '../lib/perl5db/t/disable-breakpoints-1'
722 $wrapper->output_like(qr/
723 X=\{SecondVal\};dummy=\{1\}
725 'test for s - single step',
730 my $wrapper = DebugWrap->new(
738 q/print "Exp={$exp}\n";/,
741 prog => '../lib/perl5db/t/break-on-dot'
745 $wrapper->output_like(qr/
748 "'b .' is working correctly.");
752 my $prog_fn = '../lib/perl5db/t/rt-104168';
753 my $wrapper = DebugWrap->new(
764 $wrapper->contents_like(
766 ^main::foo\([^\)\n]*\brt-104168:9\):[\ \t]*\n
769 'Test for the s command.',
774 my $wrapper = DebugWrap->new(
778 's uncalled_subroutine()',
783 prog => '../lib/perl5db/t/uncalled-subroutine'}
786 $wrapper->output_like(
788 'uncalled_subroutine was called after s EXPR()',
793 my $wrapper = DebugWrap->new(
797 'n uncalled_subroutine()',
801 prog => '../lib/perl5db/t/uncalled-subroutine',
805 $wrapper->output_like(
807 'uncalled_subroutine was called after n EXPR()',
812 my $wrapper = DebugWrap->new(
824 prog => '../lib/perl5db/t/fact',
828 $wrapper->output_like(
830 'b subroutine works fine',
834 # Test for 'M' (module list).
836 my $wrapper = DebugWrap->new(
843 prog => '../lib/perl5db/t/load-modules'
847 $wrapper->contents_like(
849 'M (module list) works fine',
854 my $wrapper = DebugWrap->new(
862 'print "Var=$var\n";',
865 prog => '../lib/perl5db/t/test-r-statement',
869 $wrapper->output_like(
877 'r statement is working properly.',
882 my $wrapper = DebugWrap->new(
889 prog => '../lib/perl5db/t/test-l-statement-1',
893 $wrapper->contents_like(
896 2:\s+print\ "1\\n";\n
899 5:\s+print\ "2\\n";\n
901 'l statement is working properly (test No. 1).',
906 1 while unlink ($rc_filename, $out_fn);