Beefy Boxes and Bandwidth Generously Provided by pair Networks
Problems? Is your data what you think it is?

Re (tilly) 1: is I/O checking worth it?

by tilly (Archbishop)
on Jan 14, 2001 at 05:14 UTC ( #51669=note: print w/replies, xml ) Need Help??

in reply to is I/O checking worth it?

The first step if security matters is to read perlsec and then turn on taint checking.

A good step regardless is to have every open test what you did. I believe in doing it like perlstyle says and having the error message include the filename, attempted operation, and $!.

If you need to read and write files but don't want to follow symlinks, this can get fairly tricky. The following code (which will fail horribly on systems without symlinks) demonstrates how to do it safely:

#! /usr/bin/perl -w use strict; use Carp; use Symbol; # Needed on 5.005 and less sub clear_file { my ($fh, $name) = @_; seek($fh, 0, 0) or confess("Cannot seek to beginning of '$name': $!" +); truncate($fh, 0) or confess("Cannot truncate '$name': $!"); } sub deny_symlink { my ($fh, $name) = @_; # In the following testing the filehandle avoids a race # condition, but I think that whether it works is OS # specific. :-( if (-l $fh or -l $name) { my $real = readlink($name); confess("Refusing to follow symlink from $name to $real"); } } sub open_read { my $name = shift; my $fh = gensym(); open($fh, "< $name") or confess("Cannot read '$name': $!"); deny_symlink($fh, $name); return $fh; } sub open_write { my $name = shift; my $fh = gensym(); open ($fh, "+>> $name") or confess("Cannot write '$name': $!"); deny_symlink($fh, $name); clear_file($fh, $name); return $fh; } my $filename = "whatever"; *FH = open_write($filename); print FH "Hello world\n"; close FH; *FH = open_read($filename); print <FH>;
In general if you need temporary files, do not attempt to roll that yourself. Use File::Temp. Really.

Also note that if you are concerned with security then you may want to think about locking. For an example (which could easily be improved) that I came up with a while ago see Simple Locking.

With luck this should give you some ideas of how to improve the security of your programs.

Replies are listed 'Best First'.
Re: Re (tilly) 1: is I/O checking worth it?
by Beatnik (Parson) on Jan 14, 2001 at 16:40 UTC
    I usually do alot of checking on more critical file I/O, instead of blindly opening, and I once so often even do a forced check on file permissions (which ofcourse will break the script on platforms that don't support it).
    Locking will only work on processes that understand the concept. If applications don't obey file locking, they can do whatever they want with the files. Perl, ofcourse, obeys the locking.
    Not all OSs have flock implemented, good example: Windows (not that I use it). flock will actually break your script if it's run on a platform that doesn't support it.
    What about the file versus dir check? A file can be opened, a dir can't (in a file meaning). Will -d suffice enough? =)
      Actually locks on Unix are only advisary, and while Perl scripts may obey them, it depends on the script writer properly calling flock.

      As for the rest, generally it is a far sounder strategy to open in a non-destructive manner, then test. Testing first opens up race conditions.

      Beyond that putting in a ton of paranoid checks tends to create unmanageable messes. The harder you make security, the less likely it is to happen. Make it easy to be secure (eg through a small number of functions like I wrote above) and think about how it fits in your overall policy. (I might work as a non-privileged user in directory structures whose permissions are locked down to just that user, then leave it at that. If I want to put a symlink in there, that is probably OK.)

      In general make sure that things are sane, you have programmed in a way where unexpected inputs cannot be misunderstood, and make it simple to maintain that. But if (and without seeing what you do I have no idea whether this applies in your case) you set up a complex scheme that is supposed to be followed, you have set yourself up for failure. Complex schemes tend to erode security.

Log In?

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: note [id://51669]
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others cooling their heels in the Monastery: (4)
As of 2022-12-02 04:07 GMT
Find Nodes?
    Voting Booth?