Beefy Boxes and Bandwidth Generously Provided by pair Networks
P is for Practical
 
PerlMonks  

Debug openings and closings

by senduran (Novice)
on Aug 27, 2007 at 07:49 UTC ( [id://635231]=perlquestion: print w/replies, xml ) Need Help??

senduran has asked for the wisdom of the Perl Monks concerning the following question:

I have a complicated script that uses many modules and runs for many minutes before dieing with a 'Too many open files' problem.

I don't want to step through it all with the debugger... Is there some simple way I can just see the stack trace every time something does an open(), and everytime something does a close(), to find the culprit that isn't closing when it should?

Replies are listed 'Best First'.
Re: Debug openings and closings
by FunkyMonk (Chancellor) on Aug 27, 2007 at 08:38 UTC
    You can override CORE::open and close. The following should get you going:

    BEGIN { *CORE::GLOBAL::open = \&my_open; sub my_open(*;$@) { my ( undef, $filename, $line ) = caller; print "opening $_[2] in $filename:$line\n"; CORE::open($_[0], $_[1], $_[2]); } } open my $fh, "<", "temp~" or die $!;

    Googling came up with Testing Legacy Code

Re: Debug openings and closings
by moritz (Cardinal) on Aug 27, 2007 at 08:26 UTC
    On linux and unix based systems you can use the command (not perl function!) strace to watch which files are opened and closed.

    On windows you can use filemon for that.

    I know that's not exactly what you want, but maybe when you see which files are opened you can guess which module is to blame.

      Actually on Linuxen it's strace, on Solaris (and other SysVs?) it's truss (as Anno mentions below), and on BSDen it's a pair of utilities ktrace and kdump (Free- and OS X for sure, pretty sure about Open-).</pedant>

Re: Debug openings and closings
by bruceb3 (Pilgrim) on Aug 27, 2007 at 09:11 UTC
    As a suggestion to avoid this kind of problem, if you use a lexical variable as a file handle instead of a bareword, when the variable goes out of scope, Perl will automatically close the file for you. e.g.
    open my $file, "<", $filename # use lexical variable open FILE, "<", $filename # use bareword.

    So if you have a subroutine;
    sub foo { my ($filename) = @_; open my $file, "<", $filename or die "blah :$!\n"; while (<$file>) { # etc } # explicit call to close not needed. }
    The file will be closed at the end of the foo subroutine. If you want the file handle then return it.
    And if you aren't using a lot of subroutines but want this behavior, simply start a new block.
Re: Debug openings and closings
by BrowserUk (Patriarch) on Aug 27, 2007 at 08:46 UTC
Re: Debug openings and closings
by Anno (Deacon) on Aug 27, 2007 at 08:38 UTC
    On most Unix systems you can trace system calls (that includes open() and close()) using something like strace (truss in other systems).

    Anno

Re: Debug openings and closings
by ides (Deacon) on Aug 27, 2007 at 14:10 UTC

    Definitely find out why you're running out of file handles, but if you find at the end of the day it is necessary, you can up these limits on your Linux/Unix system. Googling around for ulimit and that error message should help you to find how to do that on your particular OS.

    Frank Wiles <frank@revsys.com>
    www.revsys.com

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://635231]
Approved by Corion
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others imbibing at the Monastery: (6)
As of 2024-04-20 02:34 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found