Ë
    ojÕ1  ã                   ó¤  — d Z ddlZddlZddlZddlZddlZddlZddlmZ ddl	m
Z
 ddlmZmZmZ ddlmZmZ ddlmZ ddlmZmZmZmZmZ dd	lmZmZ dd
lmZ ddlm Z  ddl!m"Z" ddl#m$Z$m%Z% g d¢Z&dZ' ejP                  «       dk(  s@ ejP                  «       jS                  d«      s  ejP                  «       jS                  d«      rdZ*dZ+ndZ*dZ+dZ, G d„ de«      Z- eej\                  «       G d„ de%e$«      «       Z/ G d„ d edd«      «      Z0 G d„ d e«      Z1 G d!„ d"«      Z2 eejf                  «       G d#„ d$ejh                  «      «       Z5y)%zc
Support for Linux ethernet and IP tunnel devices.

@see: U{https://en.wikipedia.org/wiki/TUN/TAP}
é    N)Ú
namedtuple)ÚTuple)Ú	AttributeÚ	InterfaceÚimplementer)ÚFlagConstantÚFlags)ÚVersion)ÚabstractÚdeferÚerrorÚ
interfacesÚtask)ÚethernetÚraw)Úlog)Ú
deprecated)ÚfullyQualifiedName)ÚFancyEqMixinÚFancyStrMixin)ÚTunnelFlagsÚTunnelAddressÚ
TuntapPorté   ÚpariscÚppcÚsparcl   ÊT  iÒT@iÊT@l   ÒT  s   /dev/net/tunc                   óÐ   — e Zd ZdZ ed«      Z ed«      Z ed«      Z ed«      Z ed«      Z	 ed«      Z
 ed«      Z ed	«      Z ed
«      Z ed«      Z ed«      Z ed«      Zy)r   a~  
    L{TunnelFlags} defines more flags which are used to configure the behavior
    of a tunnel device.

    @cvar IFF_TUN: This indicates a I{tun}-type device.  This type of tunnel
        carries IP datagrams.  This flag is mutually exclusive with C{IFF_TAP}.

    @cvar IFF_TAP: This indicates a I{tap}-type device.  This type of tunnel
        carries ethernet frames.  This flag is mutually exclusive with C{IFF_TUN}.

    @cvar IFF_NO_PI: This indicates the I{protocol information} header will
        B{not} be included in data read from the tunnel.

    @see: U{https://www.kernel.org/doc/Documentation/networking/tuntap.txt}
    é   é   r   é    é@   é€   é   i   i   é    i @  i €  N)Ú__name__Ú
__module__Ú__qualname__Ú__doc__r   ÚIFF_TUNÚIFF_TAPÚ
TUN_FASYNCÚTUN_NOCHECKSUMÚ	TUN_NO_PIÚTUN_ONE_QUEUEÚTUN_PERSISTÚTUN_VNET_HDRÚ	IFF_NO_PIÚIFF_ONE_QUEUEÚIFF_VNET_HDRÚIFF_TUN_EXCL© ó    ú5/usr/lib/python3/dist-packages/twisted/pair/tuntap.pyr   r   6   s�   „ ññ  ˜6Ó"€GÙ˜6Ó"€Gá˜fÓ%€JÙ! &Ó)€NÙ˜VÓ$€IÙ  Ó(€MÙ˜vÓ&€KÙ Ó'€Lá˜VÓ$€IÙ  Ó(€MÙ Ó'€LÙ Ó'�Lr7   r   c                   ó>   — e Zd ZdZdZdd„ fdfZed„ «       Zd„ Zd„ Z	y	)
r   zU
    A L{TunnelAddress} represents the tunnel to which a L{TuntapPort} is bound.
    )Ú
_typeValueÚnameÚtypec                 ó   — | j                   S ©N)r;   )Úflags    r8   ú<lambda>zTunnelAddress.<lambda>^   s
   € ¨D¯I©I€ r7   r;   c                 ó.   — | j                   j                  S )z�
        Return the integer value of the C{type} attribute.  Used to produce
        correct results in the equality implementation.
        )r<   Úvalue©Úselfs    r8   r:   zTunnelAddress._typeValue`   s   € ð �y‰y�‰Ðr7   c                 ó    — || _         || _        y)zÛ
        @param type: Either L{TunnelFlags.IFF_TUN} or L{TunnelFlags.IFF_TAP},
            representing the type of this tunnel.

        @param name: The system name of the tunnel.
        @type name: L{bytes}
        N)r<   r;   )rD   r<   r;   s      r8   Ú__init__zTunnelAddress.__init__i   s   € ð ˆŒ	Øˆ�	r7   c                 ó\   — t        j                  dt        d¬«       d| j                  f|   S )zS
        Deprecated accessor for the tunnel name.  Use attributes instead.
        zUTunnelAddress.__getitem__ is deprecated since Twisted 14.0.0  Use attributes instead.r    )ÚcategoryÚ
stacklevelÚTUNTAP)ÚwarningsÚwarnÚDeprecationWarningr;   )rD   Úindexs     r8   Ú__getitem__zTunnelAddress.__getitem__t   s1   € ô 	�‰ð&ä'Øõ		
ð ˜$Ÿ)™)Ð$ UÑ+Ð+r7   N)
r&   r'   r(   r)   ÚcompareAttributesÚshowAttributesÚpropertyr:   rF   rO   r6   r7   r8   r   r   W   s;   „ ñð /ÐØÑ5Ð6¸Ð?€Nàñó ðò	ó
,r7   r   c                   ó   — e Zd ZdZy)Ú_TunnelDescriptionzÂ
    Describe an existing tunnel.

    @ivar fileno: the file descriptor associated with the tunnel
    @type fileno: L{int}

    @ivar name: the name of the tunnel
    @type name: L{bytes}
    N)r&   r'   r(   r)   r6   r7   r8   rT   rT   �   s   „ òr7   rT   zfileno namec                   ón   — e Zd ZdZ ed«      Z ed«      Z ed«      Zdd„Zdd„Z	d„ Z
d	„ Zd
„ Zd„ Zd„ Zy)Ú_IInputOutputSystemz–
    An interface for performing some basic kinds of I/O (particularly that I/O
    which might be useful for L{twisted.pair.tuntap}-using code).
    z@see: L{os.O_RDWR}z@see: L{os.O_NONBLOCK}z@see: L{os.O_CLOEXEC}c                  ó   — y)z"
        @see: L{os.open}
        Nr6   )Úfilenamer?   Úmodes      r8   Úopenz_IInputOutputSystem.open—   ó   � r7   Nc                  ó   — y)z&
        @see: L{fcntl.ioctl}
        Nr6   )ÚfdÚoptÚargÚmutate_flags       r8   Úioctlz_IInputOutputSystem.ioctlœ   r[   r7   c                  ó   — y)z"
        @see: L{os.read}
        Nr6   )r]   Úlimits     r8   Úreadz_IInputOutputSystem.read¡   r[   r7   c                  ó   — y)z#
        @see: L{os.write}
        Nr6   )r]   Údatas     r8   Úwritez_IInputOutputSystem.write¦   r[   r7   c                  ó   — y)z#
        @see: L{os.close}
        Nr6   )r]   s    r8   Úclosez_IInputOutputSystem.close«   r[   r7   c                  ó   — y)aŒ  
        Send a datagram to a certain address.

        @param datagram: The payload of a UDP datagram to send.
        @type datagram: L{bytes}

        @param address: The destination to which to send the datagram.
        @type address: L{tuple} of (L{bytes}, L{int})

        @return: The local address from which the datagram was sent.
        @rtype: L{tuple} of (L{bytes}, L{int})
        Nr6   )ÚdatagramÚaddresss     r8   ÚsendUDPz_IInputOutputSystem.sendUDP°   r[   r7   c                  ó   — y)af  
        Return a socket which can be used to receive datagrams sent to the
        given address.

        @param fileno: A file descriptor representing a tunnel device which the
            datagram was either sent via or will be received via.
        @type fileno: L{int}

        @param host: The IPv4 address at which the datagram will be received.
        @type host: L{bytes}

        @param port: The UDP port number at which the datagram will be
            received.
        @type port: L{int}

        @return: A L{socket.socket} which can be used to receive the specified
            datagram.
        Nr6   )ÚfilenoÚhostÚports      r8   Ú
receiveUDPz_IInputOutputSystem.receiveUDP¾   r[   r7   )iÿ  )NN)r&   r'   r(   r)   r   ÚO_RDWRÚ
O_NONBLOCKÚ	O_CLOEXECrZ   ra   rd   rg   ri   rm   rr   r6   r7   r8   rV   rV   �   sM   „ ññ
 Ð+Ó,€FÙÐ3Ó4€JÙÐ1Ó2€Ióó
ò
ò
ò
ò
ór7   rV   c                   ó  — e Zd ZdZ eej                  «      Z eej                  «      Z eej                  «      Z eej                  «      Z	 ee
j                  «      Zej                  Zej                  Z eedd«      Zy)Ú_RealSystemzœ
    An interface to the parts of the operating system which L{TuntapPort}
    relies on.  This is most of an implementation of L{_IInputOutputSystem}.
    ru   i   N)r&   r'   r(   r)   ÚstaticmethodÚosrZ   rd   rg   ri   Úfcntlra   rs   rt   Úgetattrru   r6   r7   r8   rw   rw   Ó   sq   „ ññ
 ˜Ÿ™Ó €DÙ˜Ÿ™Ó €DÙ˜Ÿ™Ó"€EÙ˜Ÿ™Ó"€EÙ˜Ÿ™Ó%€Eà�Y‰Y€FØ—‘€Jñ ˜˜K¨Ó3�Ir7   rw   c                   óœ   — e Zd ZdZdZdd„Zdefd„Zd„ Zd„ Z	d	„ Z
d
„ Zd„ Zd„ Zd„ Zd„ Z e edddd«      e«      d„ «       Zdd„Zd„ Zd„ Zy)r   zH
    A Port that reads and writes packets from/to a TUN/TAP-device.
    i   Nc                 óþ  — t         j                  j                  |«      rd| _         t        j                  | _        n=d| _         t        j                  | _        t        j                  j                  |«      sJ ‚|€
t        «       }|| _
        t        j                  j                  | |«       || _        || _        || _        | j#                  | j                  «      }|› d| j
                  j$                  › d�| _        y )Nr   r   z (ú))r   ÚIEthernetProtocolÚ
providedByr   r+   Ú_moder*   r   ÚIRawPacketProtocolrw   Ú_systemr   ÚFileDescriptorrF   Ú	interfaceÚprotocolÚmaxPacketSizeÚ_getLogPrefixr;   Úlogstr)rD   r…   Úprotor‡   ÚreactorÚsystemÚ	logPrefixs          r8   rF   zTuntapPort.__init__î   sÈ   € Ü×%Ñ%×0Ñ0°Ô7ØˆDŒMÜ$×,Ñ,ˆD�JàˆDŒMÜ$×,Ñ,ˆDŒJÜ×)Ñ)×4Ñ4°UÔ;Ð;Ð;àˆ>Ü “]ˆFØˆŒä×Ñ×(Ñ(¨¨wÔ7Ø"ˆŒØˆŒØ*ˆÔà×&Ñ& t§}¡}Ó5ˆ	Ø"˜ 2 d§j¡j§o¡oÐ%6°aÐ8ˆ�r7   Úreturnc                 óÄ   — t        | j                  j                  «      f}| j                  r|dz   }n|dz   }|| j                  j
                  | j                  fz   }d|z  S )N)Ú )znot z<%s %slistening on %s/%s>)r   r†   Ú	__class__Ú	connectedr�   r;   r…   )rD   Úargss     r8   Ú__repr__zTuntapPort.__repr__  sY   € Ü!3°D·M±M×4KÑ4KÓ!LÐ NˆØ�>Š>Ø˜%‘<‰Dà˜)Ñ#ˆDØ�t—z‘z—‘¨¯©Ð7Ñ7ˆØ*¨TÑ1Ð1r7   c                 óz   — | j                  «        | j                  j                  | «       | j                  «        y)z°
        Create and bind my socket, and begin listening on it.

        This must be called after creating a server to begin listening on the
        specified tunnel.
        N)Ú_bindSocketr†   ÚmakeConnectionÚstartReadingrC   s    r8   ÚstartListeningzTuntapPort.startListening  s.   € ð 	×ÑÔØ�‰×$Ñ$ TÔ*Ø×ÑÕr7   c                 ó¢  — | j                   j                  | j                   j                  z  | j                   j                  z  }t	        j
                  dt        fz  ||j                  «      }| j                   j                  t        |«      }| j                   j                  |t        |«      }t        ||dt         j                  d«      «      S )af  
        Open the named tunnel using the given mode.

        @param name: The name of the tunnel to open.
        @type name: L{bytes}

        @param mode: Flags from L{TunnelFlags} with exactly one of
            L{TunnelFlags.IFF_TUN} or L{TunnelFlags.IFF_TAP} set.

        @return: A L{_TunnelDescription} representing the newly opened tunnel.
        z%dsHNó    )rƒ   rs   ru   rt   ÚstructÚpackÚ	_IFNAMSIZrB   rZ   Ú_TUN_KO_PATHra   Ú
_TUNSETIFFrT   Ústrip)rD   r;   rY   ÚflagsÚconfigro   Úresults          r8   Ú_openTunnelzTuntapPort._openTunnel  s›   € ð —‘×#Ñ# d§l¡l×&<Ñ&<Ñ<¸t¿|¹|×?VÑ?VÑVˆÜ—‘˜V¤y lÑ2°D¸$¿*¹*ÓEˆØ—‘×"Ñ"¤<°Ó7ˆØ—‘×#Ñ# F¬J¸Ó?ˆÜ! &¨&°´)Ð*<×*BÑ*BÀ7Ó*KÓLÐLr7   c                 ót  — t        j                  d| j                  j                  | j                  ¬«       	 | j                  | j                  | j                  t        j                  z  «      \  }}|| _        || _        d| _        y# t        $ r&}t        j                  d| j                  |«      ‚d}~ww xY w)z"
        Open the tunnel.
        z&%(protocol)s starting on %(interface)s)Úformatr†   r…   Nr   )r   Úmsgr†   r‘   r…   r¥   r�   r   r2   ÚOSErrorr   ÚCannotListenErrorÚ_filenor’   )rD   ro   r…   Úes       r8   r–   zTuntapPort._bindSocket)  sž   € ô 	�‰Ø;Ø—]‘]×,Ñ,Ø—n‘nõ	
ð
	CØ $× 0Ñ 0Ø—‘ §
¡
¬[×-BÑ-BÑ Bó!ÑˆF�Ið #ˆŒØˆŒàˆ�øô ò 	CÜ×)Ñ)¨$°·±ÀÓBÐBûð	Cús   ¸:B Â	B7Â!B2Â2B7c                 ó   — | j                   S r>   )r«   rC   s    r8   ro   zTuntapPort.fileno>  s   € Ø�|‰|Ðr7   c                 óH  — d}|| j                   k  rn	 | j                  j                  | j                  | j                  «      }|t        |«      z  }	 | j                  j                  |d¬«       || j                   k  rŒmyy# t
        $ rF}|j                  t        j                  t        j                  t        j                  fv rY d}~y‚ d}~wt        $ r ‚ w xY w# t        $ r< t        | j                  j                  «      }t!        j"                  dd|› d�«       Y Œ±w xY w)z=
        Called when my socket is ready for reading.
        r   N)ÚpartialzUnhandled exception from z.datagramReceived)ÚmaxThroughputrƒ   rd   r«   r‡   r©   ÚerrnoÚEWOULDBLOCKÚEAGAINÚEINTRÚBaseExceptionÚlenr†   ÚdatagramReceivedr   r‘   r   Úerr)rD   rd   rf   r¬   Úclss        r8   ÚdoReadzTuntapPort.doReadA  sü   € ð ˆØ�T×'Ñ'Ò'ðØ—|‘|×(Ñ(¨¯©°t×7IÑ7IÓJ�ð ”C˜“IÑˆDðRØ—‘×.Ñ.¨t¸QÐ.Ô?ð �T×'Ñ'Õ'øô ò Ø—7‘7œu×0Ñ0´%·,±,ÄÇÁÐLÑLÜàûÜ ò Øðûô !ò RÜ(¨¯©×)@Ñ)@ÓA�Ü—‘˜Ð 9¸#¸Ð>OÐPÖQðRús0   “0B ÁC Â	CÂ
;CÃ
CÃCÃAD!Ä D!c                 óÚ   — 	 | j                   j                  | j                  |«      S # t        $ r9}|j                  t        j
                  k(  r| j                  |«      cY d}~S ‚ d}~ww xY w)zÃ
        Write the given data as a single datagram.

        @param datagram: The data that will make up the complete datagram to be
            written.
        @type datagram: L{bytes}
        N)rƒ   rg   r«   r©   r±   r´   )rD   rk   r¬   s      r8   rg   zTuntapPort.writeX  sT   € ð	Ø—<‘<×%Ñ% d§l¡l°HÓ=Ð=øÜò 	Ø�w‰wœ%Ÿ+™+Ò%Ø—z‘z (Ó+Õ+Øûð	ús    ‚%( ¨	A*±-A%ÁA*Á$A%Á%A*c                 óD   — | j                  dj                  |«      «       y)zÒ
        Write a datagram constructed from a L{list} of L{bytes}.

        @param seq: The data that will make up the complete datagram to be
            written.
        @type seq: L{list} of L{bytes}
        r7   N)rg   Újoin)rD   Úseqs     r8   ÚwriteSequencezTuntapPort.writeSequenceg  s   € ð 	�
‰
�3—8‘8˜C“=Õ!r7   c                 ó  — | j                  «        | j                  r| j                  S | j                  rCt	        j
                  | j                  d| j                  «      | _        d| _        | j                  S t        j                  d«      S )zÈ
        Stop accepting connections on this port.

        This will shut down my socket and call self.connectionLost().

        @return: A L{Deferred} that fires when this port has stopped.
        r   TN)
ÚstopReadingÚdisconnectingÚ_stoppedDeferredr’   r   Ú
deferLaterr‹   ÚconnectionLostr   ÚsucceedrC   s    r8   ÚstopListeningzTuntapPort.stopListeningq  ss   € ð 	×ÑÔØ×ÒØ×(Ñ(Ð(Ø�^Š^Ü$(§O¡OØ—‘˜a ×!4Ñ!4ó%ˆDÔ!ð "&ˆDÔØ×(Ñ(Ð(ä—=‘= Ó&Ð&r7   ÚTwistedé   r   c                 ó^   — | j                  «       j                  t        j                  «       y)zN
        Close this tunnel.  Use L{TuntapPort.stopListening} instead.
        N)rÇ   Ú
addErrbackr   r¸   rC   s    r8   ÚloseConnectionzTuntapPort.loseConnection…  s   € ð
 	×ÑÓ×'Ñ'¬¯©Õ0r7   c                 ó"  — t        j                  d| j                  z  «       t        j                  j                  | |«       | j                  j                  «        d| _        | j                  j                  | j                  «       d| _        y)zY
        Cleans up my socket.

        @param reason: Ignored.  Do not use this.
        z(Tuntap %s Closed)r   éÿÿÿÿN)r   r¨   r…   r   r„   rÅ   r†   ÚdoStopr’   rƒ   ri   r«   )rD   Úreasons     r8   rÅ   zTuntapPort.connectionLostŒ  sd   € ô 	�‰Ð$ t§~¡~Ñ5Ô6Ü×Ñ×.Ñ.¨t°VÔ<Ø�‰×ÑÔØˆŒØ�‰×Ñ˜4Ÿ<™<Ô(Øˆ�r7   c                 ó   — | j                   S )zK
        Returns the name of my class, to prefix log entries with.
        )r‰   rC   s    r8   r�   zTuntapPort.logPrefix™  s   € ð �{‰{Ðr7   c                 óB   — t        | j                  | j                  «      S )zÑ
        Get the local address of this L{TuntapPort}.

        @return: A L{TunnelAddress} which describes the tunnel device to which
            this object is bound.
        @rtype: L{TunnelAddress}
        )r   r�   r…   rC   s    r8   ÚgetHostzTuntapPort.getHostŸ  s   € ô ˜TŸZ™Z¨¯©Ó8Ð8r7   )r%   NNr>   )r&   r'   r(   r)   r°   rF   Ústrr”   r™   r¥   r–   ro   rº   rg   r¿   rÇ   r   r
   rÌ   rÅ   r�   rÓ   r6   r7   r8   r   r   æ   s~   „ ñð €Mó9ð*2˜#ó 2ò	òMò$ò*òRò.ò"ò'ñ( ‘˜	 2 q¨!Ó,¨mÓ<ñ1ó =ð1óòó9r7   r   )6r)   r±   rz   ry   Úplatformrœ   rK   Úcollectionsr   Útypingr   Úzope.interfacer   r   r   Ú
constantlyr   r	   Úincrementalr
   Útwisted.internetr   r   r   r   r   Útwisted.pairr   r   Útwisted.pythonr   Útwisted.python.deprecater   Útwisted.python.reflectr   Útwisted.python.utilr   r   Ú__all__rž   ÚmachineÚ
startswithr    Ú
_TUNGETIFFrŸ   r   ÚIAddressr   rT   rV   rw   ÚIListeningPortr„   r   r6   r7   r8   ú<module>rç      sE  ðñ
ó Û Û 	Û Û Û Ý "Ý ç <Ñ <ç *Ý ç EÕ Eß &Ý Ý /Ý 5ß ;ò€ð €	à€H×ÑÓ˜(Ò"Ø€x×ÑÓ×$Ñ$ UÔ+Ø€x×ÑÓ×$Ñ$ WÔ-ð €JØ�Jà€JØ€JØ€ô(�%ô (ñB ˆZ× Ñ Ó!ô&,�M <ó &,ó "ð&,ôR	™Ð$8¸-ÓHô 	ôC˜)ô C÷L4ñ 4ñ& ˆZ×&Ñ&Ó'ô@9�×(Ñ(ó @9ó (ñ@9r7   