> Submitted By: Jan Mehnert (janmehnert) > # eth_mini_test.rbw:32:in `close': Unknown Error (Errno::ENOTSOCK) I use the mswin build for Net library work. Sockets have never worked for me on bcc build. ** ruby 1.9.0 (2005-07-16) [i586-bccwin32] Example: #---------- require 'net/http' p ['Net::HTTP', Net::HTTP::Revision, Net::HTTP::HTTPVersion] h = Net::HTTP.new('www.rubyist.net') resp = h.get('/index.html', nil) puts resp.body #---------- ["Net::HTTP", "1.126", "1.1"] D:/RUBY/SRC_CVSINST/lib/ruby/1.9/net/protocol.rb:70:in `close': Bad file number (Errno::EBADF) from D:/RUBY/SRC_CVSINST/lib/ruby/1.9/net/protocol.rb:70:in `close' from D:/RUBY/SRC_CVSINST/lib/ruby/1.9/net/http.rb:552:in `do_finish' from D:/RUBY/SRC_CVSINST/lib/ruby/1.9/net/http.rb:492:in `start' from D:/RUBY/SRC_CVSINST/lib/ruby/1.9/net/http.rb:982:in `request' from D:/RUBY/SRC_CVSINST/lib/ruby/1.9/net/http.rb:716:in `get' from C:/TEMP/rbD115.TMP:5 EBADF is not important, previous builds have given: Unknown Error (Errno::ENOTSOCK) Below is a **very old** trace to remind myself of the sequence of events. In summary, fptr_finalize(io.c) calls rb_w32_fclose *twice* -- once for each side of the r/w socket. My understanding is that Windows requires only _one_ closesocket call. But mswin build handles it OK. I think the difference between mswin and bccwin relates to ERRNO ?? o) msvcrt-ruby1x.dll and socket.so both refer to _errno in msvcr71.dll run-time and they see the same copy (passed between each other). o) bccwin32-ruby1x.dll and socket.so both refer to _errno in CC3250.dll run-time but it seemed evident to me that they had separate copies. (i.e. if socket.c sets errno, Ruby run-time reads the value from the most recent operation in Ruby, *not* in socket extension.) The two ERRNO implementations are not similar. I hope your debugging tools are better than mine. "is_socket" and "errno" are the things to watch, IMHO. Let me know if there's anything you want me to try. daz -- < **very old** "trace" > io rb_fdopen <- File* [004c6240] (f) read io rb_fdopen <- File* [004c6258] (f2) write RETURN( <- ) with OPEN FILE pointers ... ... ENTER( -> ) io rb_io_close_m -> io rb_io_close -> io rb_io_fptr_cleanup -> io fptr_finalize -> # fptr_finalize calls fclose [#defined as rb_w32_fclose] twice # (once for each side of the r/w socket) # fd = fileno(004c6240 -OR- 004c6258) // OK, both yield 4 as file descriptor # TO_SOCKET(fd) // OK, [00000090] # First, the write side: io # while (fclose f2 fd#4 [004c6258]) w32 rb_w32_fclose -> File* [004c6258] fd#4 sock[00000090] w32 is_socket -> w32 is_socket <- sock[00000090] (TRUE) l_onoff[0000] l_linger[0000] w32 ..(rb_w32_fclose) sock fclose -> is_socket?==TRUE w32 is_socket -> w32 ..(is_socket) WSA_GLE(WSAENOTSOCK) errno(0) w32 is_socket <- sock[00000090] (FALSE) w32 ..(rb_w32_fclose) sock fclose <- errcd(0) is_socket?==FALSE w32 rb_w32_fclose <- WSA_GLE(WSAENOTSOCK) errno!(WSAENOTSOCK) # Then, the read side: io # while (fclose f1 fd#4 [004c6240]) w32 rb_w32_fclose -> File* [004c6240] fd#4 sock[ffffffff] w32 is_socket -> w32 ..(is_socket) WSA_GLE(WSAENOTSOCK) errno(6) w32 is_socket <- sock[ffffffff] (FALSE) w32 ..(rb_w32_fclose) - UnlockFile *error* GLE(6) w32 ..(rb_w32_fclose) NON-sock fclose -> w32 rb_w32_fclose <- NON-sock fclose <- errcd(-1) io ..(fptr_finalize) ***SYS_FAIL*** err_n1 = 0, err_n2 = WSAENOTSOCK ======END======