ϪfAdZddlZddlmZddlmZddlmZmZddl m Z m Z ddl m Z mZddlmZmZmZmZdd lmZdd lmZmZdd lmZdd lmZdd lmZmZddl m!Z!m"Z"ddl#m$Z$dZ%e%Z&dZ'GddeZ(GddZ)Gddee)e(Z*Gddee)e(Z+e,j[e*j]e,j[e+j]y)zU Tests for implementations of L{IReactorUDP} and the UDP parts of L{IReactorSocket}. N) implementer) verifyObject)defererror) IPv4Address IPv6Address)Deferred maybeDeferred)IListeningPortILoggingContextIReactorSocket IReactorUDP)DatagramProtocol)LogObserverMixin findFreePort)ReactorBuilder)context) ILogContexterr) GoodClientServer)SkipTestcd}d} tjtj}|jdd}|r|j |S#t$rYwxYw)z4Returns True if the system can bind an IPv6 address.NF)::1rT)socketAF_INET6bindOSErrorclose)sockhas_ipv6s @/usr/lib/python3/dist-packages/twisted/internet/test/test_udp.py _has_ipv6r#!s[ DH }}V__- *  O    s6A AAc tsd|_|S)Nz.Does not work on systems without IPv6 support.)HAS_IPV6skip)fs r"skipWithoutIPv6r(5s A Hc"eZdZdZdZdZdZy)DatagramTransportTestsMixinzP Mixin defining tests which apply to any port/datagram based transport. c&|j}|j}ttGddt}|}|j ||}d|j jfz}|j|f|ddy)zu When a port starts, a message including a description of the associated protocol is logged. ceZdZdZy)QDatagramTransportTestsMixin.test_startedListeningLogMessage..SomeProtocolcy)NzCrazy Protocolselfs r" logPrefixz[DatagramTransportTestsMixin.test_startedListeningLogMessage..SomeProtocol.logPrefixJs'r)N)__name__ __module__ __qualname__r3r0r)r" SomeProtocolr.Hs (r)r7zCrazy Protocol starting on %drmessageN) observe buildReactorrr rgetListeningPortgetHostport assertEqual)r2loggedMessagesreactorr7protocolpexpectedMessages r"test_startedListeningLogMessagez;DatagramTransportTestsMixin.test_startedListeningLogMessage@s ##% _ % (+ ( & ( >  ! !'8 49QYY[=M=My-IJr)cJ|j|j|jtdj j d}fdfd}j ||j|j|fddy)z When a connection is lost a message is logged containing an address identifying the port and the fact that it was closed. z (UDP Port z Closed)c&jyNstopignoredr@s r" stopReactorzNDatagramTransportTestsMixin.test_connectionLostLogMessage..stopReactor]s LLNr)cXdd=tjjyrG)r stopListening addCallback)r?rBrLsr"doStopListeningzRDatagramTransportTestsMixin.test_connectionLostLogMessage..doStopListening`s"q! !// * 6 6{ Cr)rr8N) r9r:r;rr<r=callWhenRunning runReactorr>)r2rCrPr?rBr@rLs @@@@r"test_connectionLostLogMessagez9DatagramTransportTestsMixin.test_connectionLostLogMessageSs ##%  ! !'+;+= >&qyy{'7'7&8A  D 0   /+^A->y-IJr)c>Gfddt}|j|}|j||j|j |j |j |j |j|jy)z L{DatagramProtocol.stopProtocol} is called asynchronously (ie, not re-entrantly) when C{stopListening} is used to stop the datagram transport. c.eZdZdZdZdZdZdZfdZy)VDatagramTransportTestsMixin.test_stopProtocolScheduling..DisconnectingProtocolFcbd|_d|_|jjd|_y)NTF)startedinStartProtocol transportrNr1s r" startProtocolzdDatagramTransportTestsMixin.test_stopProtocolScheduling..DisconnectingProtocol.startProtocolvs)# '+$,,.',$r)cVd|_|j|_jy)NT)stoppedrYstoppedInStartrIr2r@s r" stopProtocolzcDatagramTransportTestsMixin.test_stopProtocolScheduling..DisconnectingProtocol.stopProtocol|s!# &*&:&:# r)N) r4r5r6rXr]rYr^r[r`)r@sr"DisconnectingProtocolrVps!GG#O"N -  r)raN) rr:r;rR assertTruerXr] assertFalser^)r2rarAr@s @r"test_stopProtocolSchedulingz7DatagramTransportTestsMixin.test_stopProtocolSchedulingis| $4 "##%(* gx0   (() (() 001r)N)r4r5r6__doc__rDrSrdr0r)r"r+r+;sK&K,2r)r+ceZdZdZdZdZedZdZdZ dZ dZ d Z ed Z ed Zd Zed ZedZdZdZy)UDPPortTestsMixinzY Tests for L{IReactorUDP.listenUDP} and L{IReactorSocket.adoptDatagramPort}. c|j}|j|t}|jt t |y)zY L{IReactorUDP.listenUDP} returns an object providing L{IListeningPort}. N)r:r;rrbrr r2r@r=s r"test_interfacez UDPPortTestsMixin.test_interfaces;##%$$W.>.@A  ^T:;r)cttj\}}|j}|j |t ||}|j |jtd||y)z L{IListeningPort.getHost} returns an L{IPv4Address} giving a dotted-quad of the IPv4 address the port is listening on as well as the port number. )type)r= interfaceUDPN) rr SOCK_DGRAMr:r;rr>r<r)r2host portNumberr@r=s r" test_getHostzUDPPortTestsMixin.test_getHostsj (V->->?j##%$$ %'jD%  UD*)MNr)c|j}|j|td}|j}|j |j d|j |ty)zr L{IListeningPort.getHost} returns an L{IPv6Address} when listening on an IPv6 interface. rrmN)r:r;rr<r>rpassertIsInstancer)r2r@r=addrs r"test_getHostIPv6z"UDPPortTestsMixin.test_getHostIPv6s\ ##%$$W.>.@E$R||~ E* dK0r)c|j}|jtj|jt ddy)z An L{InvalidAddressError} is raised when trying to listen on an address that isn't a valid IPv4 or IPv6 address. rz example.comrtN)r: assertRaisesrInvalidAddressError listenUDPrr_s r"test_invalidInterfacez'UDPPortTestsMixin.test_invalidInterfacesC ##%   % %      #  r)cGddt}j|d}|j}j|}|j }fd}|j ||j t|j fd|jdd|jfjy) z Datagram transports implement L{ILoggingContext.logPrefix} to return a message reflecting the protocol they are running. ceZdZdZdZdZy)IUDPPortTestsMixin.test_logPrefix..CustomLogPrefixDatagramProtocolc0||_t|_yrG)_prefixr system)r2prefixs r"__init__zRUDPPortTestsMixin.test_logPrefix..CustomLogPrefixDatagramProtocol.__init__s% &j r)c|jSrG)rr1s r"r3zSUDPPortTestsMixin.test_logPrefix..CustomLogPrefixDatagramProtocol.logPrefixs ||#r)c|j?|j}d|_|jtjtdyy)Nr)rcallbackrgetr)r2bytesrvrs r"datagramReceivedzZUDPPortTestsMixin.test_logPrefix..CustomLogPrefixDatagramProtocol.datagramReceiveds;;;*![[F"&DKOOGKK $)rr2s r" gotSystemz3UDPPortTestsMixin.test_logPrefix..gotSystems   5v >r)c$jSrGrHrJs r"z2UDPPortTestsMixin.test_logPrefix..s gllnr)s some bytes 127.0.0.1N) rr:rr;r<rO addErrbackrwriter=rR)r2rrAdr=addressrr@s` @r"test_logPrefixz UDPPortTestsMixin.test_logPrefixs H.> H##%23EF OO$$Wh7,,. ? i  S 45 =; "=>  r)cGddt}j|}|j}j|}|j }dfd}|j ||j t|j fd|jd|jfjy)zH Write a sequence of L{bytes} to a L{DatagramProtocol}. ceZdZdZdZy)DUDPPortTestsMixin.test_writeSequence..SimpleDatagramProtocolc"t|_yrG)r rr1s r"rzMUDPPortTestsMixin.test_writeSequence..SimpleDatagramProtocol.__init__s %Z r)c:|jj|yrG)rr)r2datarvs r"rzUUDPPortTestsMixin.test_writeSequence..SimpleDatagramProtocol.datagramReceiveds ##D)r)N)r4r5r6rrr0r)r"SimpleDatagramProtocolrs  ( *r)r)ssomesbytesstoswritecHjdj|y)Nr))r>join)r dataToWriter2s r"gotDataz5UDPPortTestsMixin.test_writeSequence..gotDatas   SXXk2D 9r)c$jSrGrHrJs r"rz6UDPPortTestsMixin.test_writeSequence..s ',,.r)rN) rr:rr;r<rOrr writeSequencer=rR) r2rrArr=rrrr@s ` @@r"test_writeSequencez$UDPPortTestsMixin.test_writeSequences  *%5 *##%)+$$Wh7,,.:  : '"89 ;gll(CD  r)c|j}|j|t}|jt |j j t |y)zQ C{str()} on the listening port object includes the port number. N)r:r;rassertInstrr<r=ris r"test_strzUDPPortTestsMixin.test_strsK##%$$W.>.@A c$,,.--.D :r)c|j}|j|t}|jt |j j t|y)zR C{repr()} on the listening port object includes the port number. N)r:r;rrreprr<r=rris r" test_reprzUDPPortTestsMixin.test_reprsK##%$$W.>.@A d4<<>../T;r)c |j t tjx} _|j dt tjx}_|j djj} fd} fd}tj||g}|j||j||jt|j  jd}|j|d|j |j"ffy)zS Writing to an IPv6 UDP socket on the loopback interface succeeds. rrtcjjddjjjft j x}_|S) Send a datagram from the client once it's started. @param ignored: a list of C{[None, None]}, which is ignored @returns: a deferred which fires when the server has received a datagram. spamr)rZrr<r=rr packetReceivedrKserverReceivedclientservers r"cbClientStartedzDUDPPortTestsMixin.test_writeToIPv6Interface..cbClientStartedsO    " "7UF4D4D4L4L4N4S4S,T U5:^^5E ENV2! !r)c&jyz Stop the reactor after a datagram is received. @param ignored: L{None}, which is ignored @returns: L{None} NrHrJs r"cbServerReceivedzEUDPPortTestsMixin.test_writeToIPv6Interface..cbServerReceived+s LLNr)rrNr:rrr startedDeferredr;rrZr< gatherResultsrOrrrRpacketsr>rpr= r2 serverStarted clientStartedcAddrrrrpacketrr@rs @@@r"test_writeToIPv6Interfacez+UDPPortTestsMixin.test_writeToIPv6Interfaces  ##%161AA . gv?161AA . gv?  ((* "     > ? o& &' S  " 'EJJ +C!DEr)c |j t tjx} _|j dt tjx}_|j djj} fd} fd}tj||g}|j||j||jt|j  jd}|j|d|j |j"ffy)z An IPv6 address can be passed as the C{interface} argument to L{listenUDP}. The resulting Port accepts IPv6 datagrams. rrtcjjdjjjjj dt j x}_|S)rrr)rZconnectr<r=rrr rrs r"rzMUDPPortTestsMixin.test_connectedWriteToIPv6Interface..cbClientStartedMs^    $ $UF,<,<,D,D,F,K,K L    " "7 +5:^^5E ENV2! !r)c&jyrrHrJs r"rzNUDPPortTestsMixin.test_connectedWriteToIPv6Interface..cbServerReceived[s LLNr)rrNrrs @@@r""test_connectedWriteToIPv6Interfacez4UDPPortTestsMixin.test_connectedWriteToIPv6Interface=s  ##%161AA . gv?161AA . gv?  ((* "     > ? o& &' S  " 'EJJ +C!DEr)c|j}|j|t}|jtj |j ddy)zn Writing to a hostname instead of an IP address will raise an L{InvalidAddressError}. spam)example.invalidNr:r;rryrrzrris r"/test_writingToHostnameRaisesInvalidAddressErrorzAUDPPortTestsMixin.test_writingToHostnameRaisesInvalidAddressErrornsJ ##%$$W.>.@A   % %tzz6;Q r)c|j}|j|td}|jtj |j ddy)l Writing to an IPv6 address on an IPv4 socket will raise an L{InvalidAddressError}. rrtr)rrNrris r"1test_writingToIPv6OnIPv4RaisesInvalidAddressErrorzCUDPPortTestsMixin.test_writingToIPv6OnIPv4RaisesInvalidAddressErrorysK ##%$$W.>.@K$X %33TZZTr)c|j}|j|td}|jtj |j ddy)rrrtr)rrNrris r"1test_writingToIPv4OnIPv6RaisesInvalidAddressErrorzCUDPPortTestsMixin.test_writingToIPv4OnIPv6RaisesInvalidAddressErrorsO ##%$$W.>.@E$R   % %tzz6;K r)c|j}|j|t}|jtj |j ddy)zq Connecting to a hostname instead of an IP address will raise an L{InvalidAddressError}. rrN)r:r;rryrrzrris r"2test_connectingToHostnameRaisesInvalidAddressErrorzDUDPPortTestsMixin.test_connectingToHostnameRaisesInvalidAddressErrorsH ##%$$W.>.@A %33T\\CTVWXr)c|j}|j|t}|jd|j |j y)zk L{IListeningPort.setBroadcastAllowed} sets broadcast to be allowed on the socket. TN)r:r;rsetBroadcastAllowedrbgetBroadcastAllowedris r"test_allowBroadcastz%UDPPortTestsMixin.test_allowBroadcastsK ##%$$W.>.@A   & 0023r)N)r4r5r6rerjrrr(rwr|rrrrrrrrrrrr0r)r"rgrgs < O 1 1  "!H!8;<*F*FX.F.F`  UU    Y4r)rgc eZdZdZefZ ddZy)UDPServerTestsBuilderzM Run L{UDPPortTestsMixin} tests using newly created UDP sockets. c,|j||||S)aB Get a UDP port from a reactor. @param reactor: A reactor used to build the returned L{IListeningPort} provider. @type reactor: L{twisted.internet.interfaces.IReactorUDP} @see: L{twisted.internet.IReactorUDP.listenUDP} for other argument and return types. )rm maxPacketSize)r{)r2r@rAr=rmrs r"r;z&UDPServerTestsBuilder.getListeningPorts%  (i}!  r)Nri )r4r5r6rerrequiredInterfacesr;r0r)r"rrs &FJ r)rc eZdZdZefZ ddZy)UDPFDServerTestsBuilderzC Run L{UDPPortTestsMixin} tests using adopted UDP sockets. c<tj|rd|vr-tj}tj||dd}ntj }||f}tj|tj }|j||jd |j|j|j|||j|jStd#|j|jwxYw)a Get a UDP port from a reactor, wrapping an already-initialized file descriptor. @param reactor: A reactor used to build the returned L{IListeningPort} provider. @type reactor: L{twisted.internet.interfaces.IReactorSocket} @param port: A port number to which the adopted socket will be bound. @type port: C{int} @param interface: The local IPv4 or IPv6 address to which the adopted socket will be bound. defaults to '', ie all IPv4 addresses. @type interface: C{str} @see: L{twisted.internet.IReactorSocket.adoptDatagramPort} for other argument and return types. :rFz'Reactor does not provide IReactorSocket)r providedByrr getaddrinfoAF_INETror setblockingadoptDatagramPortfilenofamilyrr) r2r@rAr=rmrdomainrportSocks r"r;z(UDPFDServerTestsBuilder.getListeningPorts.  $ $W -i ,,Y=a@C$d+}}VV->->?H MM' "   ' !00OO%x- ! DE E ! s "+C99"DNr)r4r5r6rer rr;r0r)r"rrs)*FJ-Fr)r)/rerzope.interfacerzope.interface.verifyrtwisted.internetrrtwisted.internet.addressrrtwisted.internet.deferr r twisted.internet.interfacesr r r rtwisted.internet.protocolr&twisted.internet.test.connectionmixinsrr#twisted.internet.test.reactormixinsrtwisted.pythonrtwisted.python.logrrtwisted.test.test_udprrtwisted.trial.unittestrr#r%r(r+rgrrglobalsupdatemakeTestCaseClassesr0r)r"rs &.)=: 7Q>"/4+" ; M2"2M2`U4U4p %'B 86F%'B6Fr &::<= (<<>?r)