rhodes 3.2.0.beta.4 → 3.2.0.beta.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/CHANGELOG +2 -0
- data/Manifest.txt +517 -23
- data/Rakefile +52 -7
- data/doc/build.txt +7 -1
- data/doc/device-caps.txt +1 -1
- data/doc/install.txt +12 -0
- data/doc/jqt-jqm-transition.txt +121 -0
- data/doc/release.txt +6 -1
- data/doc/ui.txt +4 -2
- data/installer/icon.ico +0 -0
- data/lib/extensions/barcode/ext/barcode/shared/src/zbar.c +7 -0
- data/lib/extensions/barcode/ext/barcode/shared/zbar/rho_bridge.c +3 -3
- data/lib/extensions/barcode/ext/barcode/shared/zbar/zbar/README.TXT +74 -3
- data/lib/extensions/fcntl/ext/Rakefile +57 -38
- data/lib/extensions/fcntl/ext/build.bat +1 -0
- data/lib/extensions/fcntl/ext/fcntl.vcproj +323 -0
- data/lib/extensions/fileutils/fileutils.rb +57 -33
- data/lib/extensions/net-http/net/ftp.rb +40 -36
- data/lib/extensions/net-http/net/http.rb +98 -38
- data/lib/extensions/net-http/net/https.rb +3 -13
- data/lib/extensions/net-http/net/protocol.rb +20 -4
- data/lib/extensions/rexml/rexml/document.rb +11 -9
- data/lib/extensions/rexml/rexml/element.rb +1 -1
- data/lib/extensions/rexml/rexml/entity.rb +1 -1
- data/lib/extensions/rexml/rexml/formatters/default.rb +3 -1
- data/lib/extensions/rexml/rexml/formatters/pretty.rb +1 -1
- data/lib/extensions/rexml/rexml/light/node.rb +1 -2
- data/lib/extensions/rexml/rexml/parent.rb +1 -0
- data/lib/extensions/rexml/rexml/parsers/xpathparser.rb +2 -1
- data/lib/extensions/rexml/rexml/quickpath.rb +4 -1
- data/lib/extensions/rexml/rexml/rexml.rb +1 -1
- data/lib/extensions/rexml/rexml/source.rb +25 -14
- data/lib/extensions/rexml/rexml/text.rb +20 -21
- data/lib/extensions/rexml/rexml/xmldecl.rb +2 -2
- data/lib/extensions/rexml/rexml/xmltokens.rb +2 -2
- data/lib/extensions/rexml/rexml/xpath_parser.rb +2 -1
- data/lib/extensions/set/set.rb +100 -25
- data/lib/extensions/uri/uri/common.rb +134 -4
- data/lib/extensions/uri/uri/ftp.rb +14 -3
- data/lib/extensions/uri/uri/generic.rb +53 -44
- data/lib/extensions/uri/uri/http.rb +1 -1
- data/lib/extensions/uri/uri/https.rb +1 -1
- data/lib/extensions/uri/uri/ldap.rb +1 -1
- data/lib/extensions/uri/uri/mailto.rb +9 -9
- data/lib/framework/rho/rhoviewhelpers.rb +3 -2
- data/lib/framework/rholang/localization_simplified.rb +5 -3
- data/platform/android/Rhodes/src/com/rhomobile/rhodes/Logger.java +14 -1
- data/platform/android/Rhodes/src/com/rhomobile/rhodes/camera/ImageCapture.java +1 -1
- data/platform/android/Rhodes/src/com/rhomobile/rhodes/camera/ImageCaptureCallback.java +0 -1
- data/platform/android/Rhodes/src/com/rhomobile/rhodes/file/RhoFileApi.java +12 -5
- data/platform/android/build/android.rake +7 -7
- data/platform/iphone/Classes/AppManager/AppManager.m +19 -7
- data/platform/iphone/rbuild/iphone.rake +1 -1
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/Frameworks/QtCore.framework/Versions/4/QtCore +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/Frameworks/QtGui.framework/Versions/4/QtGui +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/Frameworks/QtNetwork.framework/Versions/4/QtNetwork +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/Frameworks/QtWebKit.framework/Versions/4/QtWebKit +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/Frameworks/phonon.framework/Versions/4/phonon +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/Info.plist +1 -1
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/MacOS/RhoSimulator +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/PlugIns/accessible/libqtaccessiblewidgets.dylib +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/PlugIns/bearer/libqgenericbearer.dylib +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/PlugIns/codecs/libqcncodecs.dylib +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/PlugIns/codecs/libqjpcodecs.dylib +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/PlugIns/codecs/libqkrcodecs.dylib +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/PlugIns/codecs/libqtwcodecs.dylib +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/PlugIns/graphicssystems/libqtracegraphicssystem.dylib +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/PlugIns/imageformats/libqgif.dylib +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/PlugIns/imageformats/libqico.dylib +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/PlugIns/imageformats/libqjpeg.dylib +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/PlugIns/imageformats/libqmng.dylib +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/PlugIns/imageformats/libqtiff.dylib +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/PlugIns/phonon_backend/libphonon_qt7.dylib +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/PlugIns/qmltooling/libqmldbg_tcp.dylib +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/Resources/rho.icns +0 -0
- data/platform/osx/build/osx.rake +25 -3
- data/platform/shared/common/AutoPointer.h +1 -1
- data/platform/shared/common/RhoStd.h +10 -10
- data/platform/shared/common/RhodesAppBase.cpp +3 -0
- data/platform/shared/logging/RhoLogConf.cpp +1 -1
- data/platform/shared/qt/rhodes/QtMainWindow.cpp +7 -0
- data/platform/shared/qt/rhodes/RhoSimulator.h +3 -1
- data/platform/shared/qt/rhodes/main.cpp +3 -0
- data/platform/shared/qt/rhodes/resources/rho.icns +0 -0
- data/platform/shared/qt/rhodes/resources/rho.ico +0 -0
- data/platform/shared/qt/rhodes/resources/rho.png +0 -0
- data/platform/shared/qt/rhodes/resources/simulator.qrc +5 -0
- data/platform/shared/qt/rhodes/rhodes.pro +2 -0
- data/platform/shared/ruby/ext/rho/rhosupport.c +21 -2
- data/platform/shared/ruby/ext/socket_192/addrinfo.h +191 -0
- data/platform/shared/ruby/ext/socket_192/ancdata.c +1800 -0
- data/platform/shared/ruby/ext/socket_192/basicsocket.c +771 -0
- data/platform/shared/ruby/ext/socket_192/constants.c +145 -0
- data/platform/shared/ruby/ext/socket_192/depend +25 -0
- data/platform/shared/ruby/ext/socket_192/extconf.rb +365 -0
- data/platform/shared/ruby/ext/socket_192/getaddrinfo.c +674 -0
- data/platform/shared/ruby/ext/socket_192/getnameinfo.c +260 -0
- data/platform/shared/ruby/ext/socket_192/init.c +575 -0
- data/platform/shared/ruby/ext/socket_192/ipsocket.c +308 -0
- data/platform/shared/ruby/ext/socket_192/lib/socket.rb +755 -0
- data/platform/shared/ruby/ext/socket_192/mkconstants.rb +696 -0
- data/platform/shared/ruby/ext/socket_192/option.c +692 -0
- data/platform/shared/ruby/ext/socket_192/raddrinfo.c +2211 -0
- data/platform/shared/ruby/ext/socket_192/rubysocket.h +306 -0
- data/platform/shared/ruby/ext/socket_192/socket.c +1870 -0
- data/platform/shared/ruby/ext/socket_192/sockport.h +84 -0
- data/platform/shared/ruby/ext/socket_192/sockssocket.c +58 -0
- data/platform/shared/ruby/ext/socket_192/tcpserver.c +145 -0
- data/platform/shared/ruby/ext/socket_192/tcpsocket.c +69 -0
- data/platform/shared/ruby/ext/socket_192/udpsocket.c +264 -0
- data/platform/shared/ruby/ext/socket_192/unixserver.c +154 -0
- data/platform/shared/ruby/ext/socket_192/unixsocket.c +514 -0
- data/platform/shared/ruby/ext/stringio/stringio.c +158 -61
- data/platform/shared/ruby/ext/strscan/strscan.c +18 -31
- data/platform/shared/ruby/iphone/ruby/config.h +2 -1
- data/platform/shared/ruby/linux/ruby/config.h +2 -1
- data/platform/shared/ruby/symbian/ruby/config.h +2 -1
- data/platform/shared/ruby/win32/ruby/config.h +1 -0
- data/platform/shared/ruby/win32/ruby/constdefs.c +5866 -0
- data/platform/shared/ruby/win32/ruby/constdefs.h +1788 -0
- data/platform/shared/ruby/wince/ruby/config.h +1 -0
- data/platform/shared/ruby/wince/ruby/constdefs.c +5866 -0
- data/platform/shared/ruby/wince/ruby/constdefs.h +1788 -0
- data/platform/symbian/build/symbian.rake +8 -0
- data/platform/symbian/rhodes/rhodes.pro +3 -3
- data/platform/win32/RhoSimulator/RhoSimulator.exe +0 -0
- data/platform/wm/build/wm.rake +1 -1
- data/platform/wm/rhodes/Rhodes.cpp +3 -0
- data/platform/wm/rhodes/rhodes.vcproj +612 -6
- data/platform/wm/rhodes/rhosim.rc +394 -0
- data/platform/wm/rhodes/simulator/MainWindowQt.cpp +2 -2
- data/platform/wp7/RhoRubyLib/common/RhodesApp.cs +8 -2
- data/platform/wp7/RhoRubyLib/net/NetRequest.cs +5 -1
- data/platform/wp7/build/wp.rake +1 -1
- data/rakefile.rb +52 -7
- data/res/generators/templates/application/app/layout.erb +4 -4
- data/res/generators/templates/application/public/jqmobile/{jquery.mobile-1.0b3.css → jquery.mobile-1.0rc1.css} +507 -457
- data/res/generators/templates/application/public/jqmobile/{jquery.mobile-1.0b3.js → jquery.mobile-1.0rc1.js} +565 -458
- data/res/generators/templates/application/public/jqmobile/jquery.mobile-1.0rc1.min.css +12 -0
- data/res/generators/templates/application/public/jqmobile/jquery.mobile-1.0rc1.min.js +170 -0
- data/res/generators/templates/application/public/jquery/{jquery-1.6.3.js → jquery-1.6.4.js} +10 -8
- data/res/generators/templates/application/public/jquery/jquery-1.6.4.min.js +4 -0
- data/res/generators/templates/application/public/js/jqmobile-patch.js +47 -1
- data/res/icons/rho.icns +0 -0
- data/res/icons/rho.ico +0 -0
- data/res/icons/rho.png +0 -0
- data/res/icons/rho.psd +0 -0
- data/res/icons/rhodes.icns +0 -0
- data/res/icons/rhodes.ico +0 -0
- data/res/icons/rhodes.png +0 -0
- data/res/icons/rhodes.psd +0 -0
- data/res/icons/rhosim.icns +0 -0
- data/res/icons/rhosim.ico +0 -0
- data/res/icons/rhosim.png +0 -0
- data/res/icons/rhosim.psd +0 -0
- data/rhodes.gemspec +1 -1
- data/spec/framework_spec/app/spec/core/file/expand_path_spec.rb +4 -4
- data/spec/framework_spec/app/spec/library/net/FTPError_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/FTPPermError_spec.rb +12 -0
- data/spec/framework_spec/app/spec/library/net/FTPProtoError_spec.rb +12 -0
- data/spec/framework_spec/app/spec/library/net/FTPReplyError_spec.rb +12 -0
- data/spec/framework_spec/app/spec/library/net/FTPTempError_spec.rb +12 -0
- data/spec/framework_spec/app/spec/library/net/ftp/abort_spec.rb +62 -0
- data/spec/framework_spec/app/spec/library/net/ftp/acct_spec.rb +58 -0
- data/spec/framework_spec/app/spec/library/net/ftp/binary_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/net/ftp/chdir_spec.rb +101 -0
- data/spec/framework_spec/app/spec/library/net/ftp/close_spec.rb +28 -0
- data/spec/framework_spec/app/spec/library/net/ftp/closed_spec.rb +21 -0
- data/spec/framework_spec/app/spec/library/net/ftp/connect_spec.rb +49 -0
- data/spec/framework_spec/app/spec/library/net/ftp/debug_mode_spec.rb +23 -0
- data/spec/framework_spec/app/spec/library/net/ftp/delete_spec.rb +59 -0
- data/spec/framework_spec/app/spec/library/net/ftp/dir_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/ftp/fixtures/putbinaryfile +3 -0
- data/spec/framework_spec/app/spec/library/net/ftp/fixtures/puttextfile +3 -0
- data/spec/framework_spec/app/spec/library/net/ftp/fixtures/server.rb +258 -0
- data/spec/framework_spec/app/spec/library/net/ftp/get_spec.rb +21 -0
- data/spec/framework_spec/app/spec/library/net/ftp/getbinaryfile_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/ftp/getdir_spec.rb +7 -0
- data/spec/framework_spec/app/spec/library/net/ftp/gettextfile_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/ftp/help_spec.rb +66 -0
- data/spec/framework_spec/app/spec/library/net/ftp/initialize_spec.rb +87 -0
- data/spec/framework_spec/app/spec/library/net/ftp/last_response_code_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/ftp/last_response_spec.rb +25 -0
- data/spec/framework_spec/app/spec/library/net/ftp/lastresp_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/ftp/list_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/ftp/login_spec.rb +216 -0
- data/spec/framework_spec/app/spec/library/net/ftp/ls_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/ftp/mdtm_spec.rb +38 -0
- data/spec/framework_spec/app/spec/library/net/ftp/mkdir_spec.rb +61 -0
- data/spec/framework_spec/app/spec/library/net/ftp/mtime_spec.rb +50 -0
- data/spec/framework_spec/app/spec/library/net/ftp/nlst_spec.rb +122 -0
- data/spec/framework_spec/app/spec/library/net/ftp/noop_spec.rb +38 -0
- data/spec/framework_spec/app/spec/library/net/ftp/open_spec.rb +55 -0
- data/spec/framework_spec/app/spec/library/net/ftp/passive_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/net/ftp/put_spec.rb +21 -0
- data/spec/framework_spec/app/spec/library/net/ftp/putbinaryfile_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/ftp/puttextfile_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/ftp/pwd_spec.rb +53 -0
- data/spec/framework_spec/app/spec/library/net/ftp/quit_spec.rb +33 -0
- data/spec/framework_spec/app/spec/library/net/ftp/rename_spec.rb +94 -0
- data/spec/framework_spec/app/spec/library/net/ftp/resume_spec.rb +23 -0
- data/spec/framework_spec/app/spec/library/net/ftp/retrbinary_spec.rb +31 -0
- data/spec/framework_spec/app/spec/library/net/ftp/retrlines_spec.rb +35 -0
- data/spec/framework_spec/app/spec/library/net/ftp/return_code_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/net/ftp/rmdir_spec.rb +58 -0
- data/spec/framework_spec/app/spec/library/net/ftp/sendcmd_spec.rb +54 -0
- data/spec/framework_spec/app/spec/library/net/ftp/set_socket_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/ftp/shared/getbinaryfile.rb +180 -0
- data/spec/framework_spec/app/spec/library/net/ftp/shared/gettextfile.rb +130 -0
- data/spec/framework_spec/app/spec/library/net/ftp/shared/last_response_code.rb +25 -0
- data/spec/framework_spec/app/spec/library/net/ftp/shared/list.rb +134 -0
- data/spec/framework_spec/app/spec/library/net/ftp/shared/putbinaryfile.rb +233 -0
- data/spec/framework_spec/app/spec/library/net/ftp/shared/puttextfile.rb +150 -0
- data/spec/framework_spec/app/spec/library/net/ftp/shared/pwd.rb +3 -0
- data/spec/framework_spec/app/spec/library/net/ftp/site_spec.rb +53 -0
- data/spec/framework_spec/app/spec/library/net/ftp/size_spec.rb +48 -0
- data/spec/framework_spec/app/spec/library/net/ftp/status_spec.rb +63 -0
- data/spec/framework_spec/app/spec/library/net/ftp/storbinary_spec.rb +49 -0
- data/spec/framework_spec/app/spec/library/net/ftp/storlines_spec.rb +44 -0
- data/spec/framework_spec/app/spec/library/net/ftp/system_spec.rb +48 -0
- data/spec/framework_spec/app/spec/library/net/ftp/voidcmd_spec.rb +54 -0
- data/spec/framework_spec/app/spec/library/net/ftp/welcome_spec.rb +25 -0
- data/spec/framework_spec/app/spec/library/net/http/HTTPBadResponse_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/HTTPError_spec.rb +12 -0
- data/spec/framework_spec/app/spec/library/net/http/HTTPFatalError_spec.rb +12 -0
- data/spec/framework_spec/app/spec/library/net/http/HTTPHeaderSyntaxError_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/HTTPRetriableError_spec.rb +12 -0
- data/spec/framework_spec/app/spec/library/net/http/HTTPServerException_spec.rb +12 -0
- data/spec/framework_spec/app/spec/library/net/http/http/Proxy_spec.rb +35 -0
- data/spec/framework_spec/app/spec/library/net/http/http/active_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/http/address_spec.rb +9 -0
- data/spec/framework_spec/app/spec/library/net/http/http/close_on_empty_response_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/net/http/http/copy_spec.rb +23 -0
- data/spec/framework_spec/app/spec/library/net/http/http/default_port_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/http/delete_spec.rb +23 -0
- data/spec/framework_spec/app/spec/library/net/http/http/finish_spec.rb +31 -0
- data/spec/framework_spec/app/spec/library/net/http/http/fixtures/http_server.rb +97 -0
- data/spec/framework_spec/app/spec/library/net/http/http/get2_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/http/get_print_spec.rb +29 -0
- data/spec/framework_spec/app/spec/library/net/http/http/get_response_spec.rb +29 -0
- data/spec/framework_spec/app/spec/library/net/http/http/get_spec.rb +52 -0
- data/spec/framework_spec/app/spec/library/net/http/http/head2_spec.rb +9 -0
- data/spec/framework_spec/app/spec/library/net/http/http/head_spec.rb +27 -0
- data/spec/framework_spec/app/spec/library/net/http/http/http_default_port_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/http/https_default_port_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/http/initialize_spec.rb +46 -0
- data/spec/framework_spec/app/spec/library/net/http/http/inspect_spec.rb +26 -0
- data/spec/framework_spec/app/spec/library/net/http/http/is_version_1_1_spec.rb +7 -0
- data/spec/framework_spec/app/spec/library/net/http/http/is_version_1_2_spec.rb +7 -0
- data/spec/framework_spec/app/spec/library/net/http/http/lock_spec.rb +23 -0
- data/spec/framework_spec/app/spec/library/net/http/http/mkcol_spec.rb +23 -0
- data/spec/framework_spec/app/spec/library/net/http/http/move_spec.rb +27 -0
- data/spec/framework_spec/app/spec/library/net/http/http/new_spec.rb +86 -0
- data/spec/framework_spec/app/spec/library/net/http/http/newobj_spec.rb +48 -0
- data/spec/framework_spec/app/spec/library/net/http/http/open_timeout_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/net/http/http/options_spec.rb +27 -0
- data/spec/framework_spec/app/spec/library/net/http/http/port_spec.rb +9 -0
- data/spec/framework_spec/app/spec/library/net/http/http/post2_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/http/post_form_spec.rb +21 -0
- data/spec/framework_spec/app/spec/library/net/http/http/post_spec.rb +40 -0
- data/spec/framework_spec/app/spec/library/net/http/http/propfind_spec.rb +26 -0
- data/spec/framework_spec/app/spec/library/net/http/http/proppatch_spec.rb +26 -0
- data/spec/framework_spec/app/spec/library/net/http/http/proxy_address_spec.rb +31 -0
- data/spec/framework_spec/app/spec/library/net/http/http/proxy_class_spec.rb +9 -0
- data/spec/framework_spec/app/spec/library/net/http/http/proxy_pass_spec.rb +39 -0
- data/spec/framework_spec/app/spec/library/net/http/http/proxy_port_spec.rb +39 -0
- data/spec/framework_spec/app/spec/library/net/http/http/proxy_user_spec.rb +39 -0
- data/spec/framework_spec/app/spec/library/net/http/http/put2_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/http/put_spec.rb +26 -0
- data/spec/framework_spec/app/spec/library/net/http/http/read_timeout_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/net/http/http/request_get_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/http/request_head_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/http/request_post_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/http/request_put_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/http/request_spec.rb +111 -0
- data/spec/framework_spec/app/spec/library/net/http/http/request_types_spec.rb +254 -0
- data/spec/framework_spec/app/spec/library/net/http/http/send_request_spec.rb +120 -0
- data/spec/framework_spec/app/spec/library/net/http/http/set_debug_output_spec.rb +35 -0
- data/spec/framework_spec/app/spec/library/net/http/http/shared/request_get.rb +45 -0
- data/spec/framework_spec/app/spec/library/net/http/http/shared/request_head.rb +45 -0
- data/spec/framework_spec/app/spec/library/net/http/http/shared/request_post.rb +45 -0
- data/spec/framework_spec/app/spec/library/net/http/http/shared/request_put.rb +45 -0
- data/spec/framework_spec/app/spec/library/net/http/http/shared/started.rb +28 -0
- data/spec/framework_spec/app/spec/library/net/http/http/shared/version_1_1.rb +19 -0
- data/spec/framework_spec/app/spec/library/net/http/http/shared/version_1_2.rb +6 -0
- data/spec/framework_spec/app/spec/library/net/http/http/socket_type_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/http/start_spec.rb +103 -0
- data/spec/framework_spec/app/spec/library/net/http/http/started_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/http/trace_spec.rb +26 -0
- data/spec/framework_spec/app/spec/library/net/http/http/unlock_spec.rb +26 -0
- data/spec/framework_spec/app/spec/library/net/http/http/use_ssl_spec.rb +9 -0
- data/spec/framework_spec/app/spec/library/net/http/http/version_1_1_spec.rb +22 -0
- data/spec/framework_spec/app/spec/library/net/http/http/version_1_2_spec.rb +20 -0
- data/spec/framework_spec/app/spec/library/net/http/httpexceptions/fixtures/classes.rb +5 -0
- data/spec/framework_spec/app/spec/library/net/http/httpexceptions/initialize_spec.rb +17 -0
- data/spec/framework_spec/app/spec/library/net/http/httpexceptions/response_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/net/http/httpgenericrequest/body_exist_spec.rb +27 -0
- data/spec/framework_spec/app/spec/library/net/http/httpgenericrequest/body_spec.rb +30 -0
- data/spec/framework_spec/app/spec/library/net/http/httpgenericrequest/body_stream_spec.rb +32 -0
- data/spec/framework_spec/app/spec/library/net/http/httpgenericrequest/exec_spec.rb +122 -0
- data/spec/framework_spec/app/spec/library/net/http/httpgenericrequest/inspect_spec.rb +25 -0
- data/spec/framework_spec/app/spec/library/net/http/httpgenericrequest/method_spec.rb +15 -0
- data/spec/framework_spec/app/spec/library/net/http/httpgenericrequest/path_spec.rb +12 -0
- data/spec/framework_spec/app/spec/library/net/http/httpgenericrequest/request_body_permitted_spec.rb +12 -0
- data/spec/framework_spec/app/spec/library/net/http/httpgenericrequest/response_body_permitted_spec.rb +12 -0
- data/spec/framework_spec/app/spec/library/net/http/httpgenericrequest/set_body_internal_spec.rb +21 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/add_field_spec.rb +31 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/basic_auth_spec.rb +14 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/canonical_each_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/chunked_spec.rb +22 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/content_length_spec.rb +54 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/content_range_spec.rb +34 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/content_type_spec.rb +26 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/delete_spec.rb +30 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/each_capitalized_name_spec.rb +45 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/each_capitalized_spec.rb +9 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/each_header_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/each_key_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/each_name_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/each_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/each_value_spec.rb +46 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/element_reference_spec.rb +39 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/element_set_spec.rb +41 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/fetch_spec.rb +69 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/fixtures/classes.rb +11 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/form_data_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/get_fields_spec.rb +39 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/initialize_http_header_spec.rb +29 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/key_spec.rb +21 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/length_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/main_type_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/proxy_basic_auth_spec.rb +14 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/range_length_spec.rb +32 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/range_spec.rb +48 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/set_content_type_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/set_form_data_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/set_range_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/shared/each_capitalized.rb +42 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/shared/each_header.rb +42 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/shared/each_name.rb +39 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/shared/set_content_type.rb +18 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/shared/set_form_data.rb +27 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/shared/set_range.rb +89 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/shared/size.rb +18 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/size_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/sub_type_spec.rb +32 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/to_hash_spec.rb +25 -0
- data/spec/framework_spec/app/spec/library/net/http/httpheader/type_params_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/net/http/httprequest/initialize_spec.rb +45 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/body_permitted_spec.rb +13 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/body_spec.rb +7 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/code_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/code_type_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/entity_spec.rb +7 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/error_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/error_type_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/exception_type_spec.rb +13 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/header_spec.rb +9 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/http_version_spec.rb +12 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/initialize_spec.rb +11 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/inspect_spec.rb +15 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/message_spec.rb +9 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/msg_spec.rb +9 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/read_body_spec.rb +86 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/read_header_spec.rb +9 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/read_new_spec.rb +22 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/reading_body_spec.rb +58 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/response_spec.rb +9 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/shared/body.rb +18 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/to_ary_spec.rb +26 -0
- data/spec/framework_spec/app/spec/library/net/http/httpresponse/value_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/rexml/attribute/clone_spec.rb +11 -0
- data/spec/framework_spec/app/spec/library/rexml/attribute/element_spec.rb +23 -0
- data/spec/framework_spec/app/spec/library/rexml/attribute/equal_value_spec.rb +18 -0
- data/spec/framework_spec/app/spec/library/rexml/attribute/hash_spec.rb +13 -0
- data/spec/framework_spec/app/spec/library/rexml/attribute/initialize_spec.rb +29 -0
- data/spec/framework_spec/app/spec/library/rexml/attribute/inspect_spec.rb +20 -0
- data/spec/framework_spec/app/spec/library/rexml/attribute/namespace_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/rexml/attribute/node_type_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/rexml/attribute/prefix_spec.rb +18 -0
- data/spec/framework_spec/app/spec/library/rexml/attribute/remove_spec.rb +20 -0
- data/spec/framework_spec/app/spec/library/rexml/attribute/to_s_spec.rb +14 -0
- data/spec/framework_spec/app/spec/library/rexml/attribute/to_string_spec.rb +15 -0
- data/spec/framework_spec/app/spec/library/rexml/attribute/value_spec.rb +15 -0
- data/spec/framework_spec/app/spec/library/rexml/attribute/write_spec.rb +23 -0
- data/spec/framework_spec/app/spec/library/rexml/attribute/xpath_spec.rb +20 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/add_spec.rb +7 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/append_spec.rb +7 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/delete_all_spec.rb +31 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/delete_spec.rb +27 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/each_attribute_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/each_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/element_reference_spec.rb +19 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/element_set_spec.rb +26 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/get_attribute_ns_spec.rb +14 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/get_attribute_spec.rb +29 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/initialize_spec.rb +19 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/length_spec.rb +7 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/namespaces_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/prefixes_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/shared/add.rb +17 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/shared/length.rb +13 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/size_spec.rb +7 -0
- data/spec/framework_spec/app/spec/library/rexml/attributes/to_a_spec.rb +20 -0
- data/spec/framework_spec/app/spec/library/rexml/cdata/clone_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/rexml/cdata/initialize_spec.rb +25 -0
- data/spec/framework_spec/app/spec/library/rexml/cdata/shared/to_s.rb +11 -0
- data/spec/framework_spec/app/spec/library/rexml/cdata/to_s_spec.rb +7 -0
- data/spec/framework_spec/app/spec/library/rexml/cdata/value_spec.rb +7 -0
- data/spec/framework_spec/app/spec/library/rexml/document/add_element_spec.rb +31 -0
- data/spec/framework_spec/app/spec/library/rexml/document/add_spec.rb +61 -0
- data/spec/framework_spec/app/spec/library/rexml/document/clone_spec.rb +20 -0
- data/spec/framework_spec/app/spec/library/rexml/document/doctype_spec.rb +15 -0
- data/spec/framework_spec/app/spec/library/rexml/document/encoding_spec.rb +22 -0
- data/spec/framework_spec/app/spec/library/rexml/document/expanded_name_spec.rb +16 -0
- data/spec/framework_spec/app/spec/library/rexml/document/new_spec.rb +38 -0
- data/spec/framework_spec/app/spec/library/rexml/document/node_type_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/rexml/document/root_spec.rb +12 -0
- data/spec/framework_spec/app/spec/library/rexml/document/stand_alone_spec.rb +19 -0
- data/spec/framework_spec/app/spec/library/rexml/document/version_spec.rb +14 -0
- data/spec/framework_spec/app/spec/library/rexml/document/write_spec.rb +39 -0
- data/spec/framework_spec/app/spec/library/rexml/document/xml_decl_spec.rb +15 -0
- data/spec/framework_spec/app/spec/library/rexml/element/add_attribute_spec.rb +41 -0
- data/spec/framework_spec/app/spec/library/rexml/element/add_attributes_spec.rb +22 -0
- data/spec/framework_spec/app/spec/library/rexml/element/add_element_spec.rb +39 -0
- data/spec/framework_spec/app/spec/library/rexml/element/add_namespace_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/rexml/element/add_text_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/rexml/element/attribute_spec.rb +17 -0
- data/spec/framework_spec/app/spec/library/rexml/element/attributes_spec.rb +19 -0
- data/spec/framework_spec/app/spec/library/rexml/element/cdatas_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/rexml/element/clone_spec.rb +29 -0
- data/spec/framework_spec/app/spec/library/rexml/element/comments_spec.rb +21 -0
- data/spec/framework_spec/app/spec/library/rexml/element/delete_attribute_spec.rb +39 -0
- data/spec/framework_spec/app/spec/library/rexml/element/delete_element_spec.rb +51 -0
- data/spec/framework_spec/app/spec/library/rexml/element/delete_namespace_spec.rb +25 -0
- data/spec/framework_spec/app/spec/library/rexml/element/document_spec.rb +18 -0
- data/spec/framework_spec/app/spec/library/rexml/element/each_element_with_attribute_spec.rb +35 -0
- data/spec/framework_spec/app/spec/library/rexml/element/each_element_with_text_spec.rb +31 -0
- data/spec/framework_spec/app/spec/library/rexml/element/get_text_spec.rb +18 -0
- data/spec/framework_spec/app/spec/library/rexml/element/has_attributes_spec.rb +17 -0
- data/spec/framework_spec/app/spec/library/rexml/element/has_elements_spec.rb +18 -0
- data/spec/framework_spec/app/spec/library/rexml/element/has_text_spec.rb +16 -0
- data/spec/framework_spec/app/spec/library/rexml/element/inspect_spec.rb +27 -0
- data/spec/framework_spec/app/spec/library/rexml/element/instructions_spec.rb +21 -0
- data/spec/framework_spec/app/spec/library/rexml/element/namespace_spec.rb +27 -0
- data/spec/framework_spec/app/spec/library/rexml/element/namespaces_spec.rb +32 -0
- data/spec/framework_spec/app/spec/library/rexml/element/new_spec.rb +35 -0
- data/spec/framework_spec/app/spec/library/rexml/element/next_element_spec.rb +19 -0
- data/spec/framework_spec/app/spec/library/rexml/element/node_type_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/rexml/element/prefixes_spec.rb +23 -0
- data/spec/framework_spec/app/spec/library/rexml/element/previous_element_spec.rb +20 -0
- data/spec/framework_spec/app/spec/library/rexml/element/raw_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/rexml/element/root_spec.rb +28 -0
- data/spec/framework_spec/app/spec/library/rexml/element/text_spec.rb +46 -0
- data/spec/framework_spec/app/spec/library/rexml/element/texts_spec.rb +16 -0
- data/spec/framework_spec/app/spec/library/rexml/element/whitespace_spec.rb +23 -0
- data/spec/framework_spec/app/spec/library/rexml/node/each_recursive_spec.rb +21 -0
- data/spec/framework_spec/app/spec/library/rexml/node/find_first_recursive_spec.rb +25 -0
- data/spec/framework_spec/app/spec/library/rexml/node/index_in_parent_spec.rb +15 -0
- data/spec/framework_spec/app/spec/library/rexml/node/next_sibling_node_spec.rb +21 -0
- data/spec/framework_spec/app/spec/library/rexml/node/parent_spec.rb +21 -0
- data/spec/framework_spec/app/spec/library/rexml/node/previous_sibling_node_spec.rb +21 -0
- data/spec/framework_spec/app/spec/library/rexml/shared/each_element.rb +36 -0
- data/spec/framework_spec/app/spec/library/rexml/shared/elements_to_a.rb +36 -0
- data/spec/framework_spec/app/spec/library/rexml/text/append_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/rexml/text/clone_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/rexml/text/comparison_spec.rb +25 -0
- data/spec/framework_spec/app/spec/library/rexml/text/empty_spec.rb +12 -0
- data/spec/framework_spec/app/spec/library/rexml/text/indent_text_spec.rb +24 -0
- data/spec/framework_spec/app/spec/library/rexml/text/inspect_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/rexml/text/new_spec.rb +49 -0
- data/spec/framework_spec/app/spec/library/rexml/text/node_type_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/rexml/text/normalize_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/rexml/text/read_with_substitution_spec.rb +13 -0
- data/spec/framework_spec/app/spec/library/rexml/text/to_s_spec.rb +18 -0
- data/spec/framework_spec/app/spec/library/rexml/text/unnormalize_spec.rb +8 -0
- data/spec/framework_spec/app/spec/library/rexml/text/value_spec.rb +37 -0
- data/spec/framework_spec/app/spec/library/rexml/text/wrap_spec.rb +21 -0
- data/spec/framework_spec/app/spec/library/rexml/text/write_with_substitution_spec.rb +33 -0
- data/spec/framework_spec/app/spec/library/set/exclusion_spec.rb +2 -2
- data/spec/framework_spec/app/spec/library/set/merge_spec.rb +2 -2
- data/spec/framework_spec/app/spec/library/set/shared/difference.rb +2 -2
- data/spec/framework_spec/app/spec/library/set/shared/intersection.rb +2 -2
- data/spec/framework_spec/app/spec/library/set/shared/union.rb +2 -2
- data/spec/framework_spec/app/spec/library/set/sortedset/exclusion_spec.rb +2 -2
- data/spec/framework_spec/app/spec/library/set/sortedset/merge_spec.rb +2 -2
- data/spec/framework_spec/app/spec/library/set/sortedset/shared/difference.rb +2 -2
- data/spec/framework_spec/app/spec/library/set/sortedset/shared/intersection.rb +2 -2
- data/spec/framework_spec/app/spec/library/set/sortedset/shared/union.rb +2 -2
- data/spec/framework_spec/app/spec/library/timeout/timeout_spec.rb +37 -0
- data/spec/framework_spec/app/spec/library/uri/eql_spec.rb +12 -0
- data/spec/framework_spec/app/spec/library/uri/equality_spec.rb +48 -0
- data/spec/framework_spec/app/spec/library/uri/escape/decode_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/escape/encode_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/escape/escape_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/escape/unescape_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/extract_spec.rb +86 -0
- data/spec/framework_spec/app/spec/library/uri/fixtures/classes.rb +11 -0
- data/spec/framework_spec/app/spec/library/uri/fixtures/normalization.rb +54 -0
- data/spec/framework_spec/app/spec/library/uri/ftp/build_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/ftp/merge_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/ftp/new2_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/ftp/path_spec.rb +56 -0
- data/spec/framework_spec/app/spec/library/uri/ftp/set_typecode_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/ftp/to_s_spec.rb +25 -0
- data/spec/framework_spec/app/spec/library/uri/ftp/typecode_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/generic/absolute_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/generic/build2_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/build_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/coerce_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/component_ary_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/component_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/generic/default_port_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/generic/eql_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/equal_value_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/fragment_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/generic/hash_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/hierarchical_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/host_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/generic/inspect_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/merge_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/generic/minus_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/normalize_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/generic/opaque_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/generic/password_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/generic/path_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/generic/plus_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/port_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/generic/query_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/generic/registry_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/generic/relative_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/route_from_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/route_to_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/scheme_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/generic/select_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/set_fragment_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/set_host_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/set_opaque_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/set_password_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/set_path_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/set_port_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/set_query_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/set_registry_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/set_scheme_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/set_user_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/set_userinfo_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/to_s_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/use_registry_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/generic/user_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/generic/userinfo_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/http/build_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/http/request_uri_spec.rb +16 -0
- data/spec/framework_spec/app/spec/library/uri/join_spec.rb +61 -0
- data/spec/framework_spec/app/spec/library/uri/ldap/attributes_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/ldap/build_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/ldap/dn_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/ldap/extensions_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/ldap/filter_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/ldap/hierarchical_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/ldap/scope_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/ldap/set_attributes_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/ldap/set_dn_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/ldap/set_extensions_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/ldap/set_filter_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/ldap/set_scope_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/mailto/build_spec.rb +99 -0
- data/spec/framework_spec/app/spec/library/uri/mailto/headers_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/mailto/set_headers_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/mailto/set_to_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/mailto/to_mailtext_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/mailto/to_rfc822text_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/mailto/to_s_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/mailto/to_spec.rb +10 -0
- data/spec/framework_spec/app/spec/library/uri/merge_spec.rb +22 -0
- data/spec/framework_spec/app/spec/library/uri/normalize_spec.rb +35 -0
- data/spec/framework_spec/app/spec/library/uri/parse_spec.rb +249 -0
- data/spec/framework_spec/app/spec/library/uri/plus_spec.rb +489 -0
- data/spec/framework_spec/app/spec/library/uri/regexp_spec.rb +18 -0
- data/spec/framework_spec/app/spec/library/uri/route_from_spec.rb +25 -0
- data/spec/framework_spec/app/spec/library/uri/route_to_spec.rb +28 -0
- data/spec/framework_spec/app/spec/library/uri/select_spec.rb +31 -0
- data/spec/framework_spec/app/spec/library/uri/set_component_spec.rb +47 -0
- data/spec/framework_spec/app/spec/library/uri/shared/eql.rb +17 -0
- data/spec/framework_spec/app/spec/library/uri/split_spec.rb +6 -0
- data/spec/framework_spec/app/spec/library/uri/uri_spec.rb +31 -0
- data/spec/framework_spec/app/spec/library/uri/util/make_components_hash_spec.rb +6 -0
- data/spec/framework_spec/build.yml +2 -2
- data/spec/framework_spec/extensions/test-libs/test/unit.rb +328 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/assertionfailederror.rb +25 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/assertions.rb +1878 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/attribute.rb +129 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/autorunner.rb +422 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/collector.rb +38 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/collector/descendant.rb +23 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/collector/dir.rb +108 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/collector/load.rb +187 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/collector/objectspace.rb +34 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/collector/xml.rb +250 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/color-scheme.rb +153 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/color.rb +123 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/data.rb +80 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/diff.rb +740 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/error.rb +151 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/exceptionhandler.rb +39 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/failure.rb +136 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/fixture.rb +214 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/notification.rb +133 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/omission.rb +191 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/pending.rb +150 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/priority.rb +182 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/runner/console.rb +59 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/runner/emacs.rb +8 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/runner/tap.rb +8 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/runner/xml.rb +15 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/testcase.rb +601 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/testresult.rb +125 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/testsuite.rb +134 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/testsuitecreator.rb +79 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/ui/console/outputlevel.rb +15 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/ui/console/testrunner.rb +561 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/ui/emacs/testrunner.rb +63 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/ui/tap/testrunner.rb +82 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/ui/testrunner.rb +53 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/ui/testrunnermediator.rb +86 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/ui/testrunnerutilities.rb +41 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/ui/xml/testrunner.rb +224 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/util/backtracefilter.rb +42 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/util/method-owner-finder.rb +28 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/util/observable.rb +90 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/util/output.rb +31 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/util/procwrapper.rb +48 -0
- data/spec/framework_spec/extensions/test-libs/test/unit/version.rb +5 -0
- data/spec/framework_spec/extensions/test-libs/webrick/accesslog.rb +10 -2
- data/spec/framework_spec/extensions/test-libs/webrick/cgi.rb +1 -1
- data/spec/framework_spec/extensions/test-libs/webrick/config.rb +1 -1
- data/spec/framework_spec/extensions/test-libs/webrick/httpauth/digestauth.rb +1 -1
- data/spec/framework_spec/extensions/test-libs/webrick/httpresponse.rb +1 -1
- data/spec/framework_spec/extensions/test-libs/webrick/https.rb +2 -2
- data/spec/framework_spec/extensions/test-libs/webrick/httpservlet/abstract.rb +1 -2
- data/spec/framework_spec/extensions/test-libs/webrick/httpservlet/cgihandler.rb +2 -2
- data/spec/framework_spec/extensions/test-libs/webrick/httpservlet/filehandler.rb +9 -5
- data/spec/framework_spec/extensions/test-libs/webrick/httpstatus.rb +32 -321
- data/spec/framework_spec/extensions/test-libs/webrick/httputils.rb +3 -3
- data/spec/framework_spec/extensions/test-libs/webrick/ssl.rb +3 -2
- data/spec/phone_spec/build.yml +1 -1
- data/version +1 -0
- metadata +521 -27
- data/lib/extensions/net-http/monitor.rb +0 -265
- data/lib/extensions/net-http/thread.rb +0 -367
- data/lib/extensions/net-http/timeout.rb +0 -114
- data/lib/extensions/net-http/uri.rb +0 -29
- data/lib/extensions/net-http/uri/common.rb +0 -727
- data/lib/extensions/net-http/uri/ftp.rb +0 -198
- data/lib/extensions/net-http/uri/generic.rb +0 -1128
- data/lib/extensions/net-http/uri/http.rb +0 -100
- data/lib/extensions/net-http/uri/https.rb +0 -20
- data/lib/extensions/net-http/uri/ldap.rb +0 -190
- data/lib/extensions/net-http/uri/ldaps.rb +0 -12
- data/lib/extensions/net-http/uri/mailto.rb +0 -266
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/Frameworks/QtDBus.framework/Versions/4/QtDBus +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/Frameworks/QtXml.framework/Versions/4/QtXml +0 -0
- data/platform/osx/bin/RhoSimulator/RhoSimulator.app/Contents/PlugIns/qmltooling/libtcpserver.dylib +0 -0
- data/res/generators/templates/application/public/jqmobile/images/icon-search-black.png +0 -0
- data/res/generators/templates/application/public/jqmobile/jquery.mobile-1.0b3.min.css +0 -8
- data/res/generators/templates/application/public/jqmobile/jquery.mobile-1.0b3.min.js +0 -169
- data/res/generators/templates/application/public/jquery/jquery-1.6.3.min.js +0 -4
- data/spec/framework_spec/extensions/test-libs/thread.rb +0 -391
|
@@ -0,0 +1,306 @@
|
|
|
1
|
+
#ifndef RUBY_SOCKET_H
|
|
2
|
+
#define RUBY_SOCKET_H 1
|
|
3
|
+
|
|
4
|
+
#include "ruby/ruby.h"
|
|
5
|
+
#include "ruby/io.h"
|
|
6
|
+
#include "ruby/util.h"
|
|
7
|
+
#include <stdio.h>
|
|
8
|
+
#include <sys/types.h>
|
|
9
|
+
#include <sys/stat.h>
|
|
10
|
+
|
|
11
|
+
#ifdef HAVE_UNISTD_H
|
|
12
|
+
#include <unistd.h>
|
|
13
|
+
#endif
|
|
14
|
+
|
|
15
|
+
#ifdef HAVE_SYS_UIO_H
|
|
16
|
+
#include <sys/uio.h>
|
|
17
|
+
#endif
|
|
18
|
+
|
|
19
|
+
#ifdef HAVE_XTI_H
|
|
20
|
+
#include <xti.h>
|
|
21
|
+
#endif
|
|
22
|
+
|
|
23
|
+
#ifndef _WIN32
|
|
24
|
+
#if defined(__BEOS__) && !defined(__HAIKU__) && !defined(BONE)
|
|
25
|
+
# include <net/socket.h>
|
|
26
|
+
#else
|
|
27
|
+
# include <sys/socket.h>
|
|
28
|
+
#endif
|
|
29
|
+
#include <netinet/in.h>
|
|
30
|
+
#ifdef HAVE_NETINET_IN_SYSTM_H
|
|
31
|
+
# include <netinet/in_systm.h>
|
|
32
|
+
#endif
|
|
33
|
+
#ifdef HAVE_NETINET_TCP_H
|
|
34
|
+
# include <netinet/tcp.h>
|
|
35
|
+
#endif
|
|
36
|
+
#ifdef HAVE_NETINET_UDP_H
|
|
37
|
+
# include <netinet/udp.h>
|
|
38
|
+
#endif
|
|
39
|
+
#ifdef HAVE_ARPA_INET_H
|
|
40
|
+
# include <arpa/inet.h>
|
|
41
|
+
#endif
|
|
42
|
+
#include <netdb.h>
|
|
43
|
+
#endif
|
|
44
|
+
#include <errno.h>
|
|
45
|
+
#ifdef HAVE_SYS_UN_H
|
|
46
|
+
#include <sys/un.h>
|
|
47
|
+
#endif
|
|
48
|
+
|
|
49
|
+
#if defined(HAVE_FCNTL)
|
|
50
|
+
#ifdef HAVE_SYS_SELECT_H
|
|
51
|
+
#include <sys/select.h>
|
|
52
|
+
#endif
|
|
53
|
+
#ifdef HAVE_SYS_TYPES_H
|
|
54
|
+
#include <sys/types.h>
|
|
55
|
+
#endif
|
|
56
|
+
#ifdef HAVE_SYS_TIME_H
|
|
57
|
+
#include <sys/time.h>
|
|
58
|
+
#endif
|
|
59
|
+
#ifdef HAVE_FCNTL_H
|
|
60
|
+
#include <fcntl.h>
|
|
61
|
+
#endif
|
|
62
|
+
#endif
|
|
63
|
+
|
|
64
|
+
#ifdef HAVE_IFADDRS_H
|
|
65
|
+
#include <ifaddrs.h>
|
|
66
|
+
#endif
|
|
67
|
+
#ifdef HAVE_SYS_IOCTL_H
|
|
68
|
+
#include <sys/ioctl.h>
|
|
69
|
+
#endif
|
|
70
|
+
#ifdef HAVE_SYS_SOCKIO_H
|
|
71
|
+
#include <sys/sockio.h>
|
|
72
|
+
#endif
|
|
73
|
+
#ifdef HAVE_NET_IF_H
|
|
74
|
+
#include <net/if.h>
|
|
75
|
+
#endif
|
|
76
|
+
|
|
77
|
+
#ifdef HAVE_SYS_PARAM_H
|
|
78
|
+
#include <sys/param.h>
|
|
79
|
+
#endif
|
|
80
|
+
#ifdef HAVE_SYS_UCRED_H
|
|
81
|
+
#include <sys/ucred.h>
|
|
82
|
+
#endif
|
|
83
|
+
#ifdef HAVE_UCRED_H
|
|
84
|
+
#include <ucred.h>
|
|
85
|
+
#endif
|
|
86
|
+
|
|
87
|
+
#ifndef EWOULDBLOCK
|
|
88
|
+
#define EWOULDBLOCK EAGAIN
|
|
89
|
+
#endif
|
|
90
|
+
|
|
91
|
+
/*
|
|
92
|
+
* workaround for NetBSD, OpenBSD and etc.
|
|
93
|
+
* The problem is since 4.4BSD-Lite.
|
|
94
|
+
* FreeBSD fix the problem at FreeBSD 2.2.0.
|
|
95
|
+
* NetBSD fix the problem at NetBSD 3.0 by kern/29624.
|
|
96
|
+
* OpenBSD fix the problem at OpenBSD 3.8.
|
|
97
|
+
*/
|
|
98
|
+
#define pseudo_AF_FTIP pseudo_AF_RTIP
|
|
99
|
+
|
|
100
|
+
#ifndef HAVE_GETADDRINFO
|
|
101
|
+
#include "addrinfo.h"
|
|
102
|
+
#endif
|
|
103
|
+
#include "sockport.h"
|
|
104
|
+
|
|
105
|
+
#ifndef NI_MAXHOST
|
|
106
|
+
# define NI_MAXHOST 1025
|
|
107
|
+
#endif
|
|
108
|
+
#ifndef NI_MAXSERV
|
|
109
|
+
# define NI_MAXSERV 32
|
|
110
|
+
#endif
|
|
111
|
+
|
|
112
|
+
#ifdef AF_INET6
|
|
113
|
+
# define IS_IP_FAMILY(af) ((af) == AF_INET || (af) == AF_INET6)
|
|
114
|
+
#else
|
|
115
|
+
# define IS_IP_FAMILY(af) ((af) == AF_INET)
|
|
116
|
+
#endif
|
|
117
|
+
|
|
118
|
+
#ifndef HAVE_SOCKADDR_STORAGE
|
|
119
|
+
/*
|
|
120
|
+
* RFC 2553: protocol-independent placeholder for socket addresses
|
|
121
|
+
*/
|
|
122
|
+
#define _SS_MAXSIZE 128
|
|
123
|
+
#define _SS_ALIGNSIZE (sizeof(double))
|
|
124
|
+
#define _SS_PAD1SIZE (_SS_ALIGNSIZE - sizeof(unsigned char) * 2)
|
|
125
|
+
#define _SS_PAD2SIZE (_SS_MAXSIZE - sizeof(unsigned char) * 2 - \
|
|
126
|
+
_SS_PAD1SIZE - _SS_ALIGNSIZE)
|
|
127
|
+
|
|
128
|
+
struct sockaddr_storage {
|
|
129
|
+
#ifdef HAVE_SA_LEN
|
|
130
|
+
unsigned char ss_len; /* address length */
|
|
131
|
+
unsigned char ss_family; /* address family */
|
|
132
|
+
#else
|
|
133
|
+
unsigned short ss_family;
|
|
134
|
+
#endif
|
|
135
|
+
char __ss_pad1[_SS_PAD1SIZE];
|
|
136
|
+
double __ss_align; /* force desired structure storage alignment */
|
|
137
|
+
char __ss_pad2[_SS_PAD2SIZE];
|
|
138
|
+
};
|
|
139
|
+
#endif
|
|
140
|
+
|
|
141
|
+
#if defined __APPLE__ && defined __MACH__
|
|
142
|
+
/*
|
|
143
|
+
* CMSG_ macros are broken on 64bit darwin, because __DARWIN_ALIGN
|
|
144
|
+
* aligns up to __darwin_size_t which is 64bit, but CMSG_DATA is
|
|
145
|
+
* 32bit-aligned.
|
|
146
|
+
*/
|
|
147
|
+
#undef __DARWIN_ALIGNBYTES
|
|
148
|
+
#define __DARWIN_ALIGNBYTES (sizeof(unsigned int) - 1)
|
|
149
|
+
#endif
|
|
150
|
+
|
|
151
|
+
#if defined(_AIX)
|
|
152
|
+
#ifndef CMSG_SPACE
|
|
153
|
+
# define CMSG_SPACE(len) (_CMSG_ALIGN(sizeof(struct cmsghdr)) + _CMSG_ALIGN(len))
|
|
154
|
+
#endif
|
|
155
|
+
#ifndef CMSG_LEN
|
|
156
|
+
# define CMSG_LEN(len) (_CMSG_ALIGN(sizeof(struct cmsghdr)) + (len))
|
|
157
|
+
#endif
|
|
158
|
+
#endif
|
|
159
|
+
|
|
160
|
+
#ifdef __BEOS__
|
|
161
|
+
#undef close
|
|
162
|
+
#define close closesocket
|
|
163
|
+
#endif
|
|
164
|
+
|
|
165
|
+
#define INET_CLIENT 0
|
|
166
|
+
#define INET_SERVER 1
|
|
167
|
+
#define INET_SOCKS 2
|
|
168
|
+
|
|
169
|
+
extern int rsock_do_not_reverse_lookup;
|
|
170
|
+
#define FMODE_NOREVLOOKUP 0x100
|
|
171
|
+
|
|
172
|
+
extern VALUE rb_cBasicSocket;
|
|
173
|
+
extern VALUE rb_cIPSocket;
|
|
174
|
+
extern VALUE rb_cTCPSocket;
|
|
175
|
+
extern VALUE rb_cTCPServer;
|
|
176
|
+
extern VALUE rb_cUDPSocket;
|
|
177
|
+
#ifdef HAVE_SYS_UN_H
|
|
178
|
+
extern VALUE rb_cUNIXSocket;
|
|
179
|
+
extern VALUE rb_cUNIXServer;
|
|
180
|
+
#endif
|
|
181
|
+
extern VALUE rb_cSocket;
|
|
182
|
+
extern VALUE rb_cAddrinfo;
|
|
183
|
+
extern VALUE rb_cSockOpt;
|
|
184
|
+
|
|
185
|
+
extern VALUE rb_eSocket;
|
|
186
|
+
|
|
187
|
+
#ifdef SOCKS
|
|
188
|
+
extern VALUE rb_cSOCKSSocket;
|
|
189
|
+
#ifdef SOCKS5
|
|
190
|
+
#include <socks.h>
|
|
191
|
+
#else
|
|
192
|
+
void SOCKSinit();
|
|
193
|
+
int Rconnect();
|
|
194
|
+
#endif
|
|
195
|
+
#endif
|
|
196
|
+
|
|
197
|
+
#include "ruby/constdefs.h"
|
|
198
|
+
|
|
199
|
+
#define BLOCKING_REGION(func, arg) (long)rb_thread_blocking_region((func), (arg), RUBY_UBF_IO, 0)
|
|
200
|
+
|
|
201
|
+
#define SockAddrStringValue(v) rsock_sockaddr_string_value(&(v))
|
|
202
|
+
#define SockAddrStringValuePtr(v) rsock_sockaddr_string_value_ptr(&(v))
|
|
203
|
+
VALUE rsock_sockaddr_string_value(volatile VALUE *);
|
|
204
|
+
char *rsock_sockaddr_string_value_ptr(volatile VALUE *);
|
|
205
|
+
VALUE rb_check_sockaddr_string_type(VALUE);
|
|
206
|
+
|
|
207
|
+
NORETURN(void rsock_raise_socket_error(const char *, int));
|
|
208
|
+
|
|
209
|
+
int rsock_family_arg(VALUE domain);
|
|
210
|
+
int rsock_socktype_arg(VALUE type);
|
|
211
|
+
int rsock_level_arg(int family, VALUE level);
|
|
212
|
+
int rsock_optname_arg(int family, int level, VALUE optname);
|
|
213
|
+
int rsock_cmsg_type_arg(int family, int level, VALUE type);
|
|
214
|
+
int rsock_shutdown_how_arg(VALUE how);
|
|
215
|
+
|
|
216
|
+
int rsock_getfamily(int sockfd);
|
|
217
|
+
|
|
218
|
+
int rb_getaddrinfo(const char *node, const char *service, const struct addrinfo *hints, struct addrinfo **res);
|
|
219
|
+
int rb_getnameinfo(const struct sockaddr *sa, socklen_t salen, char *host, size_t hostlen, char *serv, size_t servlen, int flags);
|
|
220
|
+
struct addrinfo *rsock_addrinfo(VALUE host, VALUE port, int socktype, int flags);
|
|
221
|
+
struct addrinfo *rsock_getaddrinfo(VALUE host, VALUE port, struct addrinfo *hints, int socktype_hack);
|
|
222
|
+
VALUE rsock_fd_socket_addrinfo(int fd, struct sockaddr *addr, socklen_t len);
|
|
223
|
+
VALUE rsock_io_socket_addrinfo(VALUE io, struct sockaddr *addr, socklen_t len);
|
|
224
|
+
|
|
225
|
+
VALUE rsock_addrinfo_new(struct sockaddr *addr, socklen_t len, int family, int socktype, int protocol, VALUE canonname, VALUE inspectname);
|
|
226
|
+
|
|
227
|
+
VALUE rsock_make_ipaddr(struct sockaddr *addr);
|
|
228
|
+
VALUE rsock_ipaddr(struct sockaddr *sockaddr, int norevlookup);
|
|
229
|
+
VALUE rsock_make_hostent(VALUE host, struct addrinfo *addr, VALUE (*ipaddr)(struct sockaddr *, size_t));
|
|
230
|
+
|
|
231
|
+
int rsock_revlookup_flag(VALUE revlookup, int *norevlookup);
|
|
232
|
+
|
|
233
|
+
#ifdef HAVE_SYS_UN_H
|
|
234
|
+
const char* rsock_unixpath(struct sockaddr_un *sockaddr, socklen_t len);
|
|
235
|
+
VALUE rsock_unixaddr(struct sockaddr_un *sockaddr, socklen_t len);
|
|
236
|
+
#endif
|
|
237
|
+
|
|
238
|
+
int rsock_socket(int domain, int type, int proto);
|
|
239
|
+
VALUE rsock_init_sock(VALUE sock, int fd);
|
|
240
|
+
VALUE rsock_sock_s_socketpair(int argc, VALUE *argv, VALUE klass);
|
|
241
|
+
VALUE rsock_init_inetsock(VALUE sock, VALUE remote_host, VALUE remote_serv, VALUE local_host, VALUE local_serv, int type);
|
|
242
|
+
VALUE rsock_init_unixsock(VALUE sock, VALUE path, int server);
|
|
243
|
+
|
|
244
|
+
struct rsock_send_arg {
|
|
245
|
+
int fd, flags;
|
|
246
|
+
VALUE mesg;
|
|
247
|
+
struct sockaddr *to;
|
|
248
|
+
socklen_t tolen;
|
|
249
|
+
};
|
|
250
|
+
|
|
251
|
+
VALUE rsock_sendto_blocking(void *data);
|
|
252
|
+
VALUE rsock_send_blocking(void *data);
|
|
253
|
+
VALUE rsock_bsock_send(int argc, VALUE *argv, VALUE sock);
|
|
254
|
+
|
|
255
|
+
enum sock_recv_type {
|
|
256
|
+
RECV_RECV, /* BasicSocket#recv(no from) */
|
|
257
|
+
RECV_IP, /* IPSocket#recvfrom */
|
|
258
|
+
RECV_UNIX, /* UNIXSocket#recvfrom */
|
|
259
|
+
RECV_SOCKET /* Socket#recvfrom */
|
|
260
|
+
};
|
|
261
|
+
|
|
262
|
+
VALUE rsock_s_recvfrom_nonblock(VALUE sock, int argc, VALUE *argv, enum sock_recv_type from);
|
|
263
|
+
VALUE rsock_s_recvfrom(VALUE sock, int argc, VALUE *argv, enum sock_recv_type from);
|
|
264
|
+
|
|
265
|
+
int rsock_connect(int fd, const struct sockaddr *sockaddr, int len, int socks);
|
|
266
|
+
|
|
267
|
+
VALUE rsock_s_accept(VALUE klass, int fd, struct sockaddr *sockaddr, socklen_t *len);
|
|
268
|
+
VALUE rsock_s_accept_nonblock(VALUE klass, rb_io_t *fptr, struct sockaddr *sockaddr, socklen_t *len);
|
|
269
|
+
VALUE rsock_sock_listen(VALUE sock, VALUE log);
|
|
270
|
+
|
|
271
|
+
VALUE rsock_sockopt_new(int family, int level, int optname, VALUE data);
|
|
272
|
+
|
|
273
|
+
#if defined(HAVE_SENDMSG)
|
|
274
|
+
VALUE rsock_bsock_sendmsg(int argc, VALUE *argv, VALUE sock);
|
|
275
|
+
VALUE rsock_bsock_sendmsg_nonblock(int argc, VALUE *argv, VALUE sock);
|
|
276
|
+
#else
|
|
277
|
+
#define rsock_bsock_sendmsg rb_f_notimplement
|
|
278
|
+
#define rsock_bsock_sendmsg_nonblock rb_f_notimplement
|
|
279
|
+
#endif
|
|
280
|
+
#if defined(HAVE_RECVMSG)
|
|
281
|
+
VALUE rsock_bsock_recvmsg(int argc, VALUE *argv, VALUE sock);
|
|
282
|
+
VALUE rsock_bsock_recvmsg_nonblock(int argc, VALUE *argv, VALUE sock);
|
|
283
|
+
#else
|
|
284
|
+
#define rsock_bsock_recvmsg rb_f_notimplement
|
|
285
|
+
#define rsock_bsock_recvmsg_nonblock rb_f_notimplement
|
|
286
|
+
#endif
|
|
287
|
+
|
|
288
|
+
#ifdef HAVE_ST_MSG_CONTROL
|
|
289
|
+
void rsock_discard_cmsg_resource(struct msghdr *mh);
|
|
290
|
+
#endif
|
|
291
|
+
|
|
292
|
+
void rsock_init_basicsocket(void);
|
|
293
|
+
void rsock_init_ipsocket(void);
|
|
294
|
+
void rsock_init_tcpsocket(void);
|
|
295
|
+
void rsock_init_tcpserver(void);
|
|
296
|
+
void rsock_init_sockssocket(void);
|
|
297
|
+
void rsock_init_udpsocket(void);
|
|
298
|
+
void rsock_init_unixsocket(void);
|
|
299
|
+
void rsock_init_unixserver(void);
|
|
300
|
+
void rsock_init_socket_constants(void);
|
|
301
|
+
void rsock_init_ancdata(void);
|
|
302
|
+
void rsock_init_addrinfo(void);
|
|
303
|
+
void rsock_init_sockopt(void);
|
|
304
|
+
void rsock_init_socket_init(void);
|
|
305
|
+
|
|
306
|
+
#endif
|
|
@@ -0,0 +1,1870 @@
|
|
|
1
|
+
/************************************************
|
|
2
|
+
|
|
3
|
+
socket.c -
|
|
4
|
+
|
|
5
|
+
created at: Thu Mar 31 12:21:29 JST 1994
|
|
6
|
+
|
|
7
|
+
Copyright (C) 1993-2007 Yukihiro Matsumoto
|
|
8
|
+
|
|
9
|
+
************************************************/
|
|
10
|
+
|
|
11
|
+
#include "rubysocket.h"
|
|
12
|
+
|
|
13
|
+
static void
|
|
14
|
+
setup_domain_and_type(VALUE domain, int *dv, VALUE type, int *tv)
|
|
15
|
+
{
|
|
16
|
+
*dv = rsock_family_arg(domain);
|
|
17
|
+
*tv = rsock_socktype_arg(type);
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
/*
|
|
21
|
+
* call-seq:
|
|
22
|
+
* Socket.new(domain, socktype [, protocol]) => socket
|
|
23
|
+
*
|
|
24
|
+
* Creates a new socket object.
|
|
25
|
+
*
|
|
26
|
+
* _domain_ should be a communications domain such as: :INET, :INET6, :UNIX, etc.
|
|
27
|
+
*
|
|
28
|
+
* _socktype_ should be a socket type such as: :STREAM, :DGRAM, :RAW, etc.
|
|
29
|
+
*
|
|
30
|
+
* _protocol_ should be a protocol defined in the domain.
|
|
31
|
+
* This is optional.
|
|
32
|
+
* If it is not given, 0 is used internally.
|
|
33
|
+
*
|
|
34
|
+
* Socket.new(:INET, :STREAM) # TCP socket
|
|
35
|
+
* Socket.new(:INET, :DGRAM) # UDP socket
|
|
36
|
+
* Socket.new(:UNIX, :STREAM) # UNIX stream socket
|
|
37
|
+
* Socket.new(:UNIX, :DGRAM) # UNIX datagram socket
|
|
38
|
+
*/
|
|
39
|
+
static VALUE
|
|
40
|
+
sock_initialize(int argc, VALUE *argv, VALUE sock)
|
|
41
|
+
{
|
|
42
|
+
VALUE domain, type, protocol;
|
|
43
|
+
int fd;
|
|
44
|
+
int d, t;
|
|
45
|
+
|
|
46
|
+
rb_scan_args(argc, argv, "21", &domain, &type, &protocol);
|
|
47
|
+
if (NIL_P(protocol))
|
|
48
|
+
protocol = INT2FIX(0);
|
|
49
|
+
|
|
50
|
+
rb_secure(3);
|
|
51
|
+
setup_domain_and_type(domain, &d, type, &t);
|
|
52
|
+
fd = rsock_socket(d, t, NUM2INT(protocol));
|
|
53
|
+
if (fd < 0) rb_sys_fail("socket(2)");
|
|
54
|
+
|
|
55
|
+
return rsock_init_sock(sock, fd);
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
#if defined HAVE_SOCKETPAIR
|
|
59
|
+
static VALUE
|
|
60
|
+
io_call_close(VALUE io)
|
|
61
|
+
{
|
|
62
|
+
return rb_funcall(io, rb_intern("close"), 0, 0);
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
static VALUE
|
|
66
|
+
io_close(VALUE io)
|
|
67
|
+
{
|
|
68
|
+
return rb_rescue(io_call_close, io, 0, 0);
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
static VALUE
|
|
72
|
+
pair_yield(VALUE pair)
|
|
73
|
+
{
|
|
74
|
+
return rb_ensure(rb_yield, pair, io_close, rb_ary_entry(pair, 1));
|
|
75
|
+
}
|
|
76
|
+
#endif
|
|
77
|
+
|
|
78
|
+
#if defined HAVE_SOCKETPAIR
|
|
79
|
+
/*
|
|
80
|
+
* call-seq:
|
|
81
|
+
* Socket.pair(domain, type, protocol) => [socket1, socket2]
|
|
82
|
+
* Socket.socketpair(domain, type, protocol) => [socket1, socket2]
|
|
83
|
+
*
|
|
84
|
+
* Creates a pair of sockets connected each other.
|
|
85
|
+
*
|
|
86
|
+
* _domain_ should be a communications domain such as: :INET, :INET6, :UNIX, etc.
|
|
87
|
+
*
|
|
88
|
+
* _socktype_ should be a socket type such as: :STREAM, :DGRAM, :RAW, etc.
|
|
89
|
+
*
|
|
90
|
+
* _protocol_ should be a protocol defined in the domain.
|
|
91
|
+
* 0 is default protocol for the domain.
|
|
92
|
+
*
|
|
93
|
+
* s1, s2 = Socket.pair(:UNIX, :DGRAM, 0)
|
|
94
|
+
* s1.send "a", 0
|
|
95
|
+
* s1.send "b", 0
|
|
96
|
+
* p s2.recv(10) #=> "a"
|
|
97
|
+
* p s2.recv(10) #=> "b"
|
|
98
|
+
*
|
|
99
|
+
*/
|
|
100
|
+
VALUE
|
|
101
|
+
rsock_sock_s_socketpair(int argc, VALUE *argv, VALUE klass)
|
|
102
|
+
{
|
|
103
|
+
VALUE domain, type, protocol;
|
|
104
|
+
int d, t, p, sp[2];
|
|
105
|
+
int ret;
|
|
106
|
+
VALUE s1, s2, r;
|
|
107
|
+
|
|
108
|
+
rb_scan_args(argc, argv, "21", &domain, &type, &protocol);
|
|
109
|
+
if (NIL_P(protocol))
|
|
110
|
+
protocol = INT2FIX(0);
|
|
111
|
+
|
|
112
|
+
setup_domain_and_type(domain, &d, type, &t);
|
|
113
|
+
p = NUM2INT(protocol);
|
|
114
|
+
ret = socketpair(d, t, p, sp);
|
|
115
|
+
if (ret < 0 && (errno == EMFILE || errno == ENFILE)) {
|
|
116
|
+
rb_gc();
|
|
117
|
+
ret = socketpair(d, t, p, sp);
|
|
118
|
+
}
|
|
119
|
+
if (ret < 0) {
|
|
120
|
+
rb_sys_fail("socketpair(2)");
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
s1 = rsock_init_sock(rb_obj_alloc(klass), sp[0]);
|
|
124
|
+
s2 = rsock_init_sock(rb_obj_alloc(klass), sp[1]);
|
|
125
|
+
r = rb_assoc_new(s1, s2);
|
|
126
|
+
if (rb_block_given_p()) {
|
|
127
|
+
return rb_ensure(pair_yield, r, io_close, s1);
|
|
128
|
+
}
|
|
129
|
+
return r;
|
|
130
|
+
}
|
|
131
|
+
#else
|
|
132
|
+
#define rsock_sock_s_socketpair rb_f_notimplement
|
|
133
|
+
#endif
|
|
134
|
+
|
|
135
|
+
/*
|
|
136
|
+
* call-seq:
|
|
137
|
+
* socket.connect(remote_sockaddr) => 0
|
|
138
|
+
*
|
|
139
|
+
* Requests a connection to be made on the given +remote_sockaddr+. Returns 0 if
|
|
140
|
+
* successful, otherwise an exception is raised.
|
|
141
|
+
*
|
|
142
|
+
* === Parameter
|
|
143
|
+
* * +remote_sockaddr+ - the +struct+ sockaddr contained in a string or Addrinfo object
|
|
144
|
+
*
|
|
145
|
+
* === Example:
|
|
146
|
+
* # Pull down Google's web page
|
|
147
|
+
* require 'socket'
|
|
148
|
+
* include Socket::Constants
|
|
149
|
+
* socket = Socket.new( AF_INET, SOCK_STREAM, 0 )
|
|
150
|
+
* sockaddr = Socket.pack_sockaddr_in( 80, 'www.google.com' )
|
|
151
|
+
* socket.connect( sockaddr )
|
|
152
|
+
* socket.write( "GET / HTTP/1.0\r\n\r\n" )
|
|
153
|
+
* results = socket.read
|
|
154
|
+
*
|
|
155
|
+
* === Unix-based Exceptions
|
|
156
|
+
* On unix-based systems the following system exceptions may be raised if
|
|
157
|
+
* the call to _connect_ fails:
|
|
158
|
+
* * Errno::EACCES - search permission is denied for a component of the prefix
|
|
159
|
+
* path or write access to the +socket+ is denied
|
|
160
|
+
* * Errno::EADDRINUSE - the _sockaddr_ is already in use
|
|
161
|
+
* * Errno::EADDRNOTAVAIL - the specified _sockaddr_ is not available from the
|
|
162
|
+
* local machine
|
|
163
|
+
* * Errno::EAFNOSUPPORT - the specified _sockaddr_ is not a valid address for
|
|
164
|
+
* the address family of the specified +socket+
|
|
165
|
+
* * Errno::EALREADY - a connection is already in progress for the specified
|
|
166
|
+
* socket
|
|
167
|
+
* * Errno::EBADF - the +socket+ is not a valid file descriptor
|
|
168
|
+
* * Errno::ECONNREFUSED - the target _sockaddr_ was not listening for connections
|
|
169
|
+
* refused the connection request
|
|
170
|
+
* * Errno::ECONNRESET - the remote host reset the connection request
|
|
171
|
+
* * Errno::EFAULT - the _sockaddr_ cannot be accessed
|
|
172
|
+
* * Errno::EHOSTUNREACH - the destination host cannot be reached (probably
|
|
173
|
+
* because the host is down or a remote router cannot reach it)
|
|
174
|
+
* * Errno::EINPROGRESS - the O_NONBLOCK is set for the +socket+ and the
|
|
175
|
+
* connection cannot be immediately established; the connection will be
|
|
176
|
+
* established asynchronously
|
|
177
|
+
* * Errno::EINTR - the attempt to establish the connection was interrupted by
|
|
178
|
+
* delivery of a signal that was caught; the connection will be established
|
|
179
|
+
* asynchronously
|
|
180
|
+
* * Errno::EISCONN - the specified +socket+ is already connected
|
|
181
|
+
* * Errno::EINVAL - the address length used for the _sockaddr_ is not a valid
|
|
182
|
+
* length for the address family or there is an invalid family in _sockaddr_
|
|
183
|
+
* * Errno::ENAMETOOLONG - the pathname resolved had a length which exceeded
|
|
184
|
+
* PATH_MAX
|
|
185
|
+
* * Errno::ENETDOWN - the local interface used to reach the destination is down
|
|
186
|
+
* * Errno::ENETUNREACH - no route to the network is present
|
|
187
|
+
* * Errno::ENOBUFS - no buffer space is available
|
|
188
|
+
* * Errno::ENOSR - there were insufficient STREAMS resources available to
|
|
189
|
+
* complete the operation
|
|
190
|
+
* * Errno::ENOTSOCK - the +socket+ argument does not refer to a socket
|
|
191
|
+
* * Errno::EOPNOTSUPP - the calling +socket+ is listening and cannot be connected
|
|
192
|
+
* * Errno::EPROTOTYPE - the _sockaddr_ has a different type than the socket
|
|
193
|
+
* bound to the specified peer address
|
|
194
|
+
* * Errno::ETIMEDOUT - the attempt to connect time out before a connection
|
|
195
|
+
* was made.
|
|
196
|
+
*
|
|
197
|
+
* On unix-based systems if the address family of the calling +socket+ is
|
|
198
|
+
* AF_UNIX the follow exceptions may be raised if the call to _connect_
|
|
199
|
+
* fails:
|
|
200
|
+
* * Errno::EIO - an i/o error occurred while reading from or writing to the
|
|
201
|
+
* file system
|
|
202
|
+
* * Errno::ELOOP - too many symbolic links were encountered in translating
|
|
203
|
+
* the pathname in _sockaddr_
|
|
204
|
+
* * Errno::ENAMETOOLLONG - a component of a pathname exceeded NAME_MAX
|
|
205
|
+
* characters, or an entire pathname exceeded PATH_MAX characters
|
|
206
|
+
* * Errno::ENOENT - a component of the pathname does not name an existing file
|
|
207
|
+
* or the pathname is an empty string
|
|
208
|
+
* * Errno::ENOTDIR - a component of the path prefix of the pathname in _sockaddr_
|
|
209
|
+
* is not a directory
|
|
210
|
+
*
|
|
211
|
+
* === Windows Exceptions
|
|
212
|
+
* On Windows systems the following system exceptions may be raised if
|
|
213
|
+
* the call to _connect_ fails:
|
|
214
|
+
* * Errno::ENETDOWN - the network is down
|
|
215
|
+
* * Errno::EADDRINUSE - the socket's local address is already in use
|
|
216
|
+
* * Errno::EINTR - the socket was cancelled
|
|
217
|
+
* * Errno::EINPROGRESS - a blocking socket is in progress or the service provider
|
|
218
|
+
* is still processing a callback function. Or a nonblocking connect call is
|
|
219
|
+
* in progress on the +socket+.
|
|
220
|
+
* * Errno::EALREADY - see Errno::EINVAL
|
|
221
|
+
* * Errno::EADDRNOTAVAIL - the remote address is not a valid address, such as
|
|
222
|
+
* ADDR_ANY TODO check ADDRANY TO INADDR_ANY
|
|
223
|
+
* * Errno::EAFNOSUPPORT - addresses in the specified family cannot be used with
|
|
224
|
+
* with this +socket+
|
|
225
|
+
* * Errno::ECONNREFUSED - the target _sockaddr_ was not listening for connections
|
|
226
|
+
* refused the connection request
|
|
227
|
+
* * Errno::EFAULT - the socket's internal address or address length parameter
|
|
228
|
+
* is too small or is not a valid part of the user space address
|
|
229
|
+
* * Errno::EINVAL - the +socket+ is a listening socket
|
|
230
|
+
* * Errno::EISCONN - the +socket+ is already connected
|
|
231
|
+
* * Errno::ENETUNREACH - the network cannot be reached from this host at this time
|
|
232
|
+
* * Errno::EHOSTUNREACH - no route to the network is present
|
|
233
|
+
* * Errno::ENOBUFS - no buffer space is available
|
|
234
|
+
* * Errno::ENOTSOCK - the +socket+ argument does not refer to a socket
|
|
235
|
+
* * Errno::ETIMEDOUT - the attempt to connect time out before a connection
|
|
236
|
+
* was made.
|
|
237
|
+
* * Errno::EWOULDBLOCK - the socket is marked as nonblocking and the
|
|
238
|
+
* connection cannot be completed immediately
|
|
239
|
+
* * Errno::EACCES - the attempt to connect the datagram socket to the
|
|
240
|
+
* broadcast address failed
|
|
241
|
+
*
|
|
242
|
+
* === See
|
|
243
|
+
* * connect manual pages on unix-based systems
|
|
244
|
+
* * connect function in Microsoft's Winsock functions reference
|
|
245
|
+
*/
|
|
246
|
+
static VALUE
|
|
247
|
+
sock_connect(VALUE sock, VALUE addr)
|
|
248
|
+
{
|
|
249
|
+
rb_io_t *fptr;
|
|
250
|
+
int fd, n;
|
|
251
|
+
|
|
252
|
+
SockAddrStringValue(addr);
|
|
253
|
+
addr = rb_str_new4(addr);
|
|
254
|
+
GetOpenFile(sock, fptr);
|
|
255
|
+
fd = fptr->fd;
|
|
256
|
+
n = rsock_connect(fd, (struct sockaddr*)RSTRING_PTR(addr), RSTRING_LENINT(addr), 0);
|
|
257
|
+
if (n < 0) {
|
|
258
|
+
rb_sys_fail("connect(2)");
|
|
259
|
+
}
|
|
260
|
+
|
|
261
|
+
return INT2FIX(n);
|
|
262
|
+
}
|
|
263
|
+
|
|
264
|
+
/*
|
|
265
|
+
* call-seq:
|
|
266
|
+
* socket.connect_nonblock(remote_sockaddr) => 0
|
|
267
|
+
*
|
|
268
|
+
* Requests a connection to be made on the given +remote_sockaddr+ after
|
|
269
|
+
* O_NONBLOCK is set for the underlying file descriptor.
|
|
270
|
+
* Returns 0 if successful, otherwise an exception is raised.
|
|
271
|
+
*
|
|
272
|
+
* === Parameter
|
|
273
|
+
* * +remote_sockaddr+ - the +struct+ sockaddr contained in a string or Addrinfo object
|
|
274
|
+
*
|
|
275
|
+
* === Example:
|
|
276
|
+
* # Pull down Google's web page
|
|
277
|
+
* require 'socket'
|
|
278
|
+
* include Socket::Constants
|
|
279
|
+
* socket = Socket.new(AF_INET, SOCK_STREAM, 0)
|
|
280
|
+
* sockaddr = Socket.sockaddr_in(80, 'www.google.com')
|
|
281
|
+
* begin # emulate blocking connect
|
|
282
|
+
* socket.connect_nonblock(sockaddr)
|
|
283
|
+
* rescue IO::WaitWritable
|
|
284
|
+
* IO.select(nil, [socket]) # wait 3-way handshake completion
|
|
285
|
+
* begin
|
|
286
|
+
* socket.connect_nonblock(sockaddr) # check connection failure
|
|
287
|
+
* rescue Errno::EISCONN
|
|
288
|
+
* end
|
|
289
|
+
* end
|
|
290
|
+
* socket.write("GET / HTTP/1.0\r\n\r\n")
|
|
291
|
+
* results = socket.read
|
|
292
|
+
*
|
|
293
|
+
* Refer to Socket#connect for the exceptions that may be thrown if the call
|
|
294
|
+
* to _connect_nonblock_ fails.
|
|
295
|
+
*
|
|
296
|
+
* Socket#connect_nonblock may raise any error corresponding to connect(2) failure,
|
|
297
|
+
* including Errno::EINPROGRESS.
|
|
298
|
+
*
|
|
299
|
+
* If the exception is Errno::EINPROGRESS,
|
|
300
|
+
* it is extended by IO::WaitWritable.
|
|
301
|
+
* So IO::WaitWritable can be used to rescue the exceptions for retrying connect_nonblock.
|
|
302
|
+
*
|
|
303
|
+
* === See
|
|
304
|
+
* * Socket#connect
|
|
305
|
+
*/
|
|
306
|
+
static VALUE
|
|
307
|
+
sock_connect_nonblock(VALUE sock, VALUE addr)
|
|
308
|
+
{
|
|
309
|
+
rb_io_t *fptr;
|
|
310
|
+
int n;
|
|
311
|
+
|
|
312
|
+
SockAddrStringValue(addr);
|
|
313
|
+
addr = rb_str_new4(addr);
|
|
314
|
+
GetOpenFile(sock, fptr);
|
|
315
|
+
rb_io_set_nonblock(fptr);
|
|
316
|
+
n = connect(fptr->fd, (struct sockaddr*)RSTRING_PTR(addr), RSTRING_LENINT(addr));
|
|
317
|
+
if (n < 0) {
|
|
318
|
+
if (errno == EINPROGRESS)
|
|
319
|
+
rb_mod_sys_fail(rb_mWaitWritable, "connect(2) would block");
|
|
320
|
+
rb_sys_fail("connect(2)");
|
|
321
|
+
}
|
|
322
|
+
|
|
323
|
+
return INT2FIX(n);
|
|
324
|
+
}
|
|
325
|
+
|
|
326
|
+
/*
|
|
327
|
+
* call-seq:
|
|
328
|
+
* socket.bind(local_sockaddr) => 0
|
|
329
|
+
*
|
|
330
|
+
* Binds to the given local address.
|
|
331
|
+
*
|
|
332
|
+
* === Parameter
|
|
333
|
+
* * +local_sockaddr+ - the +struct+ sockaddr contained in a string or an Addrinfo object
|
|
334
|
+
*
|
|
335
|
+
* === Example
|
|
336
|
+
* require 'socket'
|
|
337
|
+
*
|
|
338
|
+
* # use Addrinfo
|
|
339
|
+
* socket = Socket.new(:INET, :STREAM, 0)
|
|
340
|
+
* socket.bind(Addrinfo.tcp("127.0.0.1", 2222))
|
|
341
|
+
* p socket.local_address #=> #<Addrinfo: 127.0.0.1:2222 TCP>
|
|
342
|
+
*
|
|
343
|
+
* # use struct sockaddr
|
|
344
|
+
* include Socket::Constants
|
|
345
|
+
* socket = Socket.new( AF_INET, SOCK_STREAM, 0 )
|
|
346
|
+
* sockaddr = Socket.pack_sockaddr_in( 2200, 'localhost' )
|
|
347
|
+
* socket.bind( sockaddr )
|
|
348
|
+
*
|
|
349
|
+
* === Unix-based Exceptions
|
|
350
|
+
* On unix-based based systems the following system exceptions may be raised if
|
|
351
|
+
* the call to _bind_ fails:
|
|
352
|
+
* * Errno::EACCES - the specified _sockaddr_ is protected and the current
|
|
353
|
+
* user does not have permission to bind to it
|
|
354
|
+
* * Errno::EADDRINUSE - the specified _sockaddr_ is already in use
|
|
355
|
+
* * Errno::EADDRNOTAVAIL - the specified _sockaddr_ is not available from the
|
|
356
|
+
* local machine
|
|
357
|
+
* * Errno::EAFNOSUPPORT - the specified _sockaddr_ is not a valid address for
|
|
358
|
+
* the family of the calling +socket+
|
|
359
|
+
* * Errno::EBADF - the _sockaddr_ specified is not a valid file descriptor
|
|
360
|
+
* * Errno::EFAULT - the _sockaddr_ argument cannot be accessed
|
|
361
|
+
* * Errno::EINVAL - the +socket+ is already bound to an address, and the
|
|
362
|
+
* protocol does not support binding to the new _sockaddr_ or the +socket+
|
|
363
|
+
* has been shut down.
|
|
364
|
+
* * Errno::EINVAL - the address length is not a valid length for the address
|
|
365
|
+
* family
|
|
366
|
+
* * Errno::ENAMETOOLONG - the pathname resolved had a length which exceeded
|
|
367
|
+
* PATH_MAX
|
|
368
|
+
* * Errno::ENOBUFS - no buffer space is available
|
|
369
|
+
* * Errno::ENOSR - there were insufficient STREAMS resources available to
|
|
370
|
+
* complete the operation
|
|
371
|
+
* * Errno::ENOTSOCK - the +socket+ does not refer to a socket
|
|
372
|
+
* * Errno::EOPNOTSUPP - the socket type of the +socket+ does not support
|
|
373
|
+
* binding to an address
|
|
374
|
+
*
|
|
375
|
+
* On unix-based based systems if the address family of the calling +socket+ is
|
|
376
|
+
* Socket::AF_UNIX the follow exceptions may be raised if the call to _bind_
|
|
377
|
+
* fails:
|
|
378
|
+
* * Errno::EACCES - search permission is denied for a component of the prefix
|
|
379
|
+
* path or write access to the +socket+ is denied
|
|
380
|
+
* * Errno::EDESTADDRREQ - the _sockaddr_ argument is a null pointer
|
|
381
|
+
* * Errno::EISDIR - same as Errno::EDESTADDRREQ
|
|
382
|
+
* * Errno::EIO - an i/o error occurred
|
|
383
|
+
* * Errno::ELOOP - too many symbolic links were encountered in translating
|
|
384
|
+
* the pathname in _sockaddr_
|
|
385
|
+
* * Errno::ENAMETOOLLONG - a component of a pathname exceeded NAME_MAX
|
|
386
|
+
* characters, or an entire pathname exceeded PATH_MAX characters
|
|
387
|
+
* * Errno::ENOENT - a component of the pathname does not name an existing file
|
|
388
|
+
* or the pathname is an empty string
|
|
389
|
+
* * Errno::ENOTDIR - a component of the path prefix of the pathname in _sockaddr_
|
|
390
|
+
* is not a directory
|
|
391
|
+
* * Errno::EROFS - the name would reside on a read only filesystem
|
|
392
|
+
*
|
|
393
|
+
* === Windows Exceptions
|
|
394
|
+
* On Windows systems the following system exceptions may be raised if
|
|
395
|
+
* the call to _bind_ fails:
|
|
396
|
+
* * Errno::ENETDOWN-- the network is down
|
|
397
|
+
* * Errno::EACCES - the attempt to connect the datagram socket to the
|
|
398
|
+
* broadcast address failed
|
|
399
|
+
* * Errno::EADDRINUSE - the socket's local address is already in use
|
|
400
|
+
* * Errno::EADDRNOTAVAIL - the specified address is not a valid address for this
|
|
401
|
+
* computer
|
|
402
|
+
* * Errno::EFAULT - the socket's internal address or address length parameter
|
|
403
|
+
* is too small or is not a valid part of the user space addressed
|
|
404
|
+
* * Errno::EINVAL - the +socket+ is already bound to an address
|
|
405
|
+
* * Errno::ENOBUFS - no buffer space is available
|
|
406
|
+
* * Errno::ENOTSOCK - the +socket+ argument does not refer to a socket
|
|
407
|
+
*
|
|
408
|
+
* === See
|
|
409
|
+
* * bind manual pages on unix-based systems
|
|
410
|
+
* * bind function in Microsoft's Winsock functions reference
|
|
411
|
+
*/
|
|
412
|
+
static VALUE
|
|
413
|
+
sock_bind(VALUE sock, VALUE addr)
|
|
414
|
+
{
|
|
415
|
+
rb_io_t *fptr;
|
|
416
|
+
|
|
417
|
+
SockAddrStringValue(addr);
|
|
418
|
+
GetOpenFile(sock, fptr);
|
|
419
|
+
if (bind(fptr->fd, (struct sockaddr*)RSTRING_PTR(addr), RSTRING_LENINT(addr)) < 0)
|
|
420
|
+
rb_sys_fail("bind(2)");
|
|
421
|
+
|
|
422
|
+
return INT2FIX(0);
|
|
423
|
+
}
|
|
424
|
+
|
|
425
|
+
/*
|
|
426
|
+
* call-seq:
|
|
427
|
+
* socket.listen( int ) => 0
|
|
428
|
+
*
|
|
429
|
+
* Listens for connections, using the specified +int+ as the backlog. A call
|
|
430
|
+
* to _listen_ only applies if the +socket+ is of type SOCK_STREAM or
|
|
431
|
+
* SOCK_SEQPACKET.
|
|
432
|
+
*
|
|
433
|
+
* === Parameter
|
|
434
|
+
* * +backlog+ - the maximum length of the queue for pending connections.
|
|
435
|
+
*
|
|
436
|
+
* === Example 1
|
|
437
|
+
* require 'socket'
|
|
438
|
+
* include Socket::Constants
|
|
439
|
+
* socket = Socket.new( AF_INET, SOCK_STREAM, 0 )
|
|
440
|
+
* sockaddr = Socket.pack_sockaddr_in( 2200, 'localhost' )
|
|
441
|
+
* socket.bind( sockaddr )
|
|
442
|
+
* socket.listen( 5 )
|
|
443
|
+
*
|
|
444
|
+
* === Example 2 (listening on an arbitrary port, unix-based systems only):
|
|
445
|
+
* require 'socket'
|
|
446
|
+
* include Socket::Constants
|
|
447
|
+
* socket = Socket.new( AF_INET, SOCK_STREAM, 0 )
|
|
448
|
+
* socket.listen( 1 )
|
|
449
|
+
*
|
|
450
|
+
* === Unix-based Exceptions
|
|
451
|
+
* On unix based systems the above will work because a new +sockaddr+ struct
|
|
452
|
+
* is created on the address ADDR_ANY, for an arbitrary port number as handed
|
|
453
|
+
* off by the kernel. It will not work on Windows, because Windows requires that
|
|
454
|
+
* the +socket+ is bound by calling _bind_ before it can _listen_.
|
|
455
|
+
*
|
|
456
|
+
* If the _backlog_ amount exceeds the implementation-dependent maximum
|
|
457
|
+
* queue length, the implementation's maximum queue length will be used.
|
|
458
|
+
*
|
|
459
|
+
* On unix-based based systems the following system exceptions may be raised if the
|
|
460
|
+
* call to _listen_ fails:
|
|
461
|
+
* * Errno::EBADF - the _socket_ argument is not a valid file descriptor
|
|
462
|
+
* * Errno::EDESTADDRREQ - the _socket_ is not bound to a local address, and
|
|
463
|
+
* the protocol does not support listening on an unbound socket
|
|
464
|
+
* * Errno::EINVAL - the _socket_ is already connected
|
|
465
|
+
* * Errno::ENOTSOCK - the _socket_ argument does not refer to a socket
|
|
466
|
+
* * Errno::EOPNOTSUPP - the _socket_ protocol does not support listen
|
|
467
|
+
* * Errno::EACCES - the calling process does not have appropriate privileges
|
|
468
|
+
* * Errno::EINVAL - the _socket_ has been shut down
|
|
469
|
+
* * Errno::ENOBUFS - insufficient resources are available in the system to
|
|
470
|
+
* complete the call
|
|
471
|
+
*
|
|
472
|
+
* === Windows Exceptions
|
|
473
|
+
* On Windows systems the following system exceptions may be raised if
|
|
474
|
+
* the call to _listen_ fails:
|
|
475
|
+
* * Errno::ENETDOWN - the network is down
|
|
476
|
+
* * Errno::EADDRINUSE - the socket's local address is already in use. This
|
|
477
|
+
* usually occurs during the execution of _bind_ but could be delayed
|
|
478
|
+
* if the call to _bind_ was to a partially wildcard address (involving
|
|
479
|
+
* ADDR_ANY) and if a specific address needs to be committed at the
|
|
480
|
+
* time of the call to _listen_
|
|
481
|
+
* * Errno::EINPROGRESS - a Windows Sockets 1.1 call is in progress or the
|
|
482
|
+
* service provider is still processing a callback function
|
|
483
|
+
* * Errno::EINVAL - the +socket+ has not been bound with a call to _bind_.
|
|
484
|
+
* * Errno::EISCONN - the +socket+ is already connected
|
|
485
|
+
* * Errno::EMFILE - no more socket descriptors are available
|
|
486
|
+
* * Errno::ENOBUFS - no buffer space is available
|
|
487
|
+
* * Errno::ENOTSOC - +socket+ is not a socket
|
|
488
|
+
* * Errno::EOPNOTSUPP - the referenced +socket+ is not a type that supports
|
|
489
|
+
* the _listen_ method
|
|
490
|
+
*
|
|
491
|
+
* === See
|
|
492
|
+
* * listen manual pages on unix-based systems
|
|
493
|
+
* * listen function in Microsoft's Winsock functions reference
|
|
494
|
+
*/
|
|
495
|
+
VALUE
|
|
496
|
+
rsock_sock_listen(VALUE sock, VALUE log)
|
|
497
|
+
{
|
|
498
|
+
rb_io_t *fptr;
|
|
499
|
+
int backlog;
|
|
500
|
+
|
|
501
|
+
rb_secure(4);
|
|
502
|
+
backlog = NUM2INT(log);
|
|
503
|
+
GetOpenFile(sock, fptr);
|
|
504
|
+
if (listen(fptr->fd, backlog) < 0)
|
|
505
|
+
rb_sys_fail("listen(2)");
|
|
506
|
+
|
|
507
|
+
return INT2FIX(0);
|
|
508
|
+
}
|
|
509
|
+
|
|
510
|
+
/*
|
|
511
|
+
* call-seq:
|
|
512
|
+
* socket.recvfrom(maxlen) => [mesg, sender_addrinfo]
|
|
513
|
+
* socket.recvfrom(maxlen, flags) => [mesg, sender_addrinfo]
|
|
514
|
+
*
|
|
515
|
+
* Receives up to _maxlen_ bytes from +socket+. _flags_ is zero or more
|
|
516
|
+
* of the +MSG_+ options. The first element of the results, _mesg_, is the data
|
|
517
|
+
* received. The second element, _sender_addrinfo_, contains protocol-specific
|
|
518
|
+
* address information of the sender.
|
|
519
|
+
*
|
|
520
|
+
* === Parameters
|
|
521
|
+
* * +maxlen+ - the maximum number of bytes to receive from the socket
|
|
522
|
+
* * +flags+ - zero or more of the +MSG_+ options
|
|
523
|
+
*
|
|
524
|
+
* === Example
|
|
525
|
+
* # In one file, start this first
|
|
526
|
+
* require 'socket'
|
|
527
|
+
* include Socket::Constants
|
|
528
|
+
* socket = Socket.new( AF_INET, SOCK_STREAM, 0 )
|
|
529
|
+
* sockaddr = Socket.pack_sockaddr_in( 2200, 'localhost' )
|
|
530
|
+
* socket.bind( sockaddr )
|
|
531
|
+
* socket.listen( 5 )
|
|
532
|
+
* client, client_addrinfo = socket.accept
|
|
533
|
+
* data = client.recvfrom( 20 )[0].chomp
|
|
534
|
+
* puts "I only received 20 bytes '#{data}'"
|
|
535
|
+
* sleep 1
|
|
536
|
+
* socket.close
|
|
537
|
+
*
|
|
538
|
+
* # In another file, start this second
|
|
539
|
+
* require 'socket'
|
|
540
|
+
* include Socket::Constants
|
|
541
|
+
* socket = Socket.new( AF_INET, SOCK_STREAM, 0 )
|
|
542
|
+
* sockaddr = Socket.pack_sockaddr_in( 2200, 'localhost' )
|
|
543
|
+
* socket.connect( sockaddr )
|
|
544
|
+
* socket.puts "Watch this get cut short!"
|
|
545
|
+
* socket.close
|
|
546
|
+
*
|
|
547
|
+
* === Unix-based Exceptions
|
|
548
|
+
* On unix-based based systems the following system exceptions may be raised if the
|
|
549
|
+
* call to _recvfrom_ fails:
|
|
550
|
+
* * Errno::EAGAIN - the +socket+ file descriptor is marked as O_NONBLOCK and no
|
|
551
|
+
* data is waiting to be received; or MSG_OOB is set and no out-of-band data
|
|
552
|
+
* is available and either the +socket+ file descriptor is marked as
|
|
553
|
+
* O_NONBLOCK or the +socket+ does not support blocking to wait for
|
|
554
|
+
* out-of-band-data
|
|
555
|
+
* * Errno::EWOULDBLOCK - see Errno::EAGAIN
|
|
556
|
+
* * Errno::EBADF - the +socket+ is not a valid file descriptor
|
|
557
|
+
* * Errno::ECONNRESET - a connection was forcibly closed by a peer
|
|
558
|
+
* * Errno::EFAULT - the socket's internal buffer, address or address length
|
|
559
|
+
* cannot be accessed or written
|
|
560
|
+
* * Errno::EINTR - a signal interrupted _recvfrom_ before any data was available
|
|
561
|
+
* * Errno::EINVAL - the MSG_OOB flag is set and no out-of-band data is available
|
|
562
|
+
* * Errno::EIO - an i/o error occurred while reading from or writing to the
|
|
563
|
+
* filesystem
|
|
564
|
+
* * Errno::ENOBUFS - insufficient resources were available in the system to
|
|
565
|
+
* perform the operation
|
|
566
|
+
* * Errno::ENOMEM - insufficient memory was available to fulfill the request
|
|
567
|
+
* * Errno::ENOSR - there were insufficient STREAMS resources available to
|
|
568
|
+
* complete the operation
|
|
569
|
+
* * Errno::ENOTCONN - a receive is attempted on a connection-mode socket that
|
|
570
|
+
* is not connected
|
|
571
|
+
* * Errno::ENOTSOCK - the +socket+ does not refer to a socket
|
|
572
|
+
* * Errno::EOPNOTSUPP - the specified flags are not supported for this socket type
|
|
573
|
+
* * Errno::ETIMEDOUT - the connection timed out during connection establishment
|
|
574
|
+
* or due to a transmission timeout on an active connection
|
|
575
|
+
*
|
|
576
|
+
* === Windows Exceptions
|
|
577
|
+
* On Windows systems the following system exceptions may be raised if
|
|
578
|
+
* the call to _recvfrom_ fails:
|
|
579
|
+
* * Errno::ENETDOWN - the network is down
|
|
580
|
+
* * Errno::EFAULT - the internal buffer and from parameters on +socket+ are not
|
|
581
|
+
* part of the user address space, or the internal fromlen parameter is
|
|
582
|
+
* too small to accommodate the peer address
|
|
583
|
+
* * Errno::EINTR - the (blocking) call was cancelled by an internal call to
|
|
584
|
+
* the WinSock function WSACancelBlockingCall
|
|
585
|
+
* * Errno::EINPROGRESS - a blocking Windows Sockets 1.1 call is in progress or
|
|
586
|
+
* the service provider is still processing a callback function
|
|
587
|
+
* * Errno::EINVAL - +socket+ has not been bound with a call to _bind_, or an
|
|
588
|
+
* unknown flag was specified, or MSG_OOB was specified for a socket with
|
|
589
|
+
* SO_OOBINLINE enabled, or (for byte stream-style sockets only) the internal
|
|
590
|
+
* len parameter on +socket+ was zero or negative
|
|
591
|
+
* * Errno::EISCONN - +socket+ is already connected. The call to _recvfrom_ is
|
|
592
|
+
* not permitted with a connected socket on a socket that is connection
|
|
593
|
+
* oriented or connectionless.
|
|
594
|
+
* * Errno::ENETRESET - the connection has been broken due to the keep-alive
|
|
595
|
+
* activity detecting a failure while the operation was in progress.
|
|
596
|
+
* * Errno::EOPNOTSUPP - MSG_OOB was specified, but +socket+ is not stream-style
|
|
597
|
+
* such as type SOCK_STREAM. OOB data is not supported in the communication
|
|
598
|
+
* domain associated with +socket+, or +socket+ is unidirectional and
|
|
599
|
+
* supports only send operations
|
|
600
|
+
* * Errno::ESHUTDOWN - +socket+ has been shutdown. It is not possible to
|
|
601
|
+
* call _recvfrom_ on a socket after _shutdown_ has been invoked.
|
|
602
|
+
* * Errno::EWOULDBLOCK - +socket+ is marked as nonblocking and a call to
|
|
603
|
+
* _recvfrom_ would block.
|
|
604
|
+
* * Errno::EMSGSIZE - the message was too large to fit into the specified buffer
|
|
605
|
+
* and was truncated.
|
|
606
|
+
* * Errno::ETIMEDOUT - the connection has been dropped, because of a network
|
|
607
|
+
* failure or because the system on the other end went down without
|
|
608
|
+
* notice
|
|
609
|
+
* * Errno::ECONNRESET - the virtual circuit was reset by the remote side
|
|
610
|
+
* executing a hard or abortive close. The application should close the
|
|
611
|
+
* socket; it is no longer usable. On a UDP-datagram socket this error
|
|
612
|
+
* indicates a previous send operation resulted in an ICMP Port Unreachable
|
|
613
|
+
* message.
|
|
614
|
+
*/
|
|
615
|
+
static VALUE
|
|
616
|
+
sock_recvfrom(int argc, VALUE *argv, VALUE sock)
|
|
617
|
+
{
|
|
618
|
+
return rsock_s_recvfrom(sock, argc, argv, RECV_SOCKET);
|
|
619
|
+
}
|
|
620
|
+
|
|
621
|
+
/*
|
|
622
|
+
* call-seq:
|
|
623
|
+
* socket.recvfrom_nonblock(maxlen) => [mesg, sender_addrinfo]
|
|
624
|
+
* socket.recvfrom_nonblock(maxlen, flags) => [mesg, sender_addrinfo]
|
|
625
|
+
*
|
|
626
|
+
* Receives up to _maxlen_ bytes from +socket+ using recvfrom(2) after
|
|
627
|
+
* O_NONBLOCK is set for the underlying file descriptor.
|
|
628
|
+
* _flags_ is zero or more of the +MSG_+ options.
|
|
629
|
+
* The first element of the results, _mesg_, is the data received.
|
|
630
|
+
* The second element, _sender_addrinfo_, contains protocol-specific address
|
|
631
|
+
* information of the sender.
|
|
632
|
+
*
|
|
633
|
+
* When recvfrom(2) returns 0, Socket#recvfrom_nonblock returns
|
|
634
|
+
* an empty string as data.
|
|
635
|
+
* The meaning depends on the socket: EOF on TCP, empty packet on UDP, etc.
|
|
636
|
+
*
|
|
637
|
+
* === Parameters
|
|
638
|
+
* * +maxlen+ - the maximum number of bytes to receive from the socket
|
|
639
|
+
* * +flags+ - zero or more of the +MSG_+ options
|
|
640
|
+
*
|
|
641
|
+
* === Example
|
|
642
|
+
* # In one file, start this first
|
|
643
|
+
* require 'socket'
|
|
644
|
+
* include Socket::Constants
|
|
645
|
+
* socket = Socket.new(AF_INET, SOCK_STREAM, 0)
|
|
646
|
+
* sockaddr = Socket.sockaddr_in(2200, 'localhost')
|
|
647
|
+
* socket.bind(sockaddr)
|
|
648
|
+
* socket.listen(5)
|
|
649
|
+
* client, client_addrinfo = socket.accept
|
|
650
|
+
* begin # emulate blocking recvfrom
|
|
651
|
+
* pair = client.recvfrom_nonblock(20)
|
|
652
|
+
* rescue IO::WaitReadable
|
|
653
|
+
* IO.select([client])
|
|
654
|
+
* retry
|
|
655
|
+
* end
|
|
656
|
+
* data = pair[0].chomp
|
|
657
|
+
* puts "I only received 20 bytes '#{data}'"
|
|
658
|
+
* sleep 1
|
|
659
|
+
* socket.close
|
|
660
|
+
*
|
|
661
|
+
* # In another file, start this second
|
|
662
|
+
* require 'socket'
|
|
663
|
+
* include Socket::Constants
|
|
664
|
+
* socket = Socket.new(AF_INET, SOCK_STREAM, 0)
|
|
665
|
+
* sockaddr = Socket.sockaddr_in(2200, 'localhost')
|
|
666
|
+
* socket.connect(sockaddr)
|
|
667
|
+
* socket.puts "Watch this get cut short!"
|
|
668
|
+
* socket.close
|
|
669
|
+
*
|
|
670
|
+
* Refer to Socket#recvfrom for the exceptions that may be thrown if the call
|
|
671
|
+
* to _recvfrom_nonblock_ fails.
|
|
672
|
+
*
|
|
673
|
+
* Socket#recvfrom_nonblock may raise any error corresponding to recvfrom(2) failure,
|
|
674
|
+
* including Errno::EWOULDBLOCK.
|
|
675
|
+
*
|
|
676
|
+
* If the exception is Errno::EWOULDBLOCK or Errno::AGAIN,
|
|
677
|
+
* it is extended by IO::WaitReadable.
|
|
678
|
+
* So IO::WaitReadable can be used to rescue the exceptions for retrying recvfrom_nonblock.
|
|
679
|
+
*
|
|
680
|
+
* === See
|
|
681
|
+
* * Socket#recvfrom
|
|
682
|
+
*/
|
|
683
|
+
static VALUE
|
|
684
|
+
sock_recvfrom_nonblock(int argc, VALUE *argv, VALUE sock)
|
|
685
|
+
{
|
|
686
|
+
return rsock_s_recvfrom_nonblock(sock, argc, argv, RECV_SOCKET);
|
|
687
|
+
}
|
|
688
|
+
|
|
689
|
+
/*
|
|
690
|
+
* call-seq:
|
|
691
|
+
* socket.accept => [client_socket, client_addrinfo]
|
|
692
|
+
*
|
|
693
|
+
* Accepts a next connection.
|
|
694
|
+
* Returns a new Socket object and Addrinfo object.
|
|
695
|
+
*
|
|
696
|
+
* serv = Socket.new(:INET, :STREAM, 0)
|
|
697
|
+
* serv.listen(5)
|
|
698
|
+
* c = Socket.new(:INET, :STREAM, 0)
|
|
699
|
+
* c.connect(serv.connect_address)
|
|
700
|
+
* p serv.accept #=> [#<Socket:fd 6>, #<Addrinfo: 127.0.0.1:48555 TCP>]
|
|
701
|
+
*
|
|
702
|
+
*/
|
|
703
|
+
static VALUE
|
|
704
|
+
sock_accept(VALUE sock)
|
|
705
|
+
{
|
|
706
|
+
rb_io_t *fptr;
|
|
707
|
+
VALUE sock2;
|
|
708
|
+
struct sockaddr_storage buf;
|
|
709
|
+
socklen_t len = (socklen_t)sizeof buf;
|
|
710
|
+
|
|
711
|
+
GetOpenFile(sock, fptr);
|
|
712
|
+
sock2 = rsock_s_accept(rb_cSocket,fptr->fd,(struct sockaddr*)&buf,&len);
|
|
713
|
+
|
|
714
|
+
return rb_assoc_new(sock2, rsock_io_socket_addrinfo(sock2, (struct sockaddr*)&buf, len));
|
|
715
|
+
}
|
|
716
|
+
|
|
717
|
+
/*
|
|
718
|
+
* call-seq:
|
|
719
|
+
* socket.accept_nonblock => [client_socket, client_addrinfo]
|
|
720
|
+
*
|
|
721
|
+
* Accepts an incoming connection using accept(2) after
|
|
722
|
+
* O_NONBLOCK is set for the underlying file descriptor.
|
|
723
|
+
* It returns an array containing the accepted socket
|
|
724
|
+
* for the incoming connection, _client_socket_,
|
|
725
|
+
* and an Addrinfo, _client_addrinfo_.
|
|
726
|
+
*
|
|
727
|
+
* === Example
|
|
728
|
+
* # In one script, start this first
|
|
729
|
+
* require 'socket'
|
|
730
|
+
* include Socket::Constants
|
|
731
|
+
* socket = Socket.new(AF_INET, SOCK_STREAM, 0)
|
|
732
|
+
* sockaddr = Socket.sockaddr_in(2200, 'localhost')
|
|
733
|
+
* socket.bind(sockaddr)
|
|
734
|
+
* socket.listen(5)
|
|
735
|
+
* begin # emulate blocking accept
|
|
736
|
+
* client_socket, client_addrinfo = socket.accept_nonblock
|
|
737
|
+
* rescue IO::WaitReadable, Errno::EINTR
|
|
738
|
+
* IO.select([socket])
|
|
739
|
+
* retry
|
|
740
|
+
* end
|
|
741
|
+
* puts "The client said, '#{client_socket.readline.chomp}'"
|
|
742
|
+
* client_socket.puts "Hello from script one!"
|
|
743
|
+
* socket.close
|
|
744
|
+
*
|
|
745
|
+
* # In another script, start this second
|
|
746
|
+
* require 'socket'
|
|
747
|
+
* include Socket::Constants
|
|
748
|
+
* socket = Socket.new(AF_INET, SOCK_STREAM, 0)
|
|
749
|
+
* sockaddr = Socket.sockaddr_in(2200, 'localhost')
|
|
750
|
+
* socket.connect(sockaddr)
|
|
751
|
+
* socket.puts "Hello from script 2."
|
|
752
|
+
* puts "The server said, '#{socket.readline.chomp}'"
|
|
753
|
+
* socket.close
|
|
754
|
+
*
|
|
755
|
+
* Refer to Socket#accept for the exceptions that may be thrown if the call
|
|
756
|
+
* to _accept_nonblock_ fails.
|
|
757
|
+
*
|
|
758
|
+
* Socket#accept_nonblock may raise any error corresponding to accept(2) failure,
|
|
759
|
+
* including Errno::EWOULDBLOCK.
|
|
760
|
+
*
|
|
761
|
+
* If the exception is Errno::EWOULDBLOCK, Errno::AGAIN, Errno::ECONNABORTED or Errno::EPROTO,
|
|
762
|
+
* it is extended by IO::WaitReadable.
|
|
763
|
+
* So IO::WaitReadable can be used to rescue the exceptions for retrying accept_nonblock.
|
|
764
|
+
*
|
|
765
|
+
* === See
|
|
766
|
+
* * Socket#accept
|
|
767
|
+
*/
|
|
768
|
+
static VALUE
|
|
769
|
+
sock_accept_nonblock(VALUE sock)
|
|
770
|
+
{
|
|
771
|
+
rb_io_t *fptr;
|
|
772
|
+
VALUE sock2;
|
|
773
|
+
struct sockaddr_storage buf;
|
|
774
|
+
socklen_t len = (socklen_t)sizeof buf;
|
|
775
|
+
|
|
776
|
+
GetOpenFile(sock, fptr);
|
|
777
|
+
sock2 = rsock_s_accept_nonblock(rb_cSocket, fptr, (struct sockaddr *)&buf, &len);
|
|
778
|
+
return rb_assoc_new(sock2, rsock_io_socket_addrinfo(sock2, (struct sockaddr*)&buf, len));
|
|
779
|
+
}
|
|
780
|
+
|
|
781
|
+
/*
|
|
782
|
+
* call-seq:
|
|
783
|
+
* socket.sysaccept => [client_socket_fd, client_addrinfo]
|
|
784
|
+
*
|
|
785
|
+
* Accepts an incoming connection returning an array containing the (integer)
|
|
786
|
+
* file descriptor for the incoming connection, _client_socket_fd_,
|
|
787
|
+
* and an Addrinfo, _client_addrinfo_.
|
|
788
|
+
*
|
|
789
|
+
* === Example
|
|
790
|
+
* # In one script, start this first
|
|
791
|
+
* require 'socket'
|
|
792
|
+
* include Socket::Constants
|
|
793
|
+
* socket = Socket.new( AF_INET, SOCK_STREAM, 0 )
|
|
794
|
+
* sockaddr = Socket.pack_sockaddr_in( 2200, 'localhost' )
|
|
795
|
+
* socket.bind( sockaddr )
|
|
796
|
+
* socket.listen( 5 )
|
|
797
|
+
* client_fd, client_addrinfo = socket.sysaccept
|
|
798
|
+
* client_socket = Socket.for_fd( client_fd )
|
|
799
|
+
* puts "The client said, '#{client_socket.readline.chomp}'"
|
|
800
|
+
* client_socket.puts "Hello from script one!"
|
|
801
|
+
* socket.close
|
|
802
|
+
*
|
|
803
|
+
* # In another script, start this second
|
|
804
|
+
* require 'socket'
|
|
805
|
+
* include Socket::Constants
|
|
806
|
+
* socket = Socket.new( AF_INET, SOCK_STREAM, 0 )
|
|
807
|
+
* sockaddr = Socket.pack_sockaddr_in( 2200, 'localhost' )
|
|
808
|
+
* socket.connect( sockaddr )
|
|
809
|
+
* socket.puts "Hello from script 2."
|
|
810
|
+
* puts "The server said, '#{socket.readline.chomp}'"
|
|
811
|
+
* socket.close
|
|
812
|
+
*
|
|
813
|
+
* Refer to Socket#accept for the exceptions that may be thrown if the call
|
|
814
|
+
* to _sysaccept_ fails.
|
|
815
|
+
*
|
|
816
|
+
* === See
|
|
817
|
+
* * Socket#accept
|
|
818
|
+
*/
|
|
819
|
+
static VALUE
|
|
820
|
+
sock_sysaccept(VALUE sock)
|
|
821
|
+
{
|
|
822
|
+
rb_io_t *fptr;
|
|
823
|
+
VALUE sock2;
|
|
824
|
+
struct sockaddr_storage buf;
|
|
825
|
+
socklen_t len = (socklen_t)sizeof buf;
|
|
826
|
+
|
|
827
|
+
GetOpenFile(sock, fptr);
|
|
828
|
+
sock2 = rsock_s_accept(0,fptr->fd,(struct sockaddr*)&buf,&len);
|
|
829
|
+
|
|
830
|
+
return rb_assoc_new(sock2, rsock_io_socket_addrinfo(sock2, (struct sockaddr*)&buf, len));
|
|
831
|
+
}
|
|
832
|
+
|
|
833
|
+
#ifdef HAVE_GETHOSTNAME
|
|
834
|
+
/*
|
|
835
|
+
* call-seq:
|
|
836
|
+
* Socket.gethostname => hostname
|
|
837
|
+
*
|
|
838
|
+
* Returns the hostname.
|
|
839
|
+
*
|
|
840
|
+
* p Socket.gethostname #=> "hal"
|
|
841
|
+
*
|
|
842
|
+
* Note that it is not guaranteed to be able to convert to IP address using gethostbyname, getaddrinfo, etc.
|
|
843
|
+
* If you need local IP address, use Socket.ip_address_list.
|
|
844
|
+
*/
|
|
845
|
+
static VALUE
|
|
846
|
+
sock_gethostname(VALUE obj)
|
|
847
|
+
{
|
|
848
|
+
#ifndef HOST_NAME_MAX
|
|
849
|
+
# define HOST_NAME_MAX 1024
|
|
850
|
+
#endif
|
|
851
|
+
char buf[HOST_NAME_MAX+1];
|
|
852
|
+
|
|
853
|
+
rb_secure(3);
|
|
854
|
+
if (gethostname(buf, (int)sizeof buf - 1) < 0)
|
|
855
|
+
rb_sys_fail("gethostname");
|
|
856
|
+
|
|
857
|
+
buf[sizeof buf - 1] = '\0';
|
|
858
|
+
return rb_str_new2(buf);
|
|
859
|
+
}
|
|
860
|
+
#else
|
|
861
|
+
#ifdef HAVE_UNAME
|
|
862
|
+
|
|
863
|
+
#include <sys/utsname.h>
|
|
864
|
+
|
|
865
|
+
static VALUE
|
|
866
|
+
sock_gethostname(VALUE obj)
|
|
867
|
+
{
|
|
868
|
+
struct utsname un;
|
|
869
|
+
|
|
870
|
+
rb_secure(3);
|
|
871
|
+
uname(&un);
|
|
872
|
+
return rb_str_new2(un.nodename);
|
|
873
|
+
}
|
|
874
|
+
#else
|
|
875
|
+
#define sock_gethostname rb_f_notimplement
|
|
876
|
+
#endif
|
|
877
|
+
#endif
|
|
878
|
+
|
|
879
|
+
static VALUE
|
|
880
|
+
make_addrinfo(struct addrinfo *res0, int norevlookup)
|
|
881
|
+
{
|
|
882
|
+
VALUE base, ary;
|
|
883
|
+
struct addrinfo *res;
|
|
884
|
+
|
|
885
|
+
if (res0 == NULL) {
|
|
886
|
+
rb_raise(rb_eSocket, "host not found");
|
|
887
|
+
}
|
|
888
|
+
base = rb_ary_new();
|
|
889
|
+
for (res = res0; res; res = res->ai_next) {
|
|
890
|
+
ary = rsock_ipaddr(res->ai_addr, norevlookup);
|
|
891
|
+
if (res->ai_canonname) {
|
|
892
|
+
RARRAY_PTR(ary)[2] = rb_str_new2(res->ai_canonname);
|
|
893
|
+
}
|
|
894
|
+
rb_ary_push(ary, INT2FIX(res->ai_family));
|
|
895
|
+
rb_ary_push(ary, INT2FIX(res->ai_socktype));
|
|
896
|
+
rb_ary_push(ary, INT2FIX(res->ai_protocol));
|
|
897
|
+
rb_ary_push(base, ary);
|
|
898
|
+
}
|
|
899
|
+
return base;
|
|
900
|
+
}
|
|
901
|
+
|
|
902
|
+
static VALUE
|
|
903
|
+
sock_sockaddr(struct sockaddr *addr, size_t len)
|
|
904
|
+
{
|
|
905
|
+
char *ptr;
|
|
906
|
+
|
|
907
|
+
switch (addr->sa_family) {
|
|
908
|
+
case AF_INET:
|
|
909
|
+
ptr = (char*)&((struct sockaddr_in*)addr)->sin_addr.s_addr;
|
|
910
|
+
len = sizeof(((struct sockaddr_in*)addr)->sin_addr.s_addr);
|
|
911
|
+
break;
|
|
912
|
+
#ifdef AF_INET6
|
|
913
|
+
case AF_INET6:
|
|
914
|
+
ptr = (char*)&((struct sockaddr_in6*)addr)->sin6_addr.s6_addr;
|
|
915
|
+
len = sizeof(((struct sockaddr_in6*)addr)->sin6_addr.s6_addr);
|
|
916
|
+
break;
|
|
917
|
+
#endif
|
|
918
|
+
default:
|
|
919
|
+
rb_raise(rb_eSocket, "unknown socket family:%d", addr->sa_family);
|
|
920
|
+
break;
|
|
921
|
+
}
|
|
922
|
+
return rb_str_new(ptr, len);
|
|
923
|
+
}
|
|
924
|
+
|
|
925
|
+
/*
|
|
926
|
+
* call-seq:
|
|
927
|
+
* Socket.gethostbyname(hostname) => [official_hostname, alias_hostnames, address_family, *address_list]
|
|
928
|
+
*
|
|
929
|
+
* Obtains the host information for _hostname_.
|
|
930
|
+
*
|
|
931
|
+
* p Socket.gethostbyname("hal") #=> ["localhost", ["hal"], 2, "\x7F\x00\x00\x01"]
|
|
932
|
+
*
|
|
933
|
+
*/
|
|
934
|
+
static VALUE
|
|
935
|
+
sock_s_gethostbyname(VALUE obj, VALUE host)
|
|
936
|
+
{
|
|
937
|
+
rb_secure(3);
|
|
938
|
+
return rsock_make_hostent(host, rsock_addrinfo(host, Qnil, SOCK_STREAM, AI_CANONNAME), sock_sockaddr);
|
|
939
|
+
}
|
|
940
|
+
|
|
941
|
+
/*
|
|
942
|
+
* call-seq:
|
|
943
|
+
* Socket.gethostbyaddr(address_string [, address_family]) => hostent
|
|
944
|
+
*
|
|
945
|
+
* Obtains the host information for _address_.
|
|
946
|
+
*
|
|
947
|
+
* p Socket.gethostbyaddr([221,186,184,68].pack("CCCC"))
|
|
948
|
+
* #=> ["carbon.ruby-lang.org", [], 2, "\xDD\xBA\xB8D"]
|
|
949
|
+
*/
|
|
950
|
+
static VALUE
|
|
951
|
+
sock_s_gethostbyaddr(int argc, VALUE *argv)
|
|
952
|
+
{
|
|
953
|
+
VALUE addr, family;
|
|
954
|
+
struct hostent *h;
|
|
955
|
+
struct sockaddr *sa;
|
|
956
|
+
char **pch;
|
|
957
|
+
VALUE ary, names;
|
|
958
|
+
int t = AF_INET;
|
|
959
|
+
|
|
960
|
+
rb_scan_args(argc, argv, "11", &addr, &family);
|
|
961
|
+
sa = (struct sockaddr*)StringValuePtr(addr);
|
|
962
|
+
if (!NIL_P(family)) {
|
|
963
|
+
t = rsock_family_arg(family);
|
|
964
|
+
}
|
|
965
|
+
#ifdef AF_INET6
|
|
966
|
+
else if (RSTRING_LEN(addr) == 16) {
|
|
967
|
+
t = AF_INET6;
|
|
968
|
+
}
|
|
969
|
+
#endif
|
|
970
|
+
h = gethostbyaddr(RSTRING_PTR(addr), RSTRING_LENINT(addr), t);
|
|
971
|
+
if (h == NULL) {
|
|
972
|
+
#ifdef HAVE_HSTRERROR
|
|
973
|
+
extern int h_errno;
|
|
974
|
+
rb_raise(rb_eSocket, "%s", (char*)hstrerror(h_errno));
|
|
975
|
+
#else
|
|
976
|
+
rb_raise(rb_eSocket, "host not found");
|
|
977
|
+
#endif
|
|
978
|
+
}
|
|
979
|
+
ary = rb_ary_new();
|
|
980
|
+
rb_ary_push(ary, rb_str_new2(h->h_name));
|
|
981
|
+
names = rb_ary_new();
|
|
982
|
+
rb_ary_push(ary, names);
|
|
983
|
+
if (h->h_aliases != NULL) {
|
|
984
|
+
for (pch = h->h_aliases; *pch; pch++) {
|
|
985
|
+
rb_ary_push(names, rb_str_new2(*pch));
|
|
986
|
+
}
|
|
987
|
+
}
|
|
988
|
+
rb_ary_push(ary, INT2NUM(h->h_addrtype));
|
|
989
|
+
#ifdef h_addr
|
|
990
|
+
for (pch = h->h_addr_list; *pch; pch++) {
|
|
991
|
+
rb_ary_push(ary, rb_str_new(*pch, h->h_length));
|
|
992
|
+
}
|
|
993
|
+
#else
|
|
994
|
+
rb_ary_push(ary, rb_str_new(h->h_addr, h->h_length));
|
|
995
|
+
#endif
|
|
996
|
+
|
|
997
|
+
return ary;
|
|
998
|
+
}
|
|
999
|
+
|
|
1000
|
+
/*
|
|
1001
|
+
* call-seq:
|
|
1002
|
+
* Socket.getservbyname(service_name) => port_number
|
|
1003
|
+
* Socket.getservbyname(service_name, protocol_name) => port_number
|
|
1004
|
+
*
|
|
1005
|
+
* Obtains the port number for _service_name_.
|
|
1006
|
+
*
|
|
1007
|
+
* If _protocol_name_ is not given, "tcp" is assumed.
|
|
1008
|
+
*
|
|
1009
|
+
* Socket.getservbyname("smtp") #=> 25
|
|
1010
|
+
* Socket.getservbyname("shell") #=> 514
|
|
1011
|
+
* Socket.getservbyname("syslog", "udp") #=> 514
|
|
1012
|
+
*/
|
|
1013
|
+
static VALUE
|
|
1014
|
+
sock_s_getservbyname(int argc, VALUE *argv)
|
|
1015
|
+
{
|
|
1016
|
+
VALUE service, proto;
|
|
1017
|
+
struct servent *sp;
|
|
1018
|
+
long port;
|
|
1019
|
+
const char *servicename, *protoname = "tcp";
|
|
1020
|
+
|
|
1021
|
+
rb_scan_args(argc, argv, "11", &service, &proto);
|
|
1022
|
+
StringValue(service);
|
|
1023
|
+
if (!NIL_P(proto)) StringValue(proto);
|
|
1024
|
+
servicename = StringValueCStr(service);
|
|
1025
|
+
if (!NIL_P(proto)) protoname = StringValueCStr(proto);
|
|
1026
|
+
sp = getservbyname(servicename, protoname);
|
|
1027
|
+
if (sp) {
|
|
1028
|
+
port = ntohs(sp->s_port);
|
|
1029
|
+
}
|
|
1030
|
+
else {
|
|
1031
|
+
char *end;
|
|
1032
|
+
|
|
1033
|
+
port = STRTOUL(servicename, &end, 0);
|
|
1034
|
+
if (*end != '\0') {
|
|
1035
|
+
rb_raise(rb_eSocket, "no such service %s/%s", servicename, protoname);
|
|
1036
|
+
}
|
|
1037
|
+
}
|
|
1038
|
+
return INT2FIX(port);
|
|
1039
|
+
}
|
|
1040
|
+
|
|
1041
|
+
/*
|
|
1042
|
+
* call-seq:
|
|
1043
|
+
* Socket.getservbyport(port [, protocol_name]) => service
|
|
1044
|
+
*
|
|
1045
|
+
* Obtains the port number for _port_.
|
|
1046
|
+
*
|
|
1047
|
+
* If _protocol_name_ is not given, "tcp" is assumed.
|
|
1048
|
+
*
|
|
1049
|
+
* Socket.getservbyport(80) #=> "www"
|
|
1050
|
+
* Socket.getservbyport(514, "tcp") #=> "shell"
|
|
1051
|
+
* Socket.getservbyport(514, "udp") #=> "syslog"
|
|
1052
|
+
*
|
|
1053
|
+
*/
|
|
1054
|
+
static VALUE
|
|
1055
|
+
sock_s_getservbyport(int argc, VALUE *argv)
|
|
1056
|
+
{
|
|
1057
|
+
VALUE port, proto;
|
|
1058
|
+
struct servent *sp;
|
|
1059
|
+
long portnum;
|
|
1060
|
+
const char *protoname = "tcp";
|
|
1061
|
+
|
|
1062
|
+
rb_scan_args(argc, argv, "11", &port, &proto);
|
|
1063
|
+
portnum = NUM2LONG(port);
|
|
1064
|
+
if (portnum != (uint16_t)portnum) {
|
|
1065
|
+
const char *s = portnum > 0 ? "big" : "small";
|
|
1066
|
+
rb_raise(rb_eRangeError, "integer %ld too %s to convert into `int16_t'", portnum, s);
|
|
1067
|
+
}
|
|
1068
|
+
if (!NIL_P(proto)) protoname = StringValueCStr(proto);
|
|
1069
|
+
|
|
1070
|
+
sp = getservbyport((int)htons((uint16_t)portnum), protoname);
|
|
1071
|
+
if (!sp) {
|
|
1072
|
+
rb_raise(rb_eSocket, "no such service for port %d/%s", (int)portnum, protoname);
|
|
1073
|
+
}
|
|
1074
|
+
return rb_tainted_str_new2(sp->s_name);
|
|
1075
|
+
}
|
|
1076
|
+
|
|
1077
|
+
/*
|
|
1078
|
+
* call-seq:
|
|
1079
|
+
* Socket.getaddrinfo(nodename, servname[, family[, socktype[, protocol[, flags[, reverse_lookup]]]]]) => array
|
|
1080
|
+
*
|
|
1081
|
+
* Obtains address information for _nodename_:_servname_.
|
|
1082
|
+
*
|
|
1083
|
+
* _family_ should be an address family such as: :INET, :INET6, :UNIX, etc.
|
|
1084
|
+
*
|
|
1085
|
+
* _socktype_ should be a socket type such as: :STREAM, :DGRAM, :RAW, etc.
|
|
1086
|
+
*
|
|
1087
|
+
* _protocol_ should be a protocol defined in the family.
|
|
1088
|
+
* 0 is default protocol for the family.
|
|
1089
|
+
*
|
|
1090
|
+
* _flags_ should be bitwise OR of Socket::AI_* constants.
|
|
1091
|
+
*
|
|
1092
|
+
* Socket.getaddrinfo("www.ruby-lang.org", "http", nil, :STREAM)
|
|
1093
|
+
* #=> [["AF_INET", 80, "carbon.ruby-lang.org", "221.186.184.68", 2, 1, 6]] # PF_INET/SOCK_STREAM/IPPROTO_TCP
|
|
1094
|
+
*
|
|
1095
|
+
* Socket.getaddrinfo("localhost", nil)
|
|
1096
|
+
* #=> [["AF_INET", 0, "localhost", "127.0.0.1", 2, 1, 6], # PF_INET/SOCK_STREAM/IPPROTO_TCP
|
|
1097
|
+
* # ["AF_INET", 0, "localhost", "127.0.0.1", 2, 2, 17], # PF_INET/SOCK_DGRAM/IPPROTO_UDP
|
|
1098
|
+
* # ["AF_INET", 0, "localhost", "127.0.0.1", 2, 3, 0]] # PF_INET/SOCK_RAW/IPPROTO_IP
|
|
1099
|
+
*
|
|
1100
|
+
* _reverse_lookup_ directs the form of the third element, and has to
|
|
1101
|
+
* be one of below.
|
|
1102
|
+
* If it is ommitted, the default value is +nil+.
|
|
1103
|
+
*
|
|
1104
|
+
* +true+, +:hostname+: hostname is obtained from numeric address using reverse lookup, which may take a time.
|
|
1105
|
+
* +false+, +:numeric+: hostname is same as numeric address.
|
|
1106
|
+
* +nil+: obey to the current +do_not_reverse_lookup+ flag.
|
|
1107
|
+
*
|
|
1108
|
+
* If Addrinfo object is preferred, use Addrinfo.getaddrinfo.
|
|
1109
|
+
*/
|
|
1110
|
+
static VALUE
|
|
1111
|
+
sock_s_getaddrinfo(int argc, VALUE *argv)
|
|
1112
|
+
{
|
|
1113
|
+
VALUE host, port, family, socktype, protocol, flags, ret, revlookup;
|
|
1114
|
+
struct addrinfo hints, *res;
|
|
1115
|
+
int norevlookup;
|
|
1116
|
+
|
|
1117
|
+
rb_scan_args(argc, argv, "25", &host, &port, &family, &socktype, &protocol, &flags, &revlookup);
|
|
1118
|
+
|
|
1119
|
+
MEMZERO(&hints, struct addrinfo, 1);
|
|
1120
|
+
hints.ai_family = NIL_P(family) ? PF_UNSPEC : rsock_family_arg(family);
|
|
1121
|
+
|
|
1122
|
+
if (!NIL_P(socktype)) {
|
|
1123
|
+
hints.ai_socktype = rsock_socktype_arg(socktype);
|
|
1124
|
+
}
|
|
1125
|
+
if (!NIL_P(protocol)) {
|
|
1126
|
+
hints.ai_protocol = NUM2INT(protocol);
|
|
1127
|
+
}
|
|
1128
|
+
if (!NIL_P(flags)) {
|
|
1129
|
+
hints.ai_flags = NUM2INT(flags);
|
|
1130
|
+
}
|
|
1131
|
+
if (NIL_P(revlookup) || !rsock_revlookup_flag(revlookup, &norevlookup)) {
|
|
1132
|
+
norevlookup = rsock_do_not_reverse_lookup;
|
|
1133
|
+
}
|
|
1134
|
+
res = rsock_getaddrinfo(host, port, &hints, 0);
|
|
1135
|
+
|
|
1136
|
+
ret = make_addrinfo(res, norevlookup);
|
|
1137
|
+
freeaddrinfo(res);
|
|
1138
|
+
return ret;
|
|
1139
|
+
}
|
|
1140
|
+
|
|
1141
|
+
/*
|
|
1142
|
+
* call-seq:
|
|
1143
|
+
* Socket.getnameinfo(sockaddr [, flags]) => [hostname, servicename]
|
|
1144
|
+
*
|
|
1145
|
+
* Obtains name information for _sockaddr_.
|
|
1146
|
+
*
|
|
1147
|
+
* _sockaddr_ should be one of follows.
|
|
1148
|
+
* - packed sockaddr string such as Socket.sockaddr_in(80, "127.0.0.1")
|
|
1149
|
+
* - 3-elements array such as ["AF_INET", 80, "127.0.0.1"]
|
|
1150
|
+
* - 4-elements array such as ["AF_INET", 80, ignored, "127.0.0.1"]
|
|
1151
|
+
*
|
|
1152
|
+
* _flags_ should be bitwise OR of Socket::NI_* constants.
|
|
1153
|
+
*
|
|
1154
|
+
* Note that the last form is compatible with IPSocket#{addr,peeraddr}.
|
|
1155
|
+
*
|
|
1156
|
+
* Socket.getnameinfo(Socket.sockaddr_in(80, "127.0.0.1")) #=> ["localhost", "www"]
|
|
1157
|
+
* Socket.getnameinfo(["AF_INET", 80, "127.0.0.1"]) #=> ["localhost", "www"]
|
|
1158
|
+
* Socket.getnameinfo(["AF_INET", 80, "localhost", "127.0.0.1"]) #=> ["localhost", "www"]
|
|
1159
|
+
*
|
|
1160
|
+
* If Addrinfo object is preferred, use Addrinfo#getnameinfo.
|
|
1161
|
+
*/
|
|
1162
|
+
static VALUE
|
|
1163
|
+
sock_s_getnameinfo(int argc, VALUE *argv)
|
|
1164
|
+
{
|
|
1165
|
+
VALUE sa, af = Qnil, host = Qnil, port = Qnil, flags, tmp;
|
|
1166
|
+
char *hptr, *pptr;
|
|
1167
|
+
char hbuf[1024], pbuf[1024];
|
|
1168
|
+
int fl;
|
|
1169
|
+
struct addrinfo hints, *res = NULL, *r;
|
|
1170
|
+
int error;
|
|
1171
|
+
struct sockaddr_storage ss;
|
|
1172
|
+
struct sockaddr *sap;
|
|
1173
|
+
|
|
1174
|
+
sa = flags = Qnil;
|
|
1175
|
+
rb_scan_args(argc, argv, "11", &sa, &flags);
|
|
1176
|
+
|
|
1177
|
+
fl = 0;
|
|
1178
|
+
if (!NIL_P(flags)) {
|
|
1179
|
+
fl = NUM2INT(flags);
|
|
1180
|
+
}
|
|
1181
|
+
tmp = rb_check_sockaddr_string_type(sa);
|
|
1182
|
+
if (!NIL_P(tmp)) {
|
|
1183
|
+
sa = tmp;
|
|
1184
|
+
if (sizeof(ss) < (size_t)RSTRING_LEN(sa)) {
|
|
1185
|
+
rb_raise(rb_eTypeError, "sockaddr length too big");
|
|
1186
|
+
}
|
|
1187
|
+
memcpy(&ss, RSTRING_PTR(sa), RSTRING_LEN(sa));
|
|
1188
|
+
if ((size_t)RSTRING_LEN(sa) != SS_LEN(&ss)) {
|
|
1189
|
+
rb_raise(rb_eTypeError, "sockaddr size differs - should not happen");
|
|
1190
|
+
}
|
|
1191
|
+
sap = (struct sockaddr*)&ss;
|
|
1192
|
+
goto call_nameinfo;
|
|
1193
|
+
}
|
|
1194
|
+
tmp = rb_check_array_type(sa);
|
|
1195
|
+
if (!NIL_P(tmp)) {
|
|
1196
|
+
sa = tmp;
|
|
1197
|
+
MEMZERO(&hints, struct addrinfo, 1);
|
|
1198
|
+
if (RARRAY_LEN(sa) == 3) {
|
|
1199
|
+
af = RARRAY_PTR(sa)[0];
|
|
1200
|
+
port = RARRAY_PTR(sa)[1];
|
|
1201
|
+
host = RARRAY_PTR(sa)[2];
|
|
1202
|
+
}
|
|
1203
|
+
else if (RARRAY_LEN(sa) >= 4) {
|
|
1204
|
+
af = RARRAY_PTR(sa)[0];
|
|
1205
|
+
port = RARRAY_PTR(sa)[1];
|
|
1206
|
+
host = RARRAY_PTR(sa)[3];
|
|
1207
|
+
if (NIL_P(host)) {
|
|
1208
|
+
host = RARRAY_PTR(sa)[2];
|
|
1209
|
+
}
|
|
1210
|
+
else {
|
|
1211
|
+
/*
|
|
1212
|
+
* 4th element holds numeric form, don't resolve.
|
|
1213
|
+
* see rsock_ipaddr().
|
|
1214
|
+
*/
|
|
1215
|
+
#ifdef AI_NUMERICHOST /* AIX 4.3.3 doesn't have AI_NUMERICHOST. */
|
|
1216
|
+
hints.ai_flags |= AI_NUMERICHOST;
|
|
1217
|
+
#endif
|
|
1218
|
+
}
|
|
1219
|
+
}
|
|
1220
|
+
else {
|
|
1221
|
+
rb_raise(rb_eArgError, "array size should be 3 or 4, %ld given",
|
|
1222
|
+
RARRAY_LEN(sa));
|
|
1223
|
+
}
|
|
1224
|
+
/* host */
|
|
1225
|
+
if (NIL_P(host)) {
|
|
1226
|
+
hptr = NULL;
|
|
1227
|
+
}
|
|
1228
|
+
else {
|
|
1229
|
+
strncpy(hbuf, StringValuePtr(host), sizeof(hbuf));
|
|
1230
|
+
hbuf[sizeof(hbuf) - 1] = '\0';
|
|
1231
|
+
hptr = hbuf;
|
|
1232
|
+
}
|
|
1233
|
+
/* port */
|
|
1234
|
+
if (NIL_P(port)) {
|
|
1235
|
+
strcpy(pbuf, "0");
|
|
1236
|
+
pptr = NULL;
|
|
1237
|
+
}
|
|
1238
|
+
else if (FIXNUM_P(port)) {
|
|
1239
|
+
snprintf(pbuf, sizeof(pbuf), "%ld", NUM2LONG(port));
|
|
1240
|
+
pptr = pbuf;
|
|
1241
|
+
}
|
|
1242
|
+
else {
|
|
1243
|
+
strncpy(pbuf, StringValuePtr(port), sizeof(pbuf));
|
|
1244
|
+
pbuf[sizeof(pbuf) - 1] = '\0';
|
|
1245
|
+
pptr = pbuf;
|
|
1246
|
+
}
|
|
1247
|
+
hints.ai_socktype = (fl & NI_DGRAM) ? SOCK_DGRAM : SOCK_STREAM;
|
|
1248
|
+
/* af */
|
|
1249
|
+
hints.ai_family = NIL_P(af) ? PF_UNSPEC : rsock_family_arg(af);
|
|
1250
|
+
error = rb_getaddrinfo(hptr, pptr, &hints, &res);
|
|
1251
|
+
if (error) goto error_exit_addr;
|
|
1252
|
+
sap = res->ai_addr;
|
|
1253
|
+
}
|
|
1254
|
+
else {
|
|
1255
|
+
rb_raise(rb_eTypeError, "expecting String or Array");
|
|
1256
|
+
}
|
|
1257
|
+
|
|
1258
|
+
call_nameinfo:
|
|
1259
|
+
error = rb_getnameinfo(sap, SA_LEN(sap), hbuf, sizeof(hbuf),
|
|
1260
|
+
pbuf, sizeof(pbuf), fl);
|
|
1261
|
+
if (error) goto error_exit_name;
|
|
1262
|
+
if (res) {
|
|
1263
|
+
for (r = res->ai_next; r; r = r->ai_next) {
|
|
1264
|
+
char hbuf2[1024], pbuf2[1024];
|
|
1265
|
+
|
|
1266
|
+
sap = r->ai_addr;
|
|
1267
|
+
error = rb_getnameinfo(sap, SA_LEN(sap), hbuf2, sizeof(hbuf2),
|
|
1268
|
+
pbuf2, sizeof(pbuf2), fl);
|
|
1269
|
+
if (error) goto error_exit_name;
|
|
1270
|
+
if (strcmp(hbuf, hbuf2) != 0|| strcmp(pbuf, pbuf2) != 0) {
|
|
1271
|
+
freeaddrinfo(res);
|
|
1272
|
+
rb_raise(rb_eSocket, "sockaddr resolved to multiple nodename");
|
|
1273
|
+
}
|
|
1274
|
+
}
|
|
1275
|
+
freeaddrinfo(res);
|
|
1276
|
+
}
|
|
1277
|
+
return rb_assoc_new(rb_str_new2(hbuf), rb_str_new2(pbuf));
|
|
1278
|
+
|
|
1279
|
+
error_exit_addr:
|
|
1280
|
+
if (res) freeaddrinfo(res);
|
|
1281
|
+
rsock_raise_socket_error("getaddrinfo", error);
|
|
1282
|
+
|
|
1283
|
+
error_exit_name:
|
|
1284
|
+
if (res) freeaddrinfo(res);
|
|
1285
|
+
rsock_raise_socket_error("getnameinfo", error);
|
|
1286
|
+
}
|
|
1287
|
+
|
|
1288
|
+
/*
|
|
1289
|
+
* call-seq:
|
|
1290
|
+
* Socket.sockaddr_in(port, host) => sockaddr
|
|
1291
|
+
* Socket.pack_sockaddr_in(port, host) => sockaddr
|
|
1292
|
+
*
|
|
1293
|
+
* Packs _port_ and _host_ as an AF_INET/AF_INET6 sockaddr string.
|
|
1294
|
+
*
|
|
1295
|
+
* Socket.sockaddr_in(80, "127.0.0.1")
|
|
1296
|
+
* #=> "\x02\x00\x00P\x7F\x00\x00\x01\x00\x00\x00\x00\x00\x00\x00\x00"
|
|
1297
|
+
*
|
|
1298
|
+
* Socket.sockaddr_in(80, "::1")
|
|
1299
|
+
* #=> "\n\x00\x00P\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x01\x00\x00\x00\x00"
|
|
1300
|
+
*
|
|
1301
|
+
*/
|
|
1302
|
+
static VALUE
|
|
1303
|
+
sock_s_pack_sockaddr_in(VALUE self, VALUE port, VALUE host)
|
|
1304
|
+
{
|
|
1305
|
+
struct addrinfo *res = rsock_addrinfo(host, port, 0, 0);
|
|
1306
|
+
VALUE addr = rb_str_new((char*)res->ai_addr, res->ai_addrlen);
|
|
1307
|
+
|
|
1308
|
+
freeaddrinfo(res);
|
|
1309
|
+
OBJ_INFECT(addr, port);
|
|
1310
|
+
OBJ_INFECT(addr, host);
|
|
1311
|
+
|
|
1312
|
+
return addr;
|
|
1313
|
+
}
|
|
1314
|
+
|
|
1315
|
+
/*
|
|
1316
|
+
* call-seq:
|
|
1317
|
+
* Socket.unpack_sockaddr_in(sockaddr) => [port, ip_address]
|
|
1318
|
+
*
|
|
1319
|
+
* Unpacks _sockaddr_ into port and ip_address.
|
|
1320
|
+
*
|
|
1321
|
+
* _sockaddr_ should be a string or an addrinfo for AF_INET/AF_INET6.
|
|
1322
|
+
*
|
|
1323
|
+
* sockaddr = Socket.sockaddr_in(80, "127.0.0.1")
|
|
1324
|
+
* p sockaddr #=> "\x02\x00\x00P\x7F\x00\x00\x01\x00\x00\x00\x00\x00\x00\x00\x00"
|
|
1325
|
+
* p Socket.unpack_sockaddr_in(sockaddr) #=> [80, "127.0.0.1"]
|
|
1326
|
+
*
|
|
1327
|
+
*/
|
|
1328
|
+
static VALUE
|
|
1329
|
+
sock_s_unpack_sockaddr_in(VALUE self, VALUE addr)
|
|
1330
|
+
{
|
|
1331
|
+
struct sockaddr_in * sockaddr;
|
|
1332
|
+
VALUE host;
|
|
1333
|
+
|
|
1334
|
+
sockaddr = (struct sockaddr_in*)SockAddrStringValuePtr(addr);
|
|
1335
|
+
if (RSTRING_LEN(addr) <
|
|
1336
|
+
(char*)&((struct sockaddr *)sockaddr)->sa_family +
|
|
1337
|
+
sizeof(((struct sockaddr *)sockaddr)->sa_family) -
|
|
1338
|
+
(char*)sockaddr)
|
|
1339
|
+
rb_raise(rb_eArgError, "too short sockaddr");
|
|
1340
|
+
if (((struct sockaddr *)sockaddr)->sa_family != AF_INET
|
|
1341
|
+
#ifdef INET6
|
|
1342
|
+
&& ((struct sockaddr *)sockaddr)->sa_family != AF_INET6
|
|
1343
|
+
#endif
|
|
1344
|
+
) {
|
|
1345
|
+
#ifdef INET6
|
|
1346
|
+
rb_raise(rb_eArgError, "not an AF_INET/AF_INET6 sockaddr");
|
|
1347
|
+
#else
|
|
1348
|
+
rb_raise(rb_eArgError, "not an AF_INET sockaddr");
|
|
1349
|
+
#endif
|
|
1350
|
+
}
|
|
1351
|
+
host = rsock_make_ipaddr((struct sockaddr*)sockaddr);
|
|
1352
|
+
OBJ_INFECT(host, addr);
|
|
1353
|
+
return rb_assoc_new(INT2NUM(ntohs(sockaddr->sin_port)), host);
|
|
1354
|
+
}
|
|
1355
|
+
|
|
1356
|
+
#ifdef HAVE_SYS_UN_H
|
|
1357
|
+
|
|
1358
|
+
/*
|
|
1359
|
+
* call-seq:
|
|
1360
|
+
* Socket.sockaddr_un(path) => sockaddr
|
|
1361
|
+
* Socket.pack_sockaddr_un(path) => sockaddr
|
|
1362
|
+
*
|
|
1363
|
+
* Packs _path_ as an AF_UNIX sockaddr string.
|
|
1364
|
+
*
|
|
1365
|
+
* Socket.sockaddr_un("/tmp/sock") #=> "\x01\x00/tmp/sock\x00\x00..."
|
|
1366
|
+
*
|
|
1367
|
+
*/
|
|
1368
|
+
static VALUE
|
|
1369
|
+
sock_s_pack_sockaddr_un(VALUE self, VALUE path)
|
|
1370
|
+
{
|
|
1371
|
+
struct sockaddr_un sockaddr;
|
|
1372
|
+
char *sun_path;
|
|
1373
|
+
VALUE addr;
|
|
1374
|
+
|
|
1375
|
+
MEMZERO(&sockaddr, struct sockaddr_un, 1);
|
|
1376
|
+
sockaddr.sun_family = AF_UNIX;
|
|
1377
|
+
sun_path = StringValueCStr(path);
|
|
1378
|
+
if (sizeof(sockaddr.sun_path) <= strlen(sun_path)) {
|
|
1379
|
+
rb_raise(rb_eArgError, "too long unix socket path (max: %dbytes)",
|
|
1380
|
+
(int)sizeof(sockaddr.sun_path)-1);
|
|
1381
|
+
}
|
|
1382
|
+
strncpy(sockaddr.sun_path, sun_path, sizeof(sockaddr.sun_path)-1);
|
|
1383
|
+
addr = rb_str_new((char*)&sockaddr, sizeof(sockaddr));
|
|
1384
|
+
OBJ_INFECT(addr, path);
|
|
1385
|
+
|
|
1386
|
+
return addr;
|
|
1387
|
+
}
|
|
1388
|
+
|
|
1389
|
+
/*
|
|
1390
|
+
* call-seq:
|
|
1391
|
+
* Socket.unpack_sockaddr_un(sockaddr) => path
|
|
1392
|
+
*
|
|
1393
|
+
* Unpacks _sockaddr_ into path.
|
|
1394
|
+
*
|
|
1395
|
+
* _sockaddr_ should be a string or an addrinfo for AF_UNIX.
|
|
1396
|
+
*
|
|
1397
|
+
* sockaddr = Socket.sockaddr_un("/tmp/sock")
|
|
1398
|
+
* p Socket.unpack_sockaddr_un(sockaddr) #=> "/tmp/sock"
|
|
1399
|
+
*
|
|
1400
|
+
*/
|
|
1401
|
+
static VALUE
|
|
1402
|
+
sock_s_unpack_sockaddr_un(VALUE self, VALUE addr)
|
|
1403
|
+
{
|
|
1404
|
+
struct sockaddr_un * sockaddr;
|
|
1405
|
+
const char *sun_path;
|
|
1406
|
+
VALUE path;
|
|
1407
|
+
|
|
1408
|
+
sockaddr = (struct sockaddr_un*)SockAddrStringValuePtr(addr);
|
|
1409
|
+
if (RSTRING_LEN(addr) <
|
|
1410
|
+
(char*)&((struct sockaddr *)sockaddr)->sa_family +
|
|
1411
|
+
sizeof(((struct sockaddr *)sockaddr)->sa_family) -
|
|
1412
|
+
(char*)sockaddr)
|
|
1413
|
+
rb_raise(rb_eArgError, "too short sockaddr");
|
|
1414
|
+
if (((struct sockaddr *)sockaddr)->sa_family != AF_UNIX) {
|
|
1415
|
+
rb_raise(rb_eArgError, "not an AF_UNIX sockaddr");
|
|
1416
|
+
}
|
|
1417
|
+
if (sizeof(struct sockaddr_un) < (size_t)RSTRING_LEN(addr)) {
|
|
1418
|
+
rb_raise(rb_eTypeError, "too long sockaddr_un - %ld longer than %d",
|
|
1419
|
+
RSTRING_LEN(addr), (int)sizeof(struct sockaddr_un));
|
|
1420
|
+
}
|
|
1421
|
+
sun_path = rsock_unixpath(sockaddr, RSTRING_LENINT(addr));
|
|
1422
|
+
if (sizeof(struct sockaddr_un) == RSTRING_LEN(addr) &&
|
|
1423
|
+
sun_path == sockaddr->sun_path &&
|
|
1424
|
+
sun_path + strlen(sun_path) == RSTRING_PTR(addr) + RSTRING_LEN(addr)) {
|
|
1425
|
+
rb_raise(rb_eArgError, "sockaddr_un.sun_path not NUL terminated");
|
|
1426
|
+
}
|
|
1427
|
+
path = rb_str_new2(sun_path);
|
|
1428
|
+
OBJ_INFECT(path, addr);
|
|
1429
|
+
return path;
|
|
1430
|
+
}
|
|
1431
|
+
#endif
|
|
1432
|
+
|
|
1433
|
+
#if defined(HAVE_GETIFADDRS) || defined(SIOCGLIFCONF) || defined(SIOCGIFCONF) || defined(_WIN32)
|
|
1434
|
+
static VALUE
|
|
1435
|
+
sockaddr_obj(struct sockaddr *addr)
|
|
1436
|
+
{
|
|
1437
|
+
socklen_t len;
|
|
1438
|
+
#if defined(AF_INET6) && defined(__KAME__)
|
|
1439
|
+
struct sockaddr_in6 addr6;
|
|
1440
|
+
#endif
|
|
1441
|
+
|
|
1442
|
+
if (addr == NULL)
|
|
1443
|
+
return Qnil;
|
|
1444
|
+
|
|
1445
|
+
switch (addr->sa_family) {
|
|
1446
|
+
case AF_INET:
|
|
1447
|
+
len = (socklen_t)sizeof(struct sockaddr_in);
|
|
1448
|
+
break;
|
|
1449
|
+
|
|
1450
|
+
#ifdef AF_INET6
|
|
1451
|
+
case AF_INET6:
|
|
1452
|
+
len = (socklen_t)sizeof(struct sockaddr_in6);
|
|
1453
|
+
# ifdef __KAME__
|
|
1454
|
+
/* KAME uses the 2nd 16bit word of link local IPv6 address as interface index internally */
|
|
1455
|
+
/* http://orange.kame.net/dev/cvsweb.cgi/kame/IMPLEMENTATION */
|
|
1456
|
+
/* convert fe80:1::1 to fe80::1%1 */
|
|
1457
|
+
memcpy(&addr6, addr, len);
|
|
1458
|
+
addr = (struct sockaddr *)&addr6;
|
|
1459
|
+
if (IN6_IS_ADDR_LINKLOCAL(&addr6.sin6_addr) &&
|
|
1460
|
+
addr6.sin6_scope_id == 0 &&
|
|
1461
|
+
(addr6.sin6_addr.s6_addr[2] || addr6.sin6_addr.s6_addr[3])) {
|
|
1462
|
+
addr6.sin6_scope_id = (addr6.sin6_addr.s6_addr[2] << 8) | addr6.sin6_addr.s6_addr[3];
|
|
1463
|
+
addr6.sin6_addr.s6_addr[2] = 0;
|
|
1464
|
+
addr6.sin6_addr.s6_addr[3] = 0;
|
|
1465
|
+
}
|
|
1466
|
+
# endif
|
|
1467
|
+
break;
|
|
1468
|
+
#endif
|
|
1469
|
+
|
|
1470
|
+
#ifdef HAVE_SYS_UN_H
|
|
1471
|
+
case AF_UNIX:
|
|
1472
|
+
len = (socklen_t)sizeof(struct sockaddr_un);
|
|
1473
|
+
break;
|
|
1474
|
+
#endif
|
|
1475
|
+
|
|
1476
|
+
default:
|
|
1477
|
+
len = (socklen_t)sizeof(struct sockaddr_in);
|
|
1478
|
+
break;
|
|
1479
|
+
}
|
|
1480
|
+
#ifdef SA_LEN
|
|
1481
|
+
if (len < (socklen_t)SA_LEN(addr))
|
|
1482
|
+
len = (socklen_t)SA_LEN(addr);
|
|
1483
|
+
#endif
|
|
1484
|
+
|
|
1485
|
+
return rsock_addrinfo_new(addr, len, addr->sa_family, 0, 0, Qnil, Qnil);
|
|
1486
|
+
}
|
|
1487
|
+
#endif
|
|
1488
|
+
|
|
1489
|
+
#if defined(HAVE_GETIFADDRS) || (defined(SIOCGLIFCONF) && defined(SIOCGLIFNUM) && !defined(__hpux)) || defined(SIOCGIFCONF) || defined(_WIN32)
|
|
1490
|
+
/*
|
|
1491
|
+
* call-seq:
|
|
1492
|
+
* Socket.ip_address_list => array
|
|
1493
|
+
*
|
|
1494
|
+
* Returns local IP addresses as an array.
|
|
1495
|
+
*
|
|
1496
|
+
* The array contains Addrinfo objects.
|
|
1497
|
+
*
|
|
1498
|
+
* pp Socket.ip_address_list
|
|
1499
|
+
* #=> [#<Addrinfo: 127.0.0.1>,
|
|
1500
|
+
* #<Addrinfo: 192.168.0.128>,
|
|
1501
|
+
* #<Addrinfo: ::1>,
|
|
1502
|
+
* ...]
|
|
1503
|
+
*
|
|
1504
|
+
*/
|
|
1505
|
+
static VALUE
|
|
1506
|
+
socket_s_ip_address_list(VALUE self)
|
|
1507
|
+
{
|
|
1508
|
+
#if defined(HAVE_GETIFADDRS)
|
|
1509
|
+
struct ifaddrs *ifp = NULL;
|
|
1510
|
+
struct ifaddrs *p;
|
|
1511
|
+
int ret;
|
|
1512
|
+
VALUE list;
|
|
1513
|
+
|
|
1514
|
+
ret = getifaddrs(&ifp);
|
|
1515
|
+
if (ret == -1) {
|
|
1516
|
+
rb_sys_fail("getifaddrs");
|
|
1517
|
+
}
|
|
1518
|
+
|
|
1519
|
+
list = rb_ary_new();
|
|
1520
|
+
for (p = ifp; p; p = p->ifa_next) {
|
|
1521
|
+
if (p->ifa_addr != NULL && IS_IP_FAMILY(p->ifa_addr->sa_family)) {
|
|
1522
|
+
rb_ary_push(list, sockaddr_obj(p->ifa_addr));
|
|
1523
|
+
}
|
|
1524
|
+
}
|
|
1525
|
+
|
|
1526
|
+
freeifaddrs(ifp);
|
|
1527
|
+
|
|
1528
|
+
return list;
|
|
1529
|
+
#elif defined(SIOCGLIFCONF) && defined(SIOCGLIFNUM) && !defined(__hpux)
|
|
1530
|
+
/* Solaris if_tcp(7P) */
|
|
1531
|
+
/* HP-UX has SIOCGLIFCONF too. But it uses different struct */
|
|
1532
|
+
int fd = -1;
|
|
1533
|
+
int ret;
|
|
1534
|
+
struct lifnum ln;
|
|
1535
|
+
struct lifconf lc;
|
|
1536
|
+
char *reason = NULL;
|
|
1537
|
+
int save_errno;
|
|
1538
|
+
int i;
|
|
1539
|
+
VALUE list = Qnil;
|
|
1540
|
+
|
|
1541
|
+
lc.lifc_buf = NULL;
|
|
1542
|
+
|
|
1543
|
+
fd = socket(AF_INET, SOCK_DGRAM, 0);
|
|
1544
|
+
if (fd == -1)
|
|
1545
|
+
rb_sys_fail("socket");
|
|
1546
|
+
|
|
1547
|
+
memset(&ln, 0, sizeof(ln));
|
|
1548
|
+
ln.lifn_family = AF_UNSPEC;
|
|
1549
|
+
|
|
1550
|
+
ret = ioctl(fd, SIOCGLIFNUM, &ln);
|
|
1551
|
+
if (ret == -1) {
|
|
1552
|
+
reason = "SIOCGLIFNUM";
|
|
1553
|
+
goto finish;
|
|
1554
|
+
}
|
|
1555
|
+
|
|
1556
|
+
memset(&lc, 0, sizeof(lc));
|
|
1557
|
+
lc.lifc_family = AF_UNSPEC;
|
|
1558
|
+
lc.lifc_flags = 0;
|
|
1559
|
+
lc.lifc_len = sizeof(struct lifreq) * ln.lifn_count;
|
|
1560
|
+
lc.lifc_req = xmalloc(lc.lifc_len);
|
|
1561
|
+
|
|
1562
|
+
ret = ioctl(fd, SIOCGLIFCONF, &lc);
|
|
1563
|
+
if (ret == -1) {
|
|
1564
|
+
reason = "SIOCGLIFCONF";
|
|
1565
|
+
goto finish;
|
|
1566
|
+
}
|
|
1567
|
+
|
|
1568
|
+
list = rb_ary_new();
|
|
1569
|
+
for (i = 0; i < ln.lifn_count; i++) {
|
|
1570
|
+
struct lifreq *req = &lc.lifc_req[i];
|
|
1571
|
+
if (IS_IP_FAMILY(req->lifr_addr.ss_family)) {
|
|
1572
|
+
if (req->lifr_addr.ss_family == AF_INET6 &&
|
|
1573
|
+
IN6_IS_ADDR_LINKLOCAL(&((struct sockaddr_in6 *)(&req->lifr_addr))->sin6_addr) &&
|
|
1574
|
+
((struct sockaddr_in6 *)(&req->lifr_addr))->sin6_scope_id == 0) {
|
|
1575
|
+
struct lifreq req2;
|
|
1576
|
+
memcpy(req2.lifr_name, req->lifr_name, LIFNAMSIZ);
|
|
1577
|
+
ret = ioctl(fd, SIOCGLIFINDEX, &req2);
|
|
1578
|
+
if (ret == -1) {
|
|
1579
|
+
reason = "SIOCGLIFINDEX";
|
|
1580
|
+
goto finish;
|
|
1581
|
+
}
|
|
1582
|
+
((struct sockaddr_in6 *)(&req->lifr_addr))->sin6_scope_id = req2.lifr_index;
|
|
1583
|
+
}
|
|
1584
|
+
rb_ary_push(list, sockaddr_obj((struct sockaddr *)&req->lifr_addr));
|
|
1585
|
+
}
|
|
1586
|
+
}
|
|
1587
|
+
|
|
1588
|
+
finish:
|
|
1589
|
+
save_errno = errno;
|
|
1590
|
+
if (lc.lifc_buf != NULL)
|
|
1591
|
+
xfree(lc.lifc_req);
|
|
1592
|
+
if (fd != -1)
|
|
1593
|
+
close(fd);
|
|
1594
|
+
errno = save_errno;
|
|
1595
|
+
|
|
1596
|
+
if (reason)
|
|
1597
|
+
rb_sys_fail(reason);
|
|
1598
|
+
return list;
|
|
1599
|
+
|
|
1600
|
+
#elif defined(SIOCGIFCONF)
|
|
1601
|
+
int fd = -1;
|
|
1602
|
+
int ret;
|
|
1603
|
+
#define EXTRA_SPACE (sizeof(struct ifconf) + sizeof(struct sockaddr_storage))
|
|
1604
|
+
char initbuf[4096+EXTRA_SPACE];
|
|
1605
|
+
char *buf = initbuf;
|
|
1606
|
+
int bufsize;
|
|
1607
|
+
struct ifconf conf;
|
|
1608
|
+
struct ifreq *req;
|
|
1609
|
+
VALUE list = Qnil;
|
|
1610
|
+
const char *reason = NULL;
|
|
1611
|
+
int save_errno;
|
|
1612
|
+
|
|
1613
|
+
fd = socket(AF_INET, SOCK_DGRAM, 0);
|
|
1614
|
+
if (fd == -1)
|
|
1615
|
+
rb_sys_fail("socket");
|
|
1616
|
+
|
|
1617
|
+
bufsize = sizeof(initbuf);
|
|
1618
|
+
buf = initbuf;
|
|
1619
|
+
|
|
1620
|
+
retry:
|
|
1621
|
+
conf.ifc_len = bufsize;
|
|
1622
|
+
conf.ifc_req = (struct ifreq *)buf;
|
|
1623
|
+
|
|
1624
|
+
/* fprintf(stderr, "bufsize: %d\n", bufsize); */
|
|
1625
|
+
|
|
1626
|
+
ret = ioctl(fd, SIOCGIFCONF, &conf);
|
|
1627
|
+
if (ret == -1) {
|
|
1628
|
+
reason = "SIOCGIFCONF";
|
|
1629
|
+
goto finish;
|
|
1630
|
+
}
|
|
1631
|
+
|
|
1632
|
+
/* fprintf(stderr, "conf.ifc_len: %d\n", conf.ifc_len); */
|
|
1633
|
+
|
|
1634
|
+
if (bufsize - EXTRA_SPACE < conf.ifc_len) {
|
|
1635
|
+
if (bufsize < conf.ifc_len) {
|
|
1636
|
+
/* NetBSD returns required size for all interfaces. */
|
|
1637
|
+
bufsize = conf.ifc_len + EXTRA_SPACE;
|
|
1638
|
+
}
|
|
1639
|
+
else {
|
|
1640
|
+
bufsize = bufsize << 1;
|
|
1641
|
+
}
|
|
1642
|
+
if (buf == initbuf)
|
|
1643
|
+
buf = NULL;
|
|
1644
|
+
buf = xrealloc(buf, bufsize);
|
|
1645
|
+
goto retry;
|
|
1646
|
+
}
|
|
1647
|
+
|
|
1648
|
+
close(fd);
|
|
1649
|
+
fd = -1;
|
|
1650
|
+
|
|
1651
|
+
list = rb_ary_new();
|
|
1652
|
+
req = conf.ifc_req;
|
|
1653
|
+
while ((char*)req < (char*)conf.ifc_req + conf.ifc_len) {
|
|
1654
|
+
struct sockaddr *addr = &req->ifr_addr;
|
|
1655
|
+
if (IS_IP_FAMILY(addr->sa_family)) {
|
|
1656
|
+
rb_ary_push(list, sockaddr_obj(addr));
|
|
1657
|
+
}
|
|
1658
|
+
#ifdef HAVE_SA_LEN
|
|
1659
|
+
# ifndef _SIZEOF_ADDR_IFREQ
|
|
1660
|
+
# define _SIZEOF_ADDR_IFREQ(r) \
|
|
1661
|
+
(sizeof(struct ifreq) + \
|
|
1662
|
+
(sizeof(struct sockaddr) < (r).ifr_addr.sa_len ? \
|
|
1663
|
+
(r).ifr_addr.sa_len - sizeof(struct sockaddr) : \
|
|
1664
|
+
0))
|
|
1665
|
+
# endif
|
|
1666
|
+
req = (struct ifreq *)((char*)req + _SIZEOF_ADDR_IFREQ(*req));
|
|
1667
|
+
#else
|
|
1668
|
+
req = (struct ifreq *)((char*)req + sizeof(struct ifreq));
|
|
1669
|
+
#endif
|
|
1670
|
+
}
|
|
1671
|
+
|
|
1672
|
+
finish:
|
|
1673
|
+
|
|
1674
|
+
save_errno = errno;
|
|
1675
|
+
if (buf != initbuf)
|
|
1676
|
+
xfree(buf);
|
|
1677
|
+
if (fd != -1)
|
|
1678
|
+
close(fd);
|
|
1679
|
+
errno = save_errno;
|
|
1680
|
+
|
|
1681
|
+
if (reason)
|
|
1682
|
+
rb_sys_fail(reason);
|
|
1683
|
+
return list;
|
|
1684
|
+
|
|
1685
|
+
#undef EXTRA_SPACE
|
|
1686
|
+
#elif defined(_WIN32)
|
|
1687
|
+
typedef struct ip_adapter_unicast_address_st {
|
|
1688
|
+
unsigned LONG_LONG dummy0;
|
|
1689
|
+
struct ip_adapter_unicast_address_st *Next;
|
|
1690
|
+
struct {
|
|
1691
|
+
struct sockaddr *lpSockaddr;
|
|
1692
|
+
int iSockaddrLength;
|
|
1693
|
+
} Address;
|
|
1694
|
+
int dummy1;
|
|
1695
|
+
int dummy2;
|
|
1696
|
+
int dummy3;
|
|
1697
|
+
long dummy4;
|
|
1698
|
+
long dummy5;
|
|
1699
|
+
long dummy6;
|
|
1700
|
+
} ip_adapter_unicast_address_t;
|
|
1701
|
+
typedef struct ip_adapter_anycast_address_st {
|
|
1702
|
+
unsigned LONG_LONG dummy0;
|
|
1703
|
+
struct ip_adapter_anycast_address_st *Next;
|
|
1704
|
+
struct {
|
|
1705
|
+
struct sockaddr *lpSockaddr;
|
|
1706
|
+
int iSockaddrLength;
|
|
1707
|
+
} Address;
|
|
1708
|
+
} ip_adapter_anycast_address_t;
|
|
1709
|
+
typedef struct ip_adapter_addresses_st {
|
|
1710
|
+
unsigned LONG_LONG dummy0;
|
|
1711
|
+
struct ip_adapter_addresses_st *Next;
|
|
1712
|
+
void *dummy1;
|
|
1713
|
+
ip_adapter_unicast_address_t *FirstUnicastAddress;
|
|
1714
|
+
ip_adapter_anycast_address_t *FirstAnycastAddress;
|
|
1715
|
+
void *dummy2;
|
|
1716
|
+
void *dummy3;
|
|
1717
|
+
void *dummy4;
|
|
1718
|
+
void *dummy5;
|
|
1719
|
+
void *dummy6;
|
|
1720
|
+
BYTE dummy7[8];
|
|
1721
|
+
DWORD dummy8;
|
|
1722
|
+
DWORD dummy9;
|
|
1723
|
+
DWORD dummy10;
|
|
1724
|
+
DWORD IfType;
|
|
1725
|
+
int OperStatus;
|
|
1726
|
+
DWORD dummy12;
|
|
1727
|
+
DWORD dummy13[16];
|
|
1728
|
+
void *dummy14;
|
|
1729
|
+
} ip_adapter_addresses_t;
|
|
1730
|
+
typedef ULONG (WINAPI *GetAdaptersAddresses_t)(ULONG, ULONG, PVOID, ip_adapter_addresses_t *, PULONG);
|
|
1731
|
+
HMODULE h;
|
|
1732
|
+
GetAdaptersAddresses_t pGetAdaptersAddresses;
|
|
1733
|
+
ULONG len;
|
|
1734
|
+
DWORD ret;
|
|
1735
|
+
ip_adapter_addresses_t *adapters;
|
|
1736
|
+
VALUE list;
|
|
1737
|
+
|
|
1738
|
+
h = LoadLibrary("iphlpapi.dll");
|
|
1739
|
+
if (!h)
|
|
1740
|
+
rb_notimplement();
|
|
1741
|
+
pGetAdaptersAddresses = (GetAdaptersAddresses_t)GetProcAddress(h, "GetAdaptersAddresses");
|
|
1742
|
+
if (!pGetAdaptersAddresses) {
|
|
1743
|
+
FreeLibrary(h);
|
|
1744
|
+
rb_notimplement();
|
|
1745
|
+
}
|
|
1746
|
+
|
|
1747
|
+
ret = pGetAdaptersAddresses(AF_UNSPEC, 0, NULL, NULL, &len);
|
|
1748
|
+
if (ret != ERROR_SUCCESS && ret != ERROR_BUFFER_OVERFLOW) {
|
|
1749
|
+
errno = rb_w32_map_errno(ret);
|
|
1750
|
+
FreeLibrary(h);
|
|
1751
|
+
rb_sys_fail("GetAdaptersAddresses");
|
|
1752
|
+
}
|
|
1753
|
+
adapters = (ip_adapter_addresses_t *)ALLOCA_N(BYTE, len);
|
|
1754
|
+
ret = pGetAdaptersAddresses(AF_UNSPEC, 0, NULL, adapters, &len);
|
|
1755
|
+
if (ret != ERROR_SUCCESS) {
|
|
1756
|
+
errno = rb_w32_map_errno(ret);
|
|
1757
|
+
FreeLibrary(h);
|
|
1758
|
+
rb_sys_fail("GetAdaptersAddresses");
|
|
1759
|
+
}
|
|
1760
|
+
|
|
1761
|
+
list = rb_ary_new();
|
|
1762
|
+
for (; adapters; adapters = adapters->Next) {
|
|
1763
|
+
ip_adapter_unicast_address_t *uni;
|
|
1764
|
+
ip_adapter_anycast_address_t *any;
|
|
1765
|
+
if (adapters->OperStatus != 1) /* 1 means IfOperStatusUp */
|
|
1766
|
+
continue;
|
|
1767
|
+
for (uni = adapters->FirstUnicastAddress; uni; uni = uni->Next) {
|
|
1768
|
+
#ifndef INET6
|
|
1769
|
+
if (uni->Address.lpSockaddr->sa_family == AF_INET)
|
|
1770
|
+
#else
|
|
1771
|
+
if (IS_IP_FAMILY(uni->Address.lpSockaddr->sa_family))
|
|
1772
|
+
#endif
|
|
1773
|
+
rb_ary_push(list, sockaddr_obj(uni->Address.lpSockaddr));
|
|
1774
|
+
}
|
|
1775
|
+
for (any = adapters->FirstAnycastAddress; any; any = any->Next) {
|
|
1776
|
+
#ifndef INET6
|
|
1777
|
+
if (any->Address.lpSockaddr->sa_family == AF_INET)
|
|
1778
|
+
#else
|
|
1779
|
+
if (IS_IP_FAMILY(any->Address.lpSockaddr->sa_family))
|
|
1780
|
+
#endif
|
|
1781
|
+
rb_ary_push(list, sockaddr_obj(any->Address.lpSockaddr));
|
|
1782
|
+
}
|
|
1783
|
+
}
|
|
1784
|
+
|
|
1785
|
+
FreeLibrary(h);
|
|
1786
|
+
return list;
|
|
1787
|
+
#endif
|
|
1788
|
+
}
|
|
1789
|
+
#else
|
|
1790
|
+
#define socket_s_ip_address_list rb_f_notimplement
|
|
1791
|
+
#endif
|
|
1792
|
+
|
|
1793
|
+
/*
|
|
1794
|
+
* Document-class: ::Socket < BasicSocket
|
|
1795
|
+
*
|
|
1796
|
+
* Class +Socket+ provides access to the underlying operating system
|
|
1797
|
+
* socket implementations. It can be used to provide more operating system
|
|
1798
|
+
* specific functionality than the protocol-specific socket classes.
|
|
1799
|
+
*
|
|
1800
|
+
* The constants defined under Socket::Constants are also defined under Socket.
|
|
1801
|
+
* For example, Socket::AF_INET is usable as well as Socket::Constants::AF_INET.
|
|
1802
|
+
* See Socket::Constants for the list of constants.
|
|
1803
|
+
*
|
|
1804
|
+
* === Exception Handling
|
|
1805
|
+
* Ruby's implementation of +Socket+ causes an exception to be raised
|
|
1806
|
+
* based on the error generated by the system dependent implementation.
|
|
1807
|
+
* This is why the methods are documented in a way that isolate
|
|
1808
|
+
* Unix-based system exceptions from Windows based exceptions. If more
|
|
1809
|
+
* information on particular exception is needed please refer to the
|
|
1810
|
+
* Unix manual pages or the Windows WinSock reference.
|
|
1811
|
+
*
|
|
1812
|
+
* === Convenient methods
|
|
1813
|
+
*
|
|
1814
|
+
* Although the general way to create socket is Socket.new,
|
|
1815
|
+
* there are several methods for socket creation for most cases.
|
|
1816
|
+
*
|
|
1817
|
+
* * TCP client socket: Socket.tcp, TCPSocket.open
|
|
1818
|
+
* * TCP server socket: Socket.tcp_server_loop, TCPServer.open
|
|
1819
|
+
* * UNIX client socket: Socket.unix, UNIXSocket.open
|
|
1820
|
+
* * UNIX server socket: Socket.unix_server_loop, UNIXServer.open
|
|
1821
|
+
*
|
|
1822
|
+
* === Documentation by
|
|
1823
|
+
* * Zach Dennis
|
|
1824
|
+
* * Sam Roberts
|
|
1825
|
+
* * <em>Programming Ruby</em> from The Pragmatic Bookshelf.
|
|
1826
|
+
*
|
|
1827
|
+
* Much material in this documentation is taken with permission from
|
|
1828
|
+
* <em>Programming Ruby</em> from The Pragmatic Bookshelf.
|
|
1829
|
+
*/
|
|
1830
|
+
void
|
|
1831
|
+
Init_socket()
|
|
1832
|
+
{
|
|
1833
|
+
rsock_init_basicsocket();
|
|
1834
|
+
|
|
1835
|
+
rb_cSocket = rb_define_class("Socket", rb_cBasicSocket);
|
|
1836
|
+
|
|
1837
|
+
rsock_init_socket_init();
|
|
1838
|
+
|
|
1839
|
+
rb_define_method(rb_cSocket, "initialize", sock_initialize, -1);
|
|
1840
|
+
rb_define_method(rb_cSocket, "connect", sock_connect, 1);
|
|
1841
|
+
rb_define_method(rb_cSocket, "connect_nonblock", sock_connect_nonblock, 1);
|
|
1842
|
+
rb_define_method(rb_cSocket, "bind", sock_bind, 1);
|
|
1843
|
+
rb_define_method(rb_cSocket, "listen", rsock_sock_listen, 1);
|
|
1844
|
+
rb_define_method(rb_cSocket, "accept", sock_accept, 0);
|
|
1845
|
+
rb_define_method(rb_cSocket, "accept_nonblock", sock_accept_nonblock, 0);
|
|
1846
|
+
rb_define_method(rb_cSocket, "sysaccept", sock_sysaccept, 0);
|
|
1847
|
+
|
|
1848
|
+
rb_define_method(rb_cSocket, "recvfrom", sock_recvfrom, -1);
|
|
1849
|
+
rb_define_method(rb_cSocket, "recvfrom_nonblock", sock_recvfrom_nonblock, -1);
|
|
1850
|
+
|
|
1851
|
+
rb_define_singleton_method(rb_cSocket, "socketpair", rsock_sock_s_socketpair, -1);
|
|
1852
|
+
rb_define_singleton_method(rb_cSocket, "pair", rsock_sock_s_socketpair, -1);
|
|
1853
|
+
rb_define_singleton_method(rb_cSocket, "gethostname", sock_gethostname, 0);
|
|
1854
|
+
rb_define_singleton_method(rb_cSocket, "gethostbyname", sock_s_gethostbyname, 1);
|
|
1855
|
+
rb_define_singleton_method(rb_cSocket, "gethostbyaddr", sock_s_gethostbyaddr, -1);
|
|
1856
|
+
rb_define_singleton_method(rb_cSocket, "getservbyname", sock_s_getservbyname, -1);
|
|
1857
|
+
rb_define_singleton_method(rb_cSocket, "getservbyport", sock_s_getservbyport, -1);
|
|
1858
|
+
rb_define_singleton_method(rb_cSocket, "getaddrinfo", sock_s_getaddrinfo, -1);
|
|
1859
|
+
rb_define_singleton_method(rb_cSocket, "getnameinfo", sock_s_getnameinfo, -1);
|
|
1860
|
+
rb_define_singleton_method(rb_cSocket, "sockaddr_in", sock_s_pack_sockaddr_in, 2);
|
|
1861
|
+
rb_define_singleton_method(rb_cSocket, "pack_sockaddr_in", sock_s_pack_sockaddr_in, 2);
|
|
1862
|
+
rb_define_singleton_method(rb_cSocket, "unpack_sockaddr_in", sock_s_unpack_sockaddr_in, 1);
|
|
1863
|
+
#ifdef HAVE_SYS_UN_H
|
|
1864
|
+
rb_define_singleton_method(rb_cSocket, "sockaddr_un", sock_s_pack_sockaddr_un, 1);
|
|
1865
|
+
rb_define_singleton_method(rb_cSocket, "pack_sockaddr_un", sock_s_pack_sockaddr_un, 1);
|
|
1866
|
+
rb_define_singleton_method(rb_cSocket, "unpack_sockaddr_un", sock_s_unpack_sockaddr_un, 1);
|
|
1867
|
+
#endif
|
|
1868
|
+
|
|
1869
|
+
rb_define_singleton_method(rb_cSocket, "ip_address_list", socket_s_ip_address_list, 0);
|
|
1870
|
+
}
|