Search code examples
rubyfile-descriptor

What do file descriptor 3 and 4 stand for in Ruby?


Execute below code in irb (no preceding commands) will get 5.

f = File.open("./test.txt")
puts f.fileno

File descriptor number 0, 1, 2 stand for STDIN, STDOUT, STDERR. What do 3 and 4 stand for in ruby?

Enviroment: Lubuntu 14.04 64bit, Ruby 1.9.3 under rvm.


Solution

  • From Standard Input, Output, & Error :

    When it is started by the shell, a program inherits three open files, with file descriptors 0, 1, and 2, called the standard input, the standard output, and the standard error. All of these are by default connected to the terminal, so if a program only reads file descriptor 0 and writes file descriptors 1 and 2, it can do I/O without having to open files. If the program opens any other files, they will have file descriptors 3, 4, etc.

    Update

    $stdin.fileno    # => 0
    $stdout.fileno   # => 1
    $stderr.fileno # => 2
    File.open('test1').fileno # => 7
    File.open('test2').fileno # => 8
    File.open('test.txt').fileno # => 9
    

    Now lets try to read the filename from the file descriptors using for_fd method.

    File.for_fd(7) # => #<File:fd 7> # refers file test1
    File.for_fd(8) # => #<File:fd 8> # refers file test2
    File.for_fd(9) # => #<File:fd 9> # refers file test.txt
    

    Opps!, these are not possible, as file descriptors 3,4,5,6 are used by RubyVM.

    File.for_fd(3) # => 
    # The given fd is not accessible because RubyVM reserves it (ArgumentError)
    File.for_fd(4) # => 
    # The given fd is not accessible because RubyVM reserves it (ArgumentError)
    File.for_fd(5) # => 
    # The given fd is not accessible because RubyVM reserves it (ArgumentError)
    File.for_fd(6) # => 
    # The given fd is not accessible because RubyVM reserves it (ArgumentError)
    

    Note : My Ruby version is - 2.0.0-p451 in openSUSE13.1.