blogs-debugging-article1.pod 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106
  1. The nature of the data driven perl compiler is hitting the perl
  2. debuggers recursion limit, even on one-liners.
  3. Consider this bug: <a href="https://rt.cpan.org/Ticket/Display.html?id=53889"><em>[CPAN #53889]</em></a>
  4. <pre>
  5. package dummy;sub meth{print "ok"};package main;dummy->meth
  6. =>
  7. ok
  8. </pre>
  9. The compiler does not detect the meth sub in the dummy package.
  10. <pre>
  11. $ perl -MO=C,-DcOACMSGpo,-v,-oa.c -e 'package dummy;
  12. sub meth{print "ok"};package main;dummy->meth'
  13. $ cc_harness a.c
  14. $ ./a
  15. </pre>
  16. Can't locate object method "meth" via package "dummy" (perhaps you forgot to load "dummy"?) at -e line 1.
  17. <em>BTW: Easier tested in the distro with
  18. <pre>$ <b>t/testc.sh 35</b></pre>
  19. </em>
  20. First if you don't see the error in the generated c file, always turn on all debugging options and save it into a log file.
  21. $ perl -Mblib -MO=C,-DcOACMSGpoW,-v,-occode35.c ccode35.pl 2>&1 | tee methodcall.log
  22. "-DcOACMSGpoW,-v" is all debugging info you get.
  23. Now let's debug it.
  24. <pre>
  25. $ cpan B::Debugger
  26. $ perl -Mblib <strong>-d -MOd</strong>=C,-DcOACMSGpo,-v -e 'package dummy;sub meth{print "ok"};package main;dummy->meth'
  27. </pre>
  28. The code in question is in &should_save.
  29. <pre>
  30. Od::CODE(0x1870d30)((eval 9)[/cygdrive/f/prog/Perl/B-C/blib/lib/Od.pm:12]:11):
  31. 11: &$compile();
  32. DB<1> <strong>s</strong>
  33. B::C::CODE(0x1453910)(/cygdrive/f/prog/Perl/B-C/blib/lib/B/C.pm:3295):
  34. 3295: return sub { save_main() };
  35. DB<1> <strong>s</strong>
  36. B::C::save_main(/cygdrive/f/prog/Perl/B-C/blib/lib/B/C.pm:3005):
  37. 3005: my $warner = $SIG{__WARN__};
  38. DB<1> <strong>c should_save</strong>
  39. Debugged program terminated. Use q to quit or R to restart,
  40. use o inhibit_exit to avoid stopping after program termination,
  41. h q, h R or h o to get additional info.
  42. </pre>
  43. Oops. Not stopping there. Od is not perfect yet.
  44. Next attempt with line number.
  45. <pre>
  46. <strong>s
  47. s
  48. b 2908</strong>
  49. B::C::should_save(/cygdrive/f/prog/Perl/B-C/blib/lib/B/C.pm:2908):
  50. 2908: foreach my $m (qw(new DESTROY TIESCALAR TIEARRAY TIEHASH TIEHANDLE)) {
  51. </pre>
  52. better attempt. <br>
  53. we are enhancing the recursion limit (deep) from 100 to 500,
  54. and set a conditional breakpoint which only breaks when considering the "dummy" package
  55. <pre>
  56. <strong>x $DB::deep = 500
  57. b 2908 $package eq 'dummy'
  58. c
  59. x \%unused_sub_packages</strong>
  60. </pre>
  61. and so on. This is pretty deep in the symbol walker, which tries to detect all possible used subs in possible used packages. Undetected packages will cause such errors,
  62. <pre>Can't locate object method "meth" via package "dummy" (perhaps you forgot to load "dummy"?) at -e line 1.</pre>
  63. Lets continue:
  64. <pre>
  65. DB<2> <strong>n</strong>
  66. 2915: delete_unsaved_hashINC($package);
  67. DB<2>
  68. 2916: return $unused_sub_packages{$package} = 0;
  69. DB<2>
  70. 2959: walkpackages( \%{"main::"}, sub { should_save( $_[0] ); return 1 } );
  71. DB<2> <strong>s</strong>
  72. 2942: walkpackages( \%glob, $recurse, $sym );
  73. DB<3> <strong>x \%glob</strong>
  74. 0 HASH(0x14ab450)
  75. 'DESTROY' => *dummy::DESTROY
  76. 'TIEARRAY' => *dummy::TIEARRAY
  77. 'TIEHANDLE' => *dummy::TIEHANDLE
  78. 'TIEHASH' => *dummy::TIEHASH
  79. 'TIESCALAR' => *dummy::TIESCALAR
  80. 'meth' => *dummy::meth
  81. 'new' => *dummy::new
  82. </pre>
  83. Aha, the meth symbol is there. The error is probably somewhere else in the method_named() op.
  84. To be continued at <a href="http://blogs.perl.org/users/rurban/2010/01/debugging-bc-gdb-into-it-part-2.html">part 2 Debugging B::C, gdb into it</a>.