
[XMc           @   s   d  Z  d d l Z d d l Z d d l m Z d d l m Z d d l m Z d d l m	 Z	 d d l
 m Z m Z d d l m Z m Z e j e j BZ d	 e j f d
     YZ d   Z d	 d g Z d S(   s   
An epoll() based implementation of the twisted main loop.

To install the event loop (and you should do this before any connections,
listeners or connectors are added)::

    from twisted.internet import epollreactor
    epollreactor.install()
iN(   t
   implements(   t   IReactorFDSet(   t   _epoll(   t   log(   t	   posixbaset   error(   t   CONNECTION_DONEt   CONNECTION_LOSTt   EPollReactorc           B   s   e  Z d  Z e e  d   Z d   Z d   Z d   Z d   Z	 d   Z
 d   Z d   Z d	   Z d
   Z d   Z e Z d   Z RS(   sX  
    A reactor that uses epoll(4).

    @ivar _poller: A L{poll} which will be used to check for I/O
        readiness.

    @ivar _selectables: A dictionary mapping integer file descriptors to
        instances of L{FileDescriptor} which have been registered with the
        reactor.  All L{FileDescriptors} which are currently receiving read or
        write readiness notifications will be present as values in this
        dictionary.

    @ivar _reads: A dictionary mapping integer file descriptors to arbitrary
        values (this is essentially a set).  Keys in this dictionary will be
        registered with C{_poller} for read readiness notifications which will
        be dispatched to the corresponding L{FileDescriptor} instances in
        C{_selectables}.

    @ivar _writes: A dictionary mapping integer file descriptors to arbitrary
        values (this is essentially a set).  Keys in this dictionary will be
        registered with C{_poller} for write readiness notifications which will
        be dispatched to the corresponding L{FileDescriptor} instances in
        C{_selectables}.
    c         C   sA   t  j d  |  _ i  |  _ i  |  _ i  |  _ t j j |   d S(   sm   
        Initialize epoll object, file descriptor tracking dictionaries, and the
        base class.
        i   N(	   R   t   epollt   _pollert   _readst   _writest   _selectablesR   t   PosixReactorBaset   __init__(   t   self(    (    sA   /usr/lib/python2.7/dist-packages/twisted/internet/epollreactor.pyR   7   s
    			c   
      C   sz   | j    } | | k rv t j } | }	 | | k rI |	 | O}	 t j } n  |  j j | | |	  d | | <| | | <n  d S(   s   
        Private method for adding a descriptor from the event loop.

        It takes care of adding it if  new or modifying it if already added
        for another state (read -> read/write for example).
        i   N(   t   filenoR   t   CTL_ADDt   CTL_MODR
   t   _control(
   R   t   xert   primaryt   othert   selectablest   eventt	   antieventt   fdt   cmdt   flags(    (    sA   /usr/lib/python2.7/dist-packages/twisted/internet/epollreactor.pyt   _addE   s    	

c         C   s/   |  j  | |  j |  j |  j t j t j  d S(   sR   
        Add a FileDescriptor for notification of data available to read.
        N(   R   R   R   R   R   t   INt   OUT(   R   t   reader(    (    sA   /usr/lib/python2.7/dist-packages/twisted/internet/epollreactor.pyt	   addReader`   s    c         C   s/   |  j  | |  j |  j |  j t j t j  d S(   sS   
        Add a FileDescriptor for notification of data available to write.
        N(   R   R   R   R   R   R    R   (   R   t   writer(    (    sA   /usr/lib/python2.7/dist-packages/twisted/internet/epollreactor.pyt	   addWriterg   s    c         C   s   | j    } | d k rL x1 | j   D] \ } } | | k r% Pq% q% Wd Sn  | | k r t j }	 | }
 | | k r | }
 t j }	 n | | =| | =|  j j |	 | |
  n  d S(   s   
        Private method for removing a descriptor from the event loop.

        It does the inverse job of _add, and also add a check in case of the fd
        has gone away.
        iN(   R   t   itemsR   t   CTL_DELR   R
   R   (   R   R   R   R   R   R   R   R   t   fdesR   R   (    (    sA   /usr/lib/python2.7/dist-packages/twisted/internet/epollreactor.pyt   _removen   s    	c         C   s/   |  j  | |  j |  j |  j t j t j  d S(   sQ   
        Remove a Selectable for notification of data available to read.
        N(   R(   R   R   R   R   R   R    (   R   R!   (    (    sA   /usr/lib/python2.7/dist-packages/twisted/internet/epollreactor.pyt   removeReader   s    c         C   s/   |  j  | |  j |  j |  j t j t j  d S(   sR   
        Remove a Selectable for notification of data available to write.
        N(   R(   R   R   R   R   R    R   (   R   R#   (    (    sA   /usr/lib/python2.7/dist-packages/twisted/internet/epollreactor.pyt   removeWriter   s    c         C   sJ   |  j  g  |  j D] } |  j | ^ q g  |  j D] } |  j | ^ q0  S(   sD   
        Remove all selectables, and return a list of them.
        (   t
   _removeAllR   R   R   (   R   R   (    (    sA   /usr/lib/python2.7/dist-packages/twisted/internet/epollreactor.pyt	   removeAll   s     c         C   s!   g  |  j  D] } |  j | ^ q
 S(   N(   R   R   (   R   R   (    (    sA   /usr/lib/python2.7/dist-packages/twisted/internet/epollreactor.pyt
   getReaders   s    c         C   s!   g  |  j  D] } |  j | ^ q
 S(   N(   R   R   (   R   R   (    (    sA   /usr/lib/python2.7/dist-packages/twisted/internet/epollreactor.pyt
   getWriters   s    c         C   s   | d k r d } n  t | d  } y" |  j j t |  j  |  } Wn, t k
 ru } | j t j k ro d S  n X|  j	 } xR | D]J \ } } y |  j | } Wn t
 k
 r q Xt j | | | | |  q Wd S(   s1   
        Poll the poller for new events.
        i   i  N(   t   Nonet   intR
   t   waitt   lenR   t   IOErrort   errnot   EINTRt   _doReadOrWritet   KeyErrorR   t   callWithLogger(   R   t   timeoutt   lt   errt   _drdwR   R   t
   selectable(    (    sA   /usr/lib/python2.7/dist-packages/twisted/internet/epollreactor.pyt   doPoll   s     	"	c         C   s  d } t } | t @rK | t j @rK | |  j k rB t } t } q t } n yy | t j @rp | j	   } t } n  | r | t j
 @r | j   } t } n  | j   | k r t j d  } t } n  Wn! t j   t j   d } n X| r|  j | | |  n  d S(   si   
        fd is available for read or write, make the work and raise errors
        if necessary.
        s   Filedescriptor went awayi   N(   R/   t   Falset   _POLL_DISCONNECTEDR   R   R   t   TrueR   R   t   doReadR    t   doWriteR   R   t   ConnectionFdescWentAwayR   R;   t   syst   exc_infot   _disconnectSelectable(   R   R=   R   R   t   whyt   inRead(    (    sA   /usr/lib/python2.7/dist-packages/twisted/internet/epollreactor.pyR6      s.    					
(   t   __name__t
   __module__t   __doc__R    R   R   R   R"   R$   R(   R)   R*   R,   R-   R.   R>   t   doIterationR6   (    (    (    sA   /usr/lib/python2.7/dist-packages/twisted/internet/epollreactor.pyR      s   
												 c          C   s'   t    }  d d l m } | |   d S(   s&   
    Install the epoll() reactor.
    i(   t   installReactorN(   R   t   twisted.internet.mainRN   (   t   pRN   (    (    sA   /usr/lib/python2.7/dist-packages/twisted/internet/epollreactor.pyt   install   s    	RQ   (   RL   RE   R4   t   zope.interfaceR    t   twisted.internet.interfacesR   t   twisted.pythonR   R   t   twisted.internetR   R   RO   R   R   t   HUPt   ERRR@   R   R   RQ   t   __all__(    (    (    sA   /usr/lib/python2.7/dist-packages/twisted/internet/epollreactor.pyt   <module>   s   		