Advertisement
Guest User

Untitled

a guest
Jul 19th, 2018
196
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. #==============================================================================
  2. # ** Module Win32 - Handles numerical based data.
  3. #------------------------------------------------------------------------------
  4. # Author    Ruby
  5. # Version   1.8.1
  6. #==============================================================================
  7.  
  8. module Win32
  9.  
  10.   #----------------------------------------------------------------------------
  11.   # ● Retrieves data from a pointer.
  12.   #----------------------------------------------------------------------------
  13.   def copymem(len)
  14.     buf = "\0" * len
  15.     Win32API.new('kernel32', 'RtlMoveMemory', 'ppl', '').call(buf, self, len)
  16.     buf
  17.   end
  18.  
  19. end
  20.  
  21. # Extends the numeric class.
  22. class Numeric
  23.   include Win32
  24. end
  25.  
  26. # Extends the string class.
  27. class String
  28.   include Win32
  29. end
  30.  
  31. #==============================================================================
  32. # ** Module Winsock - Maps out the functions held in the Winsock DLL.
  33. #------------------------------------------------------------------------------
  34. # Author    Ruby
  35. # Version   1.8.1
  36. #==============================================================================
  37.  
  38. module Winsock
  39.  
  40.   DLL = 'ws2_32'
  41.  
  42.   #----------------------------------------------------------------------------
  43.   # * Accept Connection
  44.   #----------------------------------------------------------------------------
  45.   def self.accept(*args)
  46.     Win32API.new(DLL, 'accept', 'ppl', 'l').call(*args)
  47.   end
  48.   #----------------------------------------------------------------------------
  49.   # * Bind
  50.   #----------------------------------------------------------------------------
  51.   def self.bind(*args)
  52.     Win32API.new(DLL, 'bind', 'ppl', 'l').call(*args)
  53.   end
  54.   #----------------------------------------------------------------------------
  55.   # * Close Socket
  56.   #----------------------------------------------------------------------------
  57.   def self.closesocket(*args)
  58.     Win32API.new(DLL, 'closesocket', 'p', 'l').call(*args)
  59.   end  
  60.   #----------------------------------------------------------------------------
  61.   # * Connect
  62.   #----------------------------------------------------------------------------
  63.   def self.connect(*args)
  64.     Win32API.new(DLL, 'connect', 'ppl', 'l').call(*args)
  65.   end    
  66.   #----------------------------------------------------------------------------
  67.   # * Get host (Using Adress)
  68.   #----------------------------------------------------------------------------
  69.   def self.gethostbyaddr(*args)
  70.     Win32API.new(DLL, 'gethostbyaddr', 'pll', 'l').call(*args)
  71.   end
  72.   #----------------------------------------------------------------------------
  73.   # * Get host (Using Name)
  74.   #----------------------------------------------------------------------------
  75.   def self.gethostbyname(*args)
  76.     Win32API.new(DLL, 'gethostbyname', 'p', 'l').call(*args)
  77.   end
  78.   #----------------------------------------------------------------------------
  79.   # * Get host's Name
  80.   #----------------------------------------------------------------------------
  81.   def self.gethostname(*args)
  82.     Win32API.new(DLL, 'gethostname', 'pl', '').call(*args)
  83.   end
  84.   #----------------------------------------------------------------------------
  85.   # * Get Server (Using Name)
  86.   #----------------------------------------------------------------------------
  87.   def self.getservbyname(*args)
  88.     Win32API.new(DLL, 'getservbyname', 'pp', 'p').call(*args)
  89.   end
  90.   #----------------------------------------------------------------------------
  91.   # * HT OnL
  92.   #----------------------------------------------------------------------------
  93.   def self.htonl(*args)
  94.     Win32API.new(DLL, 'htonl', 'l', 'l').call(*args)
  95.   end
  96.   #----------------------------------------------------------------------------
  97.   # * HT OnS
  98.   #----------------------------------------------------------------------------
  99.   def self.htons(*args)
  100.     Win32API.new(DLL, 'htons', 'l', 'l').call(*args)
  101.   end
  102.   #----------------------------------------------------------------------------
  103.   # * Inet Adress
  104.   #----------------------------------------------------------------------------
  105.   def self.inet_addr(*args)
  106.     Win32API.new(DLL, 'inet_addr', 'p', 'l').call(*args)
  107.   end
  108.   #----------------------------------------------------------------------------
  109.   # * Inet NtOA
  110.   #----------------------------------------------------------------------------
  111.   def self.inet_ntoa(*args)
  112.     Win32API.new(DLL, 'inet_ntoa', 'l', 'p').call(*args)
  113.   end  
  114.   #----------------------------------------------------------------------------
  115.   # * Listen
  116.   #----------------------------------------------------------------------------
  117.   def self.listen(*args)
  118.     Win32API.new(DLL, 'listen', 'pl', 'l').call(*args)
  119.   end
  120.   #----------------------------------------------------------------------------
  121.   # * Recieve
  122.   #----------------------------------------------------------------------------
  123.   def self.recv(*args)
  124.     Win32API.new(DLL, 'recv', 'ppll', 'l').call(*args)
  125.   end
  126.   #----------------------------------------------------------------------------
  127.   # * Select
  128.   #----------------------------------------------------------------------------
  129.   def self.select(*args)
  130.     Win32API.new(DLL, 'select', 'lpppp', 'l').call(*args)
  131.   end
  132.   #----------------------------------------------------------------------------
  133.   # * Send
  134.   #----------------------------------------------------------------------------
  135.   def self.send(*args)
  136.     Win32API.new(DLL, 'send', 'ppll', 'l').call(*args)
  137.   end
  138.   #----------------------------------------------------------------------------
  139.   # * Set Socket Options
  140.   #----------------------------------------------------------------------------
  141.   def self.setsockopt(*args)
  142.     Win32API.new(DLL, 'setsockopt', 'pllpl', 'l').call(*args)
  143.   end  
  144.   #----------------------------------------------------------------------------
  145.   # * Shutdown
  146.   #----------------------------------------------------------------------------
  147.   def self.shutdown(*args)
  148.     Win32API.new(DLL, 'shutdown', 'pl', 'l').call(*args)
  149.   end
  150.   #----------------------------------------------------------------------------
  151.   # * Socket
  152.   #----------------------------------------------------------------------------
  153.   def self.socket(*args)
  154.     Win32API.new(DLL, 'socket', 'lll', 'l').call(*args)  
  155.   end
  156.   #----------------------------------------------------------------------------
  157.   # * Get Last Error
  158.   #----------------------------------------------------------------------------
  159.   def self.WSAGetLastError(*args)
  160.     Win32API.new(DLL, 'WSAGetLastError', '', 'l').call(*args)
  161.   end
  162.  
  163. end
  164.  
  165. #==============================================================================
  166. # ** Socket - Creates and manages sockets.
  167. #------------------------------------------------------------------------------
  168. # Author    Ruby
  169. # Version   1.8.1
  170. #==============================================================================
  171.  
  172. class Socket
  173.  
  174.   #----------------------------------------------------------------------------
  175.   # ● Constants
  176.   #----------------------------------------------------------------------------
  177.   AF_UNSPEC                 = 0  
  178.   AF_UNIX                   = 1
  179.   AF_INET                   = 2
  180.   AF_IPX                    = 6
  181.   AF_APPLETALK              = 16
  182.  
  183.   PF_UNSPEC                 = 0  
  184.   PF_UNIX                   = 1
  185.   PF_INET                   = 2
  186.   PF_IPX                    = 6
  187.   PF_APPLETALK              = 16
  188.  
  189.   SOCK_STREAM               = 1
  190.   SOCK_DGRAM                = 2
  191.   SOCK_RAW                  = 3
  192.   SOCK_RDM                  = 4
  193.   SOCK_SEQPACKET            = 5
  194.  
  195.   IPPROTO_IP                = 0
  196.   IPPROTO_ICMP              = 1
  197.   IPPROTO_IGMP              = 2
  198.   IPPROTO_GGP               = 3
  199.   IPPROTO_TCP               = 6
  200.   IPPROTO_PUP               = 12
  201.   IPPROTO_UDP               = 17
  202.   IPPROTO_IDP               = 22
  203.   IPPROTO_ND                = 77
  204.   IPPROTO_RAW               = 255
  205.   IPPROTO_MAX               = 256
  206.  
  207.   SOL_SOCKET                = 65535
  208.  
  209.   SO_DEBUG                  = 1
  210.   SO_REUSEADDR              = 4
  211.   SO_KEEPALIVE              = 8
  212.   SO_DONTROUTE              = 16
  213.   SO_BROADCAST              = 32
  214.   SO_LINGER                 = 128
  215.   SO_OOBINLINE              = 256
  216.   SO_RCVLOWAT               = 4100
  217.   SO_SNDTIMEO               = 4101
  218.   SO_RCVTIMEO               = 4102
  219.   SO_ERROR                  = 4103
  220.   SO_TYPE                   = 4104
  221.   SO_SNDBUF                 = 4097
  222.   SO_RCVBUF                 = 4098
  223.   SO_SNDLOWAT               = 4099
  224.  
  225.   TCP_NODELAY               = 1
  226.  
  227.   MSG_OOB                   = 1
  228.   MSG_PEEK                  = 2
  229.   MSG_DONTROUTE             = 4
  230.  
  231.   IP_OPTIONS                = 1
  232.   IP_DEFAULT_MULTICAST_LOOP = 1
  233.   IP_DEFAULT_MULTICAST_TTL  = 1
  234.   IP_MULTICAST_IF           = 2
  235.   IP_MULTICAST_TTL          = 3
  236.   IP_MULTICAST_LOOP         = 4
  237.   IP_ADD_MEMBERSHIP         = 5
  238.   IP_DROP_MEMBERSHIP        = 6
  239.   IP_TTL                    = 7
  240.   IP_TOS                    = 8
  241.   IP_MAX_MEMBERSHIPS        = 20
  242.  
  243.   EAI_ADDRFAMILY            = 1
  244.   EAI_AGAIN                 = 2
  245.   EAI_BADFLAGS              = 3
  246.   EAI_FAIL                  = 4
  247.   EAI_FAMILY                = 5
  248.   EAI_MEMORY                = 6
  249.   EAI_NODATA                = 7
  250.   EAI_NONAME                = 8
  251.   EAI_SERVICE               = 9
  252.   EAI_SOCKTYPE              = 10
  253.   EAI_SYSTEM                = 11
  254.   EAI_BADHINTS              = 12
  255.   EAI_PROTOCOL              = 13
  256.   EAI_MAX                   = 14
  257.  
  258.   AI_PASSIVE                = 1
  259.   AI_CANONNAME              = 2
  260.   AI_NUMERICHOST            = 4
  261.   AI_MASK                   = 7
  262.   AI_ALL                    = 256
  263.   AI_V4MAPPED_CFG           = 512
  264.   AI_ADDRCONFIG             = 1024
  265.   AI_DEFAULT                = 1536
  266.   AI_V4MAPPED               = 2048
  267.  
  268.   #----------------------------------------------------------------------------
  269.   # ● Returns the associated IP address for the given hostname.
  270.   #----------------------------------------------------------------------------  
  271.   def self.getaddress(host)
  272.     gethostbyname(host)[3].unpack('C4').join('.')
  273.   end
  274.   #----------------------------------------------------------------------------
  275.   # ● Returns the associated IP address for the given hostname.
  276.   #----------------------------------------------------------------------------  
  277.   def self.getservice(serv)
  278.     case serv
  279.     when Numeric
  280.       return serv
  281.     when String
  282.       return getservbyname(serv)
  283.     else
  284.       raise 'Please us an interger or string for services.'
  285.     end
  286.   end
  287.   #----------------------------------------------------------------------------
  288.   # ● Returns information about the given hostname.
  289.   #----------------------------------------------------------------------------
  290.   def self.gethostbyname(name)
  291.     raise SocketError::ENOASSOCHOST if (ptr = Winsock.gethostbyname(name)) == 0
  292.     host = ptr.copymem(16).unpack('iissi')
  293.     [host[0].copymem(64).split("\0")[0], [], host[2], host[4].copymem(4).unpack('l')[0].copymem(4)]
  294.   end
  295.   #----------------------------------------------------------------------------
  296.   # ● Returns the user's hostname.
  297.   #----------------------------------------------------------------------------  
  298.   def self.gethostname
  299.     buf = "\0" * 256
  300.     Winsock.gethostname(buf, 256)
  301.     buf.strip
  302.   end
  303.   #----------------------------------------------------------------------------
  304.   # ● Returns information about the given service.
  305.   #----------------------------------------------------------------------------
  306.   def self.getservbyname(name)
  307.     case name
  308.     when /echo/i
  309.       return 7
  310.     when /daytime/i
  311.       return 13
  312.     when /ftp/i
  313.       return 21
  314.     when /telnet/i
  315.       return 23
  316.     when /smtp/i
  317.       return 25
  318.     when /time/i
  319.       return 37
  320.     when /http/i
  321.       return 80
  322.     when /pop/i
  323.       return 110
  324.     else
  325.       raise 'Service not recognized.'
  326.     end
  327.   end
  328.   #----------------------------------------------------------------------------
  329.   # ● Creates an INET-sockaddr struct.
  330.   #----------------------------------------------------------------------------  
  331.   def self.sockaddr_in(port, host)
  332.     begin
  333.       [AF_INET, getservice(port)].pack('sn') + gethostbyname(host)[3] + [].pack('x8')
  334.     rescue
  335.     end
  336.   end
  337.   #----------------------------------------------------------------------------
  338.   # ● Creates a new socket and connects it to the given host and port.
  339.   #----------------------------------------------------------------------------  
  340.   def self.open(*args)
  341.     socket = new(*args)
  342.     if block_given?
  343.       begin
  344.         yield socket
  345.       ensure
  346.         socket.close
  347.       end
  348.     end
  349.     nil
  350.   end
  351.   #----------------------------------------------------------------------------
  352.   # ● Creates a new socket.
  353.   #----------------------------------------------------------------------------  
  354.   def initialize(domain, type, protocol)
  355.     SocketError.check if (@fd = Winsock.socket(domain, type, protocol)) == -1
  356.     @fd
  357.   end
  358.   #----------------------------------------------------------------------------
  359.   # ● Accepts incoming connections.
  360.   #----------------------------------------------------------------------------  
  361.   def accept(flags = 0)
  362.     buf = "\0" * 16
  363.     SocketError.check if Winsock.accept(@fd, buf, flags) == -1
  364.     buf
  365.   end
  366.   #----------------------------------------------------------------------------
  367.   # ● Binds a socket to the given sockaddr.
  368.   #----------------------------------------------------------------------------  
  369.   def bind(sockaddr)
  370.     SocketError.check if (ret = Winsock.bind(@fd, sockaddr, sockaddr.size)) == -1
  371.     ret
  372.   end
  373.   #----------------------------------------------------------------------------
  374.   # ● Closes a socket.
  375.   #----------------------------------------------------------------------------  
  376.   def close
  377.     SocketError.check if (ret = Winsock.closesocket(@fd)) == -1
  378.     ret
  379.   end
  380.   #----------------------------------------------------------------------------
  381.   # ● Connects a socket to the given sockaddr.
  382.   #----------------------------------------------------------------------------  
  383.   def connect(sockaddr)
  384.     SocketError.check if (ret = Winsock.connect(@fd, sockaddr, sockaddr.size)) == -1
  385.     ret
  386.   end
  387.   #----------------------------------------------------------------------------
  388.   # ● Listens for incoming connections.
  389.   #----------------------------------------------------------------------------  
  390.   def listen(backlog)
  391.     SocketError.check if (ret = Winsock.listen(@fd, backlog)) == -1
  392.     ret
  393.   end
  394.   #----------------------------------------------------------------------------
  395.   # ● Checks waiting data's status.
  396.   #----------------------------------------------------------------------------  
  397.   def select(timeout)
  398.     SocketError.check if (ret = Winsock.select(1, [1, @fd].pack('ll'), 0, 0, [timeout, timeout * 1000000].pack('ll'))) == -1
  399.     ret
  400.   end
  401.   #----------------------------------------------------------------------------
  402.   # ● Checks if data is waiting.
  403.   #----------------------------------------------------------------------------  
  404.   def ready?
  405.     not select(0) == 0
  406.   end  
  407.   #----------------------------------------------------------------------------
  408.   # ● Reads data from socket.
  409.   #----------------------------------------------------------------------------  
  410.   def read(len)
  411.     buf = "\0" * len
  412.     Win32API.new('msvcrt', '_read', 'lpl', 'l').call(@fd, buf, len)
  413.     buf
  414.   end
  415.   #----------------------------------------------------------------------------
  416.   # ● Returns recieved data.
  417.   #----------------------------------------------------------------------------  
  418.   def recv(len, flags = 0)
  419.     buf = "\0" * len
  420.     SocketError.check if Winsock.recv(@fd, buf, buf.size, flags) == -1
  421.     buf
  422.   end
  423.   #----------------------------------------------------------------------------
  424.   # ● Sends data to a host.
  425.   #----------------------------------------------------------------------------  
  426.   def send(data, flags = 0)
  427.     SocketError.check if (ret = Winsock.send(@fd, data, data.size, flags)) == -1
  428.     ret
  429.   end
  430.   #----------------------------------------------------------------------------
  431.   # ● Writes data to socket.
  432.   #----------------------------------------------------------------------------  
  433.   def write(data)
  434.     Win32API.new('msvcrt', '_write', 'lpl', 'l').call(@fd, data, 1)
  435.   end
  436.  
  437. end
  438.  
  439. #==============================================================================
  440. # ** TCPSocket - Creates and manages TCP sockets.
  441. #------------------------------------------------------------------------------
  442. # Author    Ruby
  443. # Version   1.8.1
  444. #==============================================================================
  445.  
  446. class TCPSocket < Socket
  447.  
  448.   #----------------------------------------------------------------------------
  449.   # ● Creates a new socket and connects it to the given host and port.
  450.   #----------------------------------------------------------------------------  
  451.   def self.open(*args)
  452.     socket = new(*args)
  453.     if block_given?
  454.       begin
  455.         yield socket
  456.       ensure
  457.         socket.close
  458.       end
  459.     end
  460.     nil
  461.   end
  462.   #----------------------------------------------------------------------------
  463.   # ● Creates a new socket and connects it to the given host and port.
  464.   #----------------------------------------------------------------------------  
  465.   def initialize(host, port)
  466.     super(AF_INET, SOCK_STREAM, IPPROTO_TCP)
  467.     connect(Socket.sockaddr_in(port, host))
  468.   end
  469.  
  470. end
  471.  
  472. #==============================================================================
  473. # ** SocketError
  474. #------------------------------------------------------------------------------
  475. # Default exception class for sockets.
  476. #==============================================================================
  477.  
  478. class SocketError < StandardError
  479.  
  480.   ENOASSOCHOST = 'getaddrinfo: no address associated with hostname.'
  481.  
  482.   # fixed by: https://lthzelda.wordpress.com/2010/04/28/rm-4-tcp-sockets-in-rpg-maker-vx/
  483.   def self.check
  484.     errno = Winsock.WSAGetLastError
  485.     const = Errno.constants.detect {|c| Errno.const_get(c).new.errno == errno }
  486.     if const
  487.       raise Errno.const_get(const)
  488.     else
  489.       raise "Unknown network error code: #{errno}"
  490.     end
  491.   end
  492.  
  493. end
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement