Skip to content

SeekEof fails on pipelines, FIFOs and sockets (quick fix attached)

Original Reporter info from Mantis: croco
  • Reporter name: Andrey "Croco" Stolyarov

Description:

SeekEof detects unseekable streams incorrectly, tries to call do_seek on unseekable streams and doesn't check nor handle for its failure, so it fails to work on pipelines, FIFOs and sockets (but still works on terminals and disk files).

Details are posted on the forum: https://forum.lazarus.freepascal.org/index.php/topic,51353.0.html

Steps to reproduce:

The simple program that counts the sum of numbers read from stdin (up to EOF)

program SimpleSum;
var
    sum, count, n: longint;
begin
    sum := 0;
    count := 0;
    while not SeekEof do
    begin
        read(n);
        sum := sum + n;
        count := count + 1
    end;
    writeln(count, ' ', sum)
end.

It works when the stdin is not redirected, as well as if it is redirected from a disk file, but it doesn't work for pipelines, like this:

echo "1 2 3 4 5" | ./sum

Additional information:

The file text.inc containing the fix is added. The fix is obvious: after the call to do_seek procedure, check for the error and in case of error, fall back to what is done for unseekable streams. With the fix, SeekEof works on any type of a text stream.

However, I'd like to point out that the very function "Do_IsDevice" looks like a nonsense for me, and I don't understand why SeekOf tries to restore the position at all. So the fix can be made better and the function SeekEof -- shorter.

Mantis conversion info:

  • Mantis ID: 37716
  • OS: Linux
  • Version: 3.2.0
  • Fixed in revision: 46853 (#3c925730), 46864 (#1eb11a2a), 46946 (#a71f8735)
  • Monitored by: » croco (Andrey "Croco" Stolyarov), » @xhajt03 (Tomas Hajny)
To upload designs, you'll need to enable LFS and have an admin enable hashed storage. More information