/rpython/rlib/_rsocket_rffi.py
Python | 691 lines | 579 code | 78 blank | 34 comment | 55 complexity | cdb6137375759bf299d4e1235b85ba11 MD5 | raw file
Possible License(s): AGPL-3.0, BSD-3-Clause, Apache-2.0
- from rpython.rtyper.lltypesystem import rffi
- from rpython.rtyper.lltypesystem import lltype
- from rpython.rtyper.tool import rffi_platform as platform
- from rpython.rtyper.lltypesystem.rffi import CCHARP
- from rpython.translator.tool.cbuild import ExternalCompilationInfo
- from rpython.translator.platform import platform as target_platform
- from rpython.rlib.rarithmetic import intmask, r_uint
- import os,sys
- _POSIX = os.name == "posix"
- _WIN32 = sys.platform == "win32"
- _MSVC = target_platform.name == "msvc"
- _MINGW = target_platform.name == "mingw32"
- _SOLARIS = sys.platform == "sunos5"
- _MACOSX = sys.platform == "darwin"
- _HAS_AF_PACKET = sys.platform.startswith('linux') # only Linux for now
- if _POSIX:
- includes = ('sys/types.h',
- 'sys/socket.h',
- 'sys/un.h',
- 'sys/poll.h',
- 'sys/select.h',
- 'sys/types.h',
- 'netinet/in.h',
- 'netinet/tcp.h',
- 'unistd.h',
- 'fcntl.h',
- 'stdio.h',
- 'netdb.h',
- 'arpa/inet.h',
- 'stdint.h',
- 'errno.h',
- )
- if _HAS_AF_PACKET:
- includes += ('netpacket/packet.h',
- 'sys/ioctl.h',
- 'net/if.h')
- cond_includes = [('AF_NETLINK', 'linux/netlink.h')]
- libraries = ()
- calling_conv = 'c'
- HEADER = ''.join(['#include <%s>\n' % filename for filename in includes])
- COND_HEADER = ''.join(['#ifdef %s\n#include <%s>\n#endif\n' % cond_include
- for cond_include in cond_includes])
- if _SOLARIS:
- libraries = libraries + ('socket', 'nsl')
- if _WIN32:
- includes = ()
- libraries = ('ws2_32',)
- calling_conv = 'win'
- header_lines = [
- '#include <WinSock2.h>',
- '#include <WS2tcpip.h>',
- # winsock2 defines AF_UNIX, but not sockaddr_un
- '#undef AF_UNIX',
- ]
- if _MSVC:
- header_lines.extend([
- '#include <Mstcpip.h>',
- # these types do not exist on microsoft compilers
- 'typedef int ssize_t;',
- 'typedef unsigned __int16 uint16_t;',
- 'typedef unsigned __int32 uint32_t;',
- ])
- else: # MINGW
- includes = ('stdint.h',)
- header_lines.extend([
- '''\
- #ifndef _WIN32_WINNT
- #define _WIN32_WINNT 0x0501
- #endif''',
- '#define SIO_RCVALL _WSAIOW(IOC_VENDOR,1)',
- '#define SIO_KEEPALIVE_VALS _WSAIOW(IOC_VENDOR,4)',
- '#define RCVALL_OFF 0',
- '#define RCVALL_ON 1',
- '#define RCVALL_SOCKETLEVELONLY 2',
- '''\
- #ifndef __MINGW32__
- struct tcp_keepalive {
- u_long onoff;
- u_long keepalivetime;
- u_long keepaliveinterval;
- };
- #endif
- '''
- ])
- HEADER = '\n'.join(header_lines)
- COND_HEADER = ''
- constants = {}
- eci = ExternalCompilationInfo(
- post_include_bits = [HEADER, COND_HEADER],
- includes = includes,
- libraries = libraries,
- )
- class CConfig:
- _compilation_info_ = eci
- # constants
- linux = platform.Defined('linux')
- WIN32 = platform.Defined('_WIN32')
- O_RDONLY = platform.DefinedConstantInteger('O_RDONLY')
- O_WRONLY = platform.DefinedConstantInteger('O_WRONLY')
- O_RDWR = platform.DefinedConstantInteger('O_RDWR')
- O_NONBLOCK = platform.DefinedConstantInteger('O_NONBLOCK')
- F_GETFL = platform.DefinedConstantInteger('F_GETFL')
- F_SETFL = platform.DefinedConstantInteger('F_SETFL')
- FIONBIO = platform.DefinedConstantInteger('FIONBIO')
- INVALID_SOCKET = platform.DefinedConstantInteger('INVALID_SOCKET')
- INET_ADDRSTRLEN = platform.DefinedConstantInteger('INET_ADDRSTRLEN')
- INET6_ADDRSTRLEN= platform.DefinedConstantInteger('INET6_ADDRSTRLEN')
- EINTR = platform.DefinedConstantInteger('EINTR')
- WSAEINTR = platform.DefinedConstantInteger('WSAEINTR')
- EINPROGRESS = platform.DefinedConstantInteger('EINPROGRESS')
- WSAEINPROGRESS = platform.DefinedConstantInteger('WSAEINPROGRESS')
- EWOULDBLOCK = platform.DefinedConstantInteger('EWOULDBLOCK')
- WSAEWOULDBLOCK = platform.DefinedConstantInteger('WSAEWOULDBLOCK')
- EAFNOSUPPORT = platform.DefinedConstantInteger('EAFNOSUPPORT')
- WSAEAFNOSUPPORT = platform.DefinedConstantInteger('WSAEAFNOSUPPORT')
- EISCONN = platform.DefinedConstantInteger('EISCONN')
- WSAEISCONN = platform.DefinedConstantInteger('WSAEISCONN')
- constant_names = '''
- AF_AAL5 AF_APPLETALK AF_ASH AF_ATMPVC AF_ATMSVC AF_AX25 AF_BLUETOOTH AF_BRIDGE
- AD_DECnet AF_ECONET AF_INET AF_INET6 AF_IPX AF_IRDA AF_KEY AF_LLC AF_NETBEUI
- AF_NETLINK AF_NETROM AF_PACKET AF_PPPOX AF_ROSE AF_ROUTE AF_SECURITY AF_SNA
- AF_UNIX AF_WANPIPE AF_X25 AF_UNSPEC
- AI_ADDRCONFIG AI_ALL AI_CANONNAME AI_DEFAULT AI_MASK AI_NUMERICHOST
- AI_NUMERICSERV AI_PASSIVE AI_V4MAPPED AI_V4MAPPED_CFG
- BTPROTO_L2CAP BTPROTO_SCO BTPROTO_RFCOMM
- EAI_ADDRFAMILY EAI_AGAIN EAI_BADFLAGS EAI_BADHINTS EAI_FAIL EAI_FAMILY EAI_MAX
- EAI_MEMORY EAI_NODATA EAI_NONAME EAI_OVERFLOW EAI_PROTOCOL EAI_SERVICE
- EAI_SOCKTYPE EAI_SYSTEM
- IPPROTO_AH IPPROTO_BIP IPPROTO_DSTOPTS IPPROTO_EGP IPPROTO_EON IPPROTO_ESP
- IPPROTO_FRAGMENT IPPROTO_GGP IPPROTO_GRE IPPROTO_HELLO IPPROTO_HOPOPTS
- IPPROTO_ICMPV6 IPPROTO_IDP IPPROTO_IGMP IPPROTO_IPCOMP IPPROTO_IPIP
- IPPROTO_IPV4 IPPROTO_IPV6 IPPROTO_MAX IPPROTO_MOBILE IPPROTO_ND IPPROTO_NONE
- IPPROTO_PIM IPPROTO_PUP IPPROTO_ROUTING IPPROTO_RSVP IPPROTO_TCP IPPROTO_TP
- IPPROTO_VRRP IPPROTO_XTP
- IPV6_CHECKSUM IPV6_DONTFRAG IPV6_DSTOPTS IPV6_HOPLIMIT IPV6_HOPOPTS
- IPV6_JOIN_GROUP IPV6_LEAVE_GROUP IPV6_MULTICAST_HOPS IPV6_MULTICAST_IF
- IPV6_MULTICAST_LOOP IPV6_NEXTHOP IPV6_PATHMTU IPV6_PKTINFO IPV6_RECVDSTOPTS
- IPV6_RECVHOPLIMIT IPV6_RECVHOPOPTS IPV6_RECVPATHMTU IPV6_RECVPKTINFO
- IPV6_RECVRTHDR IPV6_RECVTCLASS IPV6_RTHDR IPV6_RTHDRDSTOPTS IPV6_RTHDR_TYPE_0
- IPV6_TCLASS IPV6_UNICAST_HOPS IPV6_USE_MIN_MTU IPV6_V6ONLY
- IP_ADD_MEMBERSHIP IP_DEFAULT_MULTICAST_LOOP IP_DEFAULT_MULTICAST_TTL
- IP_DROP_MEMBERSHIP IP_HDRINCL IP_MAX_MEMBERSHIPS IP_MULTICAST_IF
- IP_MULTICAST_LOOP IP_MULTICAST_TTL IP_OPTIONS IP_RECVDSTADDR IP_RECVOPTS
- IP_RECVRETOPTS IP_RETOPTS IP_TOS IP_TTL
- MSG_BTAG MSG_ETAG MSG_CTRUNC MSG_DONTROUTE MSG_DONTWAIT MSG_EOR MSG_OOB
- MSG_PEEK MSG_TRUNC MSG_WAITALL
- NI_DGRAM NI_MAXHOST NI_MAXSERV NI_NAMEREQD NI_NOFQDN NI_NUMERICHOST
- NI_NUMERICSERV
- NETLINK_ROUTE NETLINK_SKIP NETLINK_W1 NETLINK_USERSOCK NETLINK_FIREWALL
- NETLINK_TCPDIAG NETLINK_NFLOG NETLINK_XFRM NETLINK_ARPD NETLINK_ROUTE6
- NETLINK_IP6_FW NETLINK_DNRTMSG NETLINK_TAPBASE
- PACKET_HOST PACKET_BROADCAST PACKET_MULTICAST PACKET_OTHERHOST PACKET_OUTGOING
- PACKET_LOOPBACK PACKET_FASTROUTE
- SOCK_DGRAM SOCK_RAW SOCK_RDM SOCK_SEQPACKET SOCK_STREAM
- SOL_SOCKET SOL_IPX SOL_AX25 SOL_ATALK SOL_NETROM SOL_ROSE
- SO_ACCEPTCONN SO_BROADCAST SO_DEBUG SO_DONTROUTE SO_ERROR SO_EXCLUSIVEADDRUSE
- SO_KEEPALIVE SO_LINGER SO_OOBINLINE SO_RCVBUF SO_RCVLOWAT SO_RCVTIMEO
- SO_REUSEADDR SO_REUSEPORT SO_SNDBUF SO_SNDLOWAT SO_SNDTIMEO SO_TYPE
- SO_USELOOPBACK
- TCP_CORK TCP_DEFER_ACCEPT TCP_INFO TCP_KEEPCNT TCP_KEEPIDLE TCP_KEEPINTVL
- TCP_LINGER2 TCP_MAXSEG TCP_NODELAY TCP_QUICKACK TCP_SYNCNT TCP_WINDOW_CLAMP
- IPX_TYPE
- POLLIN POLLPRI POLLOUT POLLERR POLLHUP POLLNVAL
- POLLRDNORM POLLRDBAND POLLWRNORM POLLWEBAND POLLMSG
- FD_READ FD_WRITE FD_ACCEPT FD_CONNECT FD_CLOSE
- WSA_WAIT_TIMEOUT WSA_WAIT_FAILED INFINITE
- FD_CONNECT_BIT FD_CLOSE_BIT
- WSA_IO_PENDING WSA_IO_INCOMPLETE WSA_INVALID_HANDLE
- WSA_INVALID_PARAMETER WSA_NOT_ENOUGH_MEMORY WSA_OPERATION_ABORTED
- SIO_RCVALL SIO_KEEPALIVE_VALS
- SIOCGIFNAME SIOCGIFINDEX
- '''.split()
- for name in constant_names:
- setattr(CConfig, name, platform.DefinedConstantInteger(name))
- if _WIN32:
- # some SDKs define these values with an enum, #ifdef won't work
- for name in ('RCVALL_ON', 'RCVALL_OFF', 'RCVALL_SOCKETLEVELONLY'):
- setattr(CConfig, name, platform.ConstantInteger(name))
- constant_names.append(name)
- constants["BDADDR_ANY"] = "00:00:00:00:00:00"
- constants["BDADDR_LOCAL"] = "00:00:00:FF:FF:FF"
- constants_w_defaults = [('SOL_IP', 0),
- ('SOL_TCP', 6),
- ('SOL_UDP', 17),
- ('SOMAXCONN', 5),
- ('IPPROTO_IP', 6),
- ('IPPROTO_ICMP', 1),
- ('IPPROTO_TCP', 6),
- ('IPPROTO_UDP', 17),
- ('IPPROTO_RAW', 255),
- ('IPPORT_RESERVED', 1024),
- ('IPPORT_USERRESERVED', 5000),
- ('INADDR_ANY', 0x00000000),
- ('INADDR_BROADCAST', 0xffffffff),
- ('INADDR_LOOPBACK', 0x7F000001),
- ('INADDR_UNSPEC_GROUP', 0xe0000000),
- ('INADDR_ALLHOSTS_GROUP', 0xe0000001),
- ('INADDR_MAX_LOCAL_GROUP', 0xe00000ff),
- ('INADDR_NONE', 0xffffffff),
- ('SHUT_RD', 0),
- ('SHUT_WR', 1),
- ('SHUT_RDWR', 2),
- ('POLLIN', 1),
- ('POLLPRI', 2),
- ('POLLOUT', 4),
- ('POLLERR', 8),
- ('POLLHUP', 16),
- ('FD_SETSIZE', 64),
- ]
- for name, default in constants_w_defaults:
- setattr(CConfig, name, platform.DefinedConstantInteger(name))
- # types
- if _MSVC:
- socketfd_type = rffi.UINT
- else:
- socketfd_type = rffi.INT
- CConfig.uint16_t = platform.SimpleType('uint16_t', rffi.USHORT)
- CConfig.uint32_t = platform.SimpleType('uint32_t', rffi.UINT)
- CConfig.size_t = platform.SimpleType('size_t', rffi.INT)
- CConfig.ssize_t = platform.SimpleType('ssize_t', rffi.INT)
- CConfig.socklen_t = platform.SimpleType('socklen_t', rffi.INT)
- sockaddr_ptr = lltype.Ptr(lltype.ForwardReference())
- addrinfo_ptr = lltype.Ptr(lltype.ForwardReference())
- # struct types
- CConfig.sockaddr = platform.Struct('struct sockaddr',
- [('sa_family', rffi.INT),
- ('sa_data', rffi.CFixedArray(rffi.CHAR, 1))])
- CConfig.in_addr = platform.Struct('struct in_addr',
- [('s_addr', rffi.UINT)])
- CConfig.in6_addr = platform.Struct('struct in6_addr',
- [('s6_addr', rffi.CFixedArray(rffi.CHAR, 16))])
- CConfig.sockaddr_in = platform.Struct('struct sockaddr_in',
- [('sin_family', rffi.INT),
- ('sin_port', rffi.USHORT),
- ('sin_addr', CConfig.in_addr)])
- CConfig.sockaddr_in6 = platform.Struct('struct sockaddr_in6',
- [('sin6_family', rffi.INT),
- ('sin6_port', rffi.USHORT),
- ('sin6_flowinfo', rffi.INT),
- ('sin6_addr', CConfig.in6_addr),
- ('sin6_scope_id', rffi.INT)])
- CConfig.sockaddr_un = platform.Struct('struct sockaddr_un',
- [('sun_family', rffi.INT),
- ('sun_path', rffi.CFixedArray(rffi.CHAR, 1))],
- ifdef='AF_UNIX')
- CConfig.sockaddr_nl = platform.Struct('struct sockaddr_nl',
- [('nl_family', rffi.INT),
- ('nl_pid', rffi.INT),
- ('nl_groups', rffi.INT)],
- ifdef='AF_NETLINK')
- CConfig.addrinfo = platform.Struct('struct addrinfo',
- [('ai_flags', rffi.INT),
- ('ai_family', rffi.INT),
- ('ai_socktype', rffi.INT),
- ('ai_protocol', rffi.INT),
- ('ai_addrlen', rffi.INT),
- ('ai_addr', sockaddr_ptr),
- ('ai_canonname', CCHARP),
- ('ai_next', addrinfo_ptr)])
- CConfig.hostent = platform.Struct('struct hostent',
- [('h_name', CCHARP),
- ('h_aliases', rffi.CCHARPP),
- ('h_addrtype', rffi.INT),
- ('h_length', rffi.INT),
- ('h_addr_list', rffi.CCHARPP),
- ])
- CConfig.servent = platform.Struct('struct servent',
- [('s_name', CCHARP),
- ('s_port', rffi.INT),
- ('s_proto', CCHARP),
- ])
- CConfig.protoent = platform.Struct('struct protoent',
- [('p_proto', rffi.INT),
- ])
- if _POSIX:
- CConfig.nfds_t = platform.SimpleType('nfds_t')
- CConfig.pollfd = platform.Struct('struct pollfd',
- [('fd', socketfd_type),
- ('events', rffi.SHORT),
- ('revents', rffi.SHORT)])
- if _HAS_AF_PACKET:
- CConfig.sockaddr_ll = platform.Struct('struct sockaddr_ll',
- [('sll_family', rffi.INT),
- ('sll_ifindex', rffi.INT),
- ('sll_protocol', rffi.INT),
- ('sll_pkttype', rffi.INT),
- ('sll_hatype', rffi.INT),
- ('sll_addr', rffi.CFixedArray(rffi.CHAR, 8)),
- ('sll_halen', rffi.INT)])
- CConfig.ifreq = platform.Struct('struct ifreq',
- [('ifr_ifindex', rffi.INT),
- ('ifr_name', rffi.CFixedArray(rffi.CHAR, 8))])
- if _WIN32:
- CConfig.WSAEVENT = platform.SimpleType('WSAEVENT', rffi.VOIDP)
- CConfig.WSANETWORKEVENTS = platform.Struct(
- 'struct _WSANETWORKEVENTS',
- [('lNetworkEvents', rffi.LONG),
- ('iErrorCode', rffi.CFixedArray(rffi.INT, 10)), #FD_MAX_EVENTS
- ])
- CConfig.WSAPROTOCOL_INFO = platform.Struct(
- 'WSAPROTOCOL_INFOA',
- []) # Struct is just passed between functions
- CConfig.FROM_PROTOCOL_INFO = platform.DefinedConstantInteger(
- 'FROM_PROTOCOL_INFO')
- CConfig.timeval = platform.Struct('struct timeval',
- [('tv_sec', rffi.LONG),
- ('tv_usec', rffi.LONG)])
- fd_set = rffi.COpaquePtr('fd_set', compilation_info=eci)
- if _WIN32:
- CConfig.WSAData = platform.Struct('struct WSAData',
- [('wVersion', rffi.USHORT),
- ('wHighVersion', rffi.USHORT),
- ('szDescription', rffi.CFixedArray(lltype.Char, 1)), # (WSADESCRIPTION_LEN+1)
- ('szSystemStatus', rffi.CFixedArray(lltype.Char, 1)), # (WSASYS_STATUS_LEN+1)
- ('iMaxSockets', rffi.USHORT),
- ('iMaxUdpDg', rffi.USHORT),
- ('lpVendorInfo', CCHARP)])
- CConfig.tcp_keepalive = platform.Struct(
- 'struct tcp_keepalive',
- [('onoff', rffi.ULONG),
- ('keepalivetime', rffi.ULONG),
- ('keepaliveinterval', rffi.ULONG)])
- class cConfig:
- pass
- cConfig.__dict__.update(platform.configure(CConfig))
- sockaddr_ptr.TO.become(cConfig.sockaddr)
- addrinfo_ptr.TO.become(cConfig.addrinfo)
- # fill in missing constants with reasonable defaults
- cConfig.NI_MAXHOST = cConfig.NI_MAXHOST or 1025
- cConfig.NI_MAXSERV = cConfig.NI_MAXSERV or 32
- cConfig.INET_ADDRSTRLEN = cConfig.INET_ADDRSTRLEN or 16
- for name in constant_names:
- value = getattr(cConfig, name)
- if value is not None:
- constants[name] = value
- for name, default in constants_w_defaults:
- value = getattr(cConfig, name)
- if value is not None:
- constants[name] = value
- else:
- constants[name] = default
- if not _HAS_AF_PACKET and 'AF_PACKET' in constants:
- del constants['AF_PACKET']
- constants['has_ipv6'] = True # This is a configuration option in CPython
- for name, value in constants.items():
- if isinstance(value, long):
- if r_uint(value) == value:
- constants[name] = intmask(value)
- locals().update(constants)
- O_RDONLY = cConfig.O_RDONLY
- O_WRONLY = cConfig.O_WRONLY
- O_RDWR = cConfig.O_RDWR
- O_NONBLOCK = cConfig.O_NONBLOCK
- F_GETFL = cConfig.F_GETFL
- F_SETFL = cConfig.F_SETFL
- FIONBIO = cConfig.FIONBIO
- INET_ADDRSTRLEN = cConfig.INET_ADDRSTRLEN
- INET6_ADDRSTRLEN = cConfig.INET6_ADDRSTRLEN
- EINTR = cConfig.EINTR or cConfig.WSAEINTR
- EINPROGRESS = cConfig.EINPROGRESS or cConfig.WSAEINPROGRESS
- EWOULDBLOCK = cConfig.EWOULDBLOCK or cConfig.WSAEWOULDBLOCK
- EAFNOSUPPORT = cConfig.EAFNOSUPPORT or cConfig.WSAEAFNOSUPPORT
- EISCONN = cConfig.EISCONN or cConfig.WSAEISCONN
- linux = cConfig.linux
- WIN32 = cConfig.WIN32
- assert WIN32 == _WIN32
- if _MSVC:
- def invalid_socket(fd):
- return fd == INVALID_SOCKET
- INVALID_SOCKET = r_uint(cConfig.INVALID_SOCKET)
- else:
- def invalid_socket(fd):
- return fd < 0
- INVALID_SOCKET = -1
- uint16_t = cConfig.uint16_t
- uint32_t = cConfig.uint32_t
- size_t = cConfig.size_t
- ssize_t = cConfig.ssize_t
- socklen_t = cConfig.socklen_t
- sockaddr = cConfig.sockaddr
- #sockaddr_size = sizeof(sockaddr)
- sockaddr_in = cConfig.sockaddr_in
- sockaddr_in6 = cConfig.sockaddr_in6
- sockaddr_un = cConfig.sockaddr_un
- if cConfig.sockaddr_nl is not None:
- sockaddr_nl = cConfig.sockaddr_nl
- in_addr = cConfig.in_addr
- #in_addr_size = sizeof(in_addr)
- in6_addr = cConfig.in6_addr
- addrinfo = cConfig.addrinfo
- if _POSIX:
- nfds_t = cConfig.nfds_t
- pollfd = cConfig.pollfd
- if _HAS_AF_PACKET:
- sockaddr_ll = cConfig.sockaddr_ll
- ifreq = cConfig.ifreq
- if WIN32:
- WSAEVENT = cConfig.WSAEVENT
- WSANETWORKEVENTS = cConfig.WSANETWORKEVENTS
- SAVE_ERR = rffi.RFFI_SAVE_WSALASTERROR
- else:
- SAVE_ERR = rffi.RFFI_SAVE_ERRNO
- timeval = cConfig.timeval
- def external(name, args, result, **kwds):
- return rffi.llexternal(name, args, result, compilation_info=eci,
- calling_conv=calling_conv, **kwds)
- def external_c(name, args, result, **kwargs):
- return rffi.llexternal(name, args, result, compilation_info=eci,
- calling_conv='c', **kwargs)
- if _POSIX:
- dup = external('dup', [socketfd_type], socketfd_type, save_err=SAVE_ERR)
- gai_strerror = external('gai_strerror', [rffi.INT], CCHARP)
- #h_errno = c_int.in_dll(socketdll, 'h_errno')
- #
- #hstrerror = socketdll.hstrerror
- #hstrerror.argtypes = [c_int]
- #hstrerror.restype = c_char_p
- socket = external('socket', [rffi.INT, rffi.INT, rffi.INT], socketfd_type,
- save_err=SAVE_ERR)
- if WIN32:
- socketclosename = 'closesocket'
- else:
- socketclosename = 'close'
- socketclose = external(socketclosename, [socketfd_type], rffi.INT,
- releasegil=False, save_err=SAVE_ERR)
- socketclose_no_errno = external(socketclosename, [socketfd_type], rffi.INT,
- releasegil=False)
- socketconnect = external('connect', [socketfd_type, sockaddr_ptr, socklen_t],
- rffi.INT, save_err=SAVE_ERR)
- getaddrinfo = external('getaddrinfo', [CCHARP, CCHARP,
- addrinfo_ptr,
- lltype.Ptr(rffi.CArray(addrinfo_ptr))], rffi.INT)
- freeaddrinfo = external('freeaddrinfo', [addrinfo_ptr], lltype.Void)
- getnameinfo = external('getnameinfo', [sockaddr_ptr, socklen_t, CCHARP,
- size_t, CCHARP, size_t, rffi.INT], rffi.INT)
- if sys.platform.startswith("openbsd") or sys.platform.startswith("darwin"):
- htonl = external('htonl', [rffi.UINT], rffi.UINT, releasegil=False, macro=True)
- htons = external('htons', [rffi.USHORT], rffi.USHORT, releasegil=False, macro=True)
- ntohl = external('ntohl', [rffi.UINT], rffi.UINT, releasegil=False, macro=True)
- ntohs = external('ntohs', [rffi.USHORT], rffi.USHORT, releasegil=False, macro=True)
- else:
- htonl = external('htonl', [rffi.UINT], rffi.UINT, releasegil=False)
- htons = external('htons', [rffi.USHORT], rffi.USHORT, releasegil=False)
- ntohl = external('ntohl', [rffi.UINT], rffi.UINT, releasegil=False)
- ntohs = external('ntohs', [rffi.USHORT], rffi.USHORT, releasegil=False)
- if _POSIX:
- inet_aton = external('inet_aton', [CCHARP, lltype.Ptr(in_addr)],
- rffi.INT)
- inet_ntoa = external('inet_ntoa', [in_addr], rffi.CCHARP)
- if _POSIX:
- inet_pton = external('inet_pton', [rffi.INT, rffi.CCHARP,
- rffi.VOIDP], rffi.INT,
- save_err=SAVE_ERR)
- inet_ntop = external('inet_ntop', [rffi.INT, rffi.VOIDP, CCHARP,
- socklen_t], CCHARP,
- save_err=SAVE_ERR)
- inet_addr = external('inet_addr', [rffi.CCHARP], rffi.UINT)
- socklen_t_ptr = lltype.Ptr(rffi.CFixedArray(socklen_t, 1))
- socketaccept = external('accept', [socketfd_type, sockaddr_ptr,
- socklen_t_ptr], socketfd_type,
- save_err=SAVE_ERR)
- socketbind = external('bind', [socketfd_type, sockaddr_ptr, socklen_t],
- rffi.INT, save_err=SAVE_ERR)
- socketlisten = external('listen', [socketfd_type, rffi.INT], rffi.INT,
- save_err=SAVE_ERR)
- socketgetpeername = external('getpeername', [socketfd_type,
- sockaddr_ptr, socklen_t_ptr], rffi.INT,
- save_err=SAVE_ERR)
- socketgetsockname = external('getsockname', [socketfd_type,
- sockaddr_ptr, socklen_t_ptr], rffi.INT,
- save_err=SAVE_ERR)
- socketgetsockopt = external('getsockopt', [socketfd_type, rffi.INT,
- rffi.INT, rffi.VOIDP, socklen_t_ptr], rffi.INT,
- save_err=SAVE_ERR)
- socketsetsockopt = external('setsockopt', [socketfd_type, rffi.INT,
- rffi.INT, rffi.VOIDP, socklen_t], rffi.INT,
- save_err=SAVE_ERR)
- socketrecv = external('recv', [socketfd_type, rffi.VOIDP, rffi.INT,
- rffi.INT], ssize_t, save_err=SAVE_ERR)
- recvfrom = external('recvfrom', [socketfd_type, rffi.VOIDP, size_t,
- rffi.INT, sockaddr_ptr, socklen_t_ptr], rffi.INT,
- save_err=SAVE_ERR)
- send = external('send', [socketfd_type, rffi.CCHARP, size_t, rffi.INT],
- ssize_t, save_err=SAVE_ERR)
- sendto = external('sendto', [socketfd_type, rffi.VOIDP, size_t, rffi.INT,
- sockaddr_ptr, socklen_t], ssize_t,
- save_err=SAVE_ERR)
- socketshutdown = external('shutdown', [socketfd_type, rffi.INT], rffi.INT,
- save_err=SAVE_ERR)
- gethostname = external('gethostname', [rffi.CCHARP, rffi.INT], rffi.INT,
- save_err=SAVE_ERR)
- gethostbyname = external('gethostbyname', [rffi.CCHARP],
- lltype.Ptr(cConfig.hostent))
- gethostbyaddr = external('gethostbyaddr', [rffi.VOIDP, rffi.INT, rffi.INT], lltype.Ptr(cConfig.hostent))
- getservbyname = external('getservbyname', [rffi.CCHARP, rffi.CCHARP], lltype.Ptr(cConfig.servent))
- getservbyport = external('getservbyport', [rffi.INT, rffi.CCHARP], lltype.Ptr(cConfig.servent))
- getprotobyname = external('getprotobyname', [rffi.CCHARP], lltype.Ptr(cConfig.protoent))
- if _POSIX:
- fcntl = external('fcntl', [socketfd_type, rffi.INT, rffi.INT], rffi.INT)
- socketpair_t = rffi.CArray(socketfd_type)
- socketpair = external('socketpair', [rffi.INT, rffi.INT, rffi.INT,
- lltype.Ptr(socketpair_t)], rffi.INT,
- save_err=SAVE_ERR)
- if _HAS_AF_PACKET:
- ioctl = external('ioctl', [socketfd_type, rffi.INT, lltype.Ptr(ifreq)],
- rffi.INT)
- if _WIN32:
- ioctlsocket = external('ioctlsocket',
- [socketfd_type, rffi.LONG, rffi.ULONGP],
- rffi.INT)
- select = external('select',
- [rffi.INT, fd_set, fd_set,
- fd_set, lltype.Ptr(timeval)],
- rffi.INT,
- save_err=SAVE_ERR)
- FD_CLR = external_c('FD_CLR', [rffi.INT, fd_set], lltype.Void, macro=True)
- FD_ISSET = external_c('FD_ISSET', [rffi.INT, fd_set], rffi.INT, macro=True)
- FD_SET = external_c('FD_SET', [rffi.INT, fd_set], lltype.Void, macro=True)
- FD_ZERO = external_c('FD_ZERO', [fd_set], lltype.Void, macro=True)
- if _POSIX:
- pollfdarray = rffi.CArray(pollfd)
- poll = external('poll', [lltype.Ptr(pollfdarray), nfds_t, rffi.INT],
- rffi.INT, save_err=SAVE_ERR)
- # workaround for Mac OS/X on which poll() seems to behave a bit strangely
- # (see test_recv_send_timeout in pypy.module._socket.test.test_sock_app)
- # https://issues.apache.org/bugzilla/show_bug.cgi?id=34332
- poll_may_be_broken = _MACOSX
- elif WIN32:
- from rpython.rlib import rwin32
- #
- # The following is for rpython.rlib.rpoll
- #
- WSAEVENT_ARRAY = rffi.CArray(WSAEVENT)
- WSACreateEvent = external('WSACreateEvent', [], WSAEVENT)
- WSACloseEvent = external('WSACloseEvent', [WSAEVENT], rffi.INT)
- WSAEventSelect = external('WSAEventSelect',
- [socketfd_type, WSAEVENT, rffi.LONG],
- rffi.INT)
- WSAWaitForMultipleEvents = external('WSAWaitForMultipleEvents',
- [rffi.LONG, lltype.Ptr(WSAEVENT_ARRAY),
- rffi.INT, rffi.LONG, rffi.INT],
- rffi.ULONG)
- WSAEnumNetworkEvents = external('WSAEnumNetworkEvents',
- [socketfd_type, WSAEVENT,
- lltype.Ptr(WSANETWORKEVENTS)],
- rffi.INT)
- WSAIoctl = external('WSAIoctl',
- [socketfd_type, rwin32.DWORD,
- rffi.VOIDP, rwin32.DWORD,
- rffi.VOIDP, rwin32.DWORD,
- rwin32.LPDWORD, rffi.VOIDP, rffi.VOIDP],
- rffi.INT, save_err=SAVE_ERR)
- tcp_keepalive = cConfig.tcp_keepalive
- WSAPROTOCOL_INFO = cConfig.WSAPROTOCOL_INFO
- FROM_PROTOCOL_INFO = cConfig.FROM_PROTOCOL_INFO
- WSADuplicateSocket = external('WSADuplicateSocketA',
- [socketfd_type, rwin32.DWORD,
- lltype.Ptr(WSAPROTOCOL_INFO)],
- rffi.INT, save_err=SAVE_ERR)
- WSASocket = external('WSASocketA',
- [rffi.INT, rffi.INT, rffi.INT,
- lltype.Ptr(WSAPROTOCOL_INFO),
- rwin32.DWORD, rwin32.DWORD],
- socketfd_type, save_err=SAVE_ERR)
- if WIN32:
- WSAData = cConfig.WSAData
- WSAStartup = external('WSAStartup', [rwin32.WORD, lltype.Ptr(WSAData)],
- rffi.INT)
- _WSAGetLastError = external('WSAGetLastError', [], rwin32.DWORD,
- _nowrapper=True, sandboxsafe=True)
- geterrno = rwin32.GetLastError_saved
- # In tests, the first call to GetLastError is always wrong, because error
- # is hidden by operations in ll2ctypes. Call it now.
- _WSAGetLastError()
- def socket_strerror_str(errno):
- return rwin32.FormatError(errno)
- def gai_strerror_str(errno):
- return rwin32.FormatError(errno)
- # WinSock does not use a bitmask in select, and uses
- # socket handles greater than FD_SETSIZE
- MAX_FD_SIZE = None
- else:
- from rpython.rlib.rposix import get_saved_errno as geterrno
- socket_strerror_str = os.strerror
- def gai_strerror_str(errno):
- return rffi.charp2str(gai_strerror(errno))
- MAX_FD_SIZE = FD_SETSIZE