read is not guaranteed to read the number of bytes you specify, especially when dealing with handles which aren't tied to files. I also added error handling and made the buffer size configurable.
use constant BLK_SIZE => 16*1024; sub pseek { my( $p, $to_read, $blk_size ) = @_; $blk_size ||= BLK_SIZE; while ( $to_read ) { $blk_size = $to_read if $to_read < $blk_size; my $read = read( $p, my $discard, $blk_size ); return $read if !$read; $to_read -= $read; } return 1; }
Update: Or maybe not. My testing shows that read does wait, but its documentation uses the same wording as sysread which does not. As such, I wouldn't count on the observed bahviour.
$ perl -e'$|=1; print "a"; sleep(10); print "b"' | perl -le'read(STDIN +, $buf, 10); print $buf' ab $ perl -e'$|=1; print "a"; sleep(10); print "b"' | perl -le'sysread(ST +DIN, $buf, 10); print $buf' a
Same results on linux and Windows.
In reply to Re^2: seek() functionality on pipes
by ikegami
in thread seek() functionality on pipes
by HKS
| For: | Use: | ||
| & | & | ||
| < | < | ||
| > | > | ||
| [ | [ | ||
| ] | ] |