B
    Á S]–N  ã               @   sh  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m	Z	m
Z
mZmZmZmZmZmZmZmZmZmZ eeeeeeehƒZye W n ek
r¤   i ZY nX dd„ ZG dd„ deƒZeeefZdd	„ Zd
d„ Z dd„ Z!dd„ Z"d&dd„Z#d'dd„Z$e$Z%d(dd„Z&G dd„ dƒZ'G dd„ de'ƒZ(dd„ Z)d)dd „Z*ej+d!krdG d"d#„ d#ƒZ,G d$d%„ d%e'ƒZ-dS )*a   Basic infrastructure for asynchronous socket service clients and servers.

There are only two ways to have a program on a single processor do "more
than one thing at a time".  Multi-threaded programming is the simplest and
most popular way to do it, but there is another very different technique,
that lets you have nearly all the advantages of multi-threading, without
actually using multiple threads. it's really only practical if your program
is largely I/O bound. If your program is CPU bound, then pre-emptive
scheduled threads are probably what you really need. Network servers are
rarely CPU-bound, however.

If your operating system supports the select() system call in its I/O
library (and nearly all do), then you can use it to juggle multiple
communication channels at once; doing other work while your I/O is taking
place in the "background."  Although this strategy can seem strange and
complex, especially at first, it is in many ways easier to understand and
control than multi-threaded programming. The module documented here solves
many of the difficult problems for you, making the task of building
sophisticated high-performance network servers and clients a snap.
é    N)ÚEALREADYÚEINPROGRESSÚEWOULDBLOCKÚ
ECONNRESETÚEINVALÚENOTCONNÚ	ESHUTDOWNÚEISCONNÚEBADFÚECONNABORTEDÚEPIPEÚEAGAINÚ	errorcodec          
   C   s>   y
t  | ¡S  tttfk
r8   | tkr0t|  S d|  S X d S )NzUnknown error %s)ÚosÚstrerrorÚ
ValueErrorÚOverflowErrorÚ	NameErrorr   )Úerr© r   úlib/python3.7/asyncore.pyÚ	_strerrorD   s    
r   c               @   s   e Zd ZdS )ÚExitNowN)Ú__name__Ú
__module__Ú__qualname__r   r   r   r   r   L   s   r   c             C   s:   y|   ¡  W n( tk
r"   ‚ Y n   |  ¡  Y nX d S )N)Úhandle_read_eventÚ_reraised_exceptionsÚhandle_error)Úobjr   r   r   ÚreadQ   s    r    c             C   s:   y|   ¡  W n( tk
r"   ‚ Y n   |  ¡  Y nX d S )N)Úhandle_write_eventr   r   )r   r   r   r   ÚwriteY   s    r"   c             C   s:   y|   ¡  W n( tk
r"   ‚ Y n   |  ¡  Y nX d S )N)Úhandle_expt_eventr   r   )r   r   r   r   Ú
_exceptiona   s    r$   c          
   C   sÆ   yX|t j@ r|  ¡  |t j@ r&|  ¡  |t j@ r8|  ¡  |t jt jB t j	B @ rV|  
¡  W nh tk
rš } z$|jd tkr‚|  ¡  n|  
¡  W d d }~X Y n( tk
r®   ‚ Y n   |  ¡  Y nX d S )Nr   )ÚselectÚPOLLINr   ÚPOLLOUTr!   ÚPOLLPRIr#   ZPOLLHUPZPOLLERRZPOLLNVALÚhandle_closeÚOSErrorÚargsÚ_DISCONNECTEDr   r   )r   ÚflagsÚer   r   r   Ú	readwritei   s"    



r/   ç        c       	      C   sL  |d krt }|rHg }g }g }x\t| ¡ ƒD ]L\}}| ¡ }| ¡ }|rR| |¡ |rf|jsf| |¡ |sn|r,| |¡ q,W g |  krš|  krš|kr¬n nt | ¡ d S t	 	|||| ¡\}}}x(|D ] }| 
|¡}|d kràqÈt|ƒ qÈW x*|D ]"}| 
|¡}|d krqòt|ƒ qòW x.|D ]&}| 
|¡}|d kr:qt|ƒ qW d S )N)Ú
socket_mapÚlistÚitemsÚreadableÚwritableÚappendÚ	acceptingÚtimeZsleepr%   Úgetr    r"   r$   )	ÚtimeoutÚmapÚrÚwr.   Úfdr   Zis_rZis_wr   r   r   Úpoll}   sD      


"








r?   c             C   sÈ   |d krt }| d k	r t| d ƒ} t ¡ }|rÄx\t| ¡ ƒD ]L\}}d}| ¡ r^|tjtjB O }| 	¡ rv|j
sv|tjO }|r:| ||¡ q:W | | ¡}x.|D ]&\}}| |¡}|d kr¶qšt||ƒ qšW d S )Niè  r   )r1   Úintr%   r?   r2   r3   r4   r&   r(   r5   r7   r'   Úregisterr9   r/   )r:   r;   Zpollsterr>   r   r-   r<   r   r   r   Úpoll2¤   s(    


rB   ç      >@Fc             C   sj   |d krt }|r ttdƒr t}nt}|d krBx8|r>|| |ƒ q.W n$x"|rd|dkrd|| |ƒ |d }qDW d S )Nr?   r   é   )r1   Úhasattrr%   rB   r?   )r:   Zuse_pollr;   ÚcountZpoll_funr   r   r   ÚloopÀ   s    
rG   c               @   s6  e Zd ZdZdZdZdZdZdZe	dhƒZ
dAdd„Zdd„ ZeZdBdd	„ZdCd
d„Zejejfdd„ZdDdd„Zdd„ Zdd„ Zdd„ Zdd„ Zdd„ Zdd„ Zdd„ Zdd„ Zd d!„ Zd"d#„ Zd$d%„ ZdEd'd(„Z d)d*„ Z!d+d,„ Z"d-d.„ Z#d/d0„ Z$d1d2„ Z%d3d4„ Z&d5d6„ Z'd7d8„ Z(d9d:„ Z)d;d<„ Z*d=d>„ Z+d?d@„ Z,dS )FÚ
dispatcherFNÚwarningc          
   C   s    |d krt | _n|| _d | _|r–| d¡ |  ||¡ d| _y| ¡ | _W qœ tk
r’ } z*|j	d t
tfkrvd| _n|  |¡ ‚ W d d }~X Y qœX nd | _d S )Nr   TF)r1   Ú_mapÚ_filenoÚsetblockingÚ
set_socketÚ	connectedZgetpeernameÚaddrr*   r+   r   r   Údel_channelÚsocket)ÚselfÚsockr;   r   r   r   r   Ú__init__Ü   s     

zdispatcher.__init__c             C   s˜   | j jd | j j g}| jr.| jr.| d¡ n| jr>| d¡ | jd k	r‚y| d| j ¡ W n$ tk
r€   | t| jƒ¡ Y nX dd 	|¡t
| ƒf S )NÚ.Z	listeningrN   z%s:%dz<%s at %#x>ú )Ú	__class__r   r   r7   rO   r6   rN   Ú	TypeErrorÚreprÚjoinÚid)rR   Zstatusr   r   r   Ú__repr__ü   s    

zdispatcher.__repr__c             C   s   |d kr| j }| || j< d S )N)rJ   rK   )rR   r;   r   r   r   Úadd_channel  s    zdispatcher.add_channelc             C   s,   | j }|d kr| j}||kr"||= d | _ d S )N)rK   rJ   )rR   r;   r>   r   r   r   rP     s    zdispatcher.del_channelc             C   s.   ||f| _ t ||¡}| d¡ |  |¡ d S )Nr   )Zfamily_and_typerQ   rL   rM   )rR   ZfamilyÚtyperS   r   r   r   Úcreate_socket  s    

zdispatcher.create_socketc             C   s   || _ | ¡ | _|  |¡ d S )N)rQ   ÚfilenorK   r]   )rR   rS   r;   r   r   r   rM      s    
zdispatcher.set_socketc             C   sD   y*| j  t jt j| j  t jt j¡dB ¡ W n tk
r>   Y nX d S )NrD   )rQ   Z
setsockoptÚ
SOL_SOCKETZSO_REUSEADDRÚ
getsockoptr*   )rR   r   r   r   Úset_reuse_addr%  s    
zdispatcher.set_reuse_addrc             C   s   dS )NTr   )rR   r   r   r   r4   6  s    zdispatcher.readablec             C   s   dS )NTr   )rR   r   r   r   r5   9  s    zdispatcher.writablec             C   s(   d| _ tjdkr|dkrd}| j |¡S )NTÚnté   )r7   r   ÚnamerQ   Úlisten)rR   Znumr   r   r   rg   @  s    zdispatcher.listenc             C   s   || _ | j |¡S )N)rO   rQ   Úbind)rR   rO   r   r   r   rh   F  s    zdispatcher.bindc             C   sp   d| _ d| _| j |¡}|tttfks8|tkrBtj	dkrB|| _
d S |dtfkr^|| _
|  ¡  nt|t| ƒ‚d S )NFTrd   r   )rN   Ú
connectingrQ   Z
connect_exr   r   r   r   r   rf   rO   r	   Úhandle_connect_eventr*   r   )rR   Zaddressr   r   r   r   ÚconnectJ  s    
zdispatcher.connectc          
   C   sn   y| j  ¡ \}}W nN tk
r&   d S  tk
r` } z|jd tttfkrNd S ‚ W d d }~X Y n
X ||fS d S )Nr   )rQ   ÚacceptrX   r*   r+   r   r   r   )rR   ZconnrO   Úwhyr   r   r   rl   X  s    zdispatcher.acceptc          
   C   sf   y| j  |¡}|S  tk
r` } z2|jd tkr4dS |jd tkrN|  ¡  dS ‚ W d d }~X Y nX d S )Nr   )rQ   Úsendr*   r+   r   r,   r)   )rR   ÚdataÚresultrm   r   r   r   rn   f  s    zdispatcher.sendc          
   C   sh   y$| j  |¡}|s|  ¡  dS |S W n> tk
rb } z |jd tkrP|  ¡  dS ‚ W d d }~X Y nX d S )Nó    r   )rQ   Úrecvr)   r*   r+   r,   )rR   Úbuffer_sizero   rm   r   r   r   rr   s  s    zdispatcher.recvc          
   C   sn   d| _ d| _d| _|  ¡  | jd k	rjy| j ¡  W n6 tk
rh } z|jd tt	fkrX‚ W d d }~X Y nX d S )NFr   )
rN   r7   ri   rP   rQ   Úcloser*   r+   r   r
   )rR   rm   r   r   r   rt   …  s    
zdispatcher.closec             C   s   t j dt|ƒ ¡ d S )Nzlog: %s
)ÚsysÚstderrr"   Ústr)rR   Úmessager   r   r   Úlog•  s    zdispatcher.logÚinfoc             C   s   || j krtd||f ƒ d S )Nz%s: %s)Úignore_log_typesÚprint)rR   rx   r^   r   r   r   Úlog_info˜  s    
zdispatcher.log_infoc             C   s:   | j r|  ¡  n&| js.| jr$|  ¡  |  ¡  n|  ¡  d S )N)r7   Úhandle_acceptrN   ri   rj   Úhandle_read)rR   r   r   r   r   œ  s    

zdispatcher.handle_read_eventc             C   s@   | j  t jt j¡}|dkr(t|t|ƒƒ‚|  ¡  d| _d| _d S )Nr   TF)	rQ   rb   ra   ÚSO_ERRORr*   r   Úhandle_connectrN   ri   )rR   r   r   r   r   rj   ¨  s    zdispatcher.handle_connect_eventc             C   s*   | j r
d S | js| jr|  ¡  |  ¡  d S )N)r7   rN   ri   rj   Úhandle_write)rR   r   r   r   r!   °  s    zdispatcher.handle_write_eventc             C   s0   | j  t jt j¡}|dkr$|  ¡  n|  ¡  d S )Nr   )rQ   rb   ra   r€   r)   Úhandle_expt)rR   r   r   r   r   r#   »  s    
zdispatcher.handle_expt_eventc             C   sX   t ƒ \}}}}yt| ƒ}W n   dt| ƒ }Y nX |  d||||f d¡ |  ¡  d S )Nz)<__repr__(self) failed for object at %0x>z:uncaptured python exception, closing channel %s (%s:%s %s)Úerror)Úcompact_tracebackrY   r[   r}   r)   )rR   ZnilÚtÚvÚtbinfoZ	self_reprr   r   r   r   Ê  s    zdispatcher.handle_errorc             C   s   |   dd¡ d S )Nz!unhandled incoming priority eventrI   )r}   )rR   r   r   r   rƒ   Þ  s    zdispatcher.handle_exptc             C   s   |   dd¡ d S )Nzunhandled read eventrI   )r}   )rR   r   r   r   r   á  s    zdispatcher.handle_readc             C   s   |   dd¡ d S )Nzunhandled write eventrI   )r}   )rR   r   r   r   r‚   ä  s    zdispatcher.handle_writec             C   s   |   dd¡ d S )Nzunhandled connect eventrI   )r}   )rR   r   r   r   r   ç  s    zdispatcher.handle_connectc             C   s   |   ¡ }|d k	r| j|Ž  d S )N)rl   Úhandle_accepted)rR   Zpairr   r   r   r~   ê  s    zdispatcher.handle_acceptc             C   s   |  ¡  |  dd¡ d S )Nzunhandled accepted eventrI   )rt   r}   )rR   rS   rO   r   r   r   r‰   ï  s    zdispatcher.handle_acceptedc             C   s   |   dd¡ |  ¡  d S )Nzunhandled close eventrI   )r}   rt   )rR   r   r   r   r)   ó  s    zdispatcher.handle_close)NN)N)N)N)rz   )-r   r   r   ÚdebugrN   r7   ri   ÚclosingrO   Ú	frozensetr{   rT   r\   Ú__str__r]   rP   rQ   ZAF_INETZSOCK_STREAMr_   rM   rc   r4   r5   rg   rh   rk   rl   rn   rr   rt   ry   r}   r   rj   r!   r#   r   rƒ   r   r‚   r   r~   r‰   r)   r   r   r   r   rH   Ò   sL   

 

	

rH   c               @   s6   e Zd Zddd„Zdd„ Zdd„ Zdd	„ Zd
d„ ZdS )Údispatcher_with_sendNc             C   s   t  | ||¡ d| _d S )Nrq   )rH   rT   Ú
out_buffer)rR   rS   r;   r   r   r   rT   þ  s    zdispatcher_with_send.__init__c             C   s.   d}t  | | jd d… ¡}| j|d … | _d S )Nr   i   )rH   rn   r   )rR   Znum_sentr   r   r   Úinitiate_send  s    z"dispatcher_with_send.initiate_sendc             C   s   |   ¡  d S )N)r   )rR   r   r   r   r‚     s    z!dispatcher_with_send.handle_writec             C   s   | j  pt| jƒS )N)rN   Úlenr   )rR   r   r   r   r5   
  s    zdispatcher_with_send.writablec             C   s0   | j r|  dt|ƒ ¡ | j| | _|  ¡  d S )Nz
sending %s)rŠ   r}   rY   r   r   )rR   ro   r   r   r   rn     s    zdispatcher_with_send.send)NN)r   r   r   rT   r   r‚   r5   rn   r   r   r   r   rŽ   ü  s
   
rŽ   c              C   s†   t  ¡ \} }}g }|stdƒ‚x0|rN| |jjj|jjjt|j	ƒf¡ |j
}q W ~|d \}}}d dd„ |D ƒ¡}|||f| ||fS )Nztraceback does not existéÿÿÿÿrV   c             S   s   g | ]}d | ‘qS )z
[%s|%s|%s]r   )Ú.0Úxr   r   r   ú
<listcomp>(  s    z%compact_traceback.<locals>.<listcomp>)ru   Úexc_infoÚAssertionErrorr6   Útb_frameÚf_codeÚco_filenameÚco_namerw   Ú	tb_linenoÚtb_nextrZ   )r†   r‡   Útbrˆ   ÚfileZfunctionÚlinerz   r   r   r   r…     s    
r…   c             C   s˜   | d krt } x~t|  ¡ ƒD ]n}y| ¡  W q tk
rb } z|jd tkrLn|sR‚ W d d }~X Y q tk
rv   ‚ Y q   |s‚‚ Y qX qW |  ¡  d S )Nr   )	r1   r2   Úvaluesrt   r*   r+   r
   r   Úclear)r;   Z
ignore_allr”   r   r   r   Ú	close_all+  s     r£   Úposixc               @   sN   e Zd Zdd„ Zdd„ Zdd„ Zdd„ Zdd
d„ZeZeZ	dd„ Z
dd„ Zd	S )Úfile_wrapperc             C   s   t  |¡| _d S )N)r   Údupr>   )rR   r>   r   r   r   rT   P  s    zfile_wrapper.__init__c             C   s*   | j dkrtjd|  t| d |  ¡  d S )Nr   zunclosed file %r)Úsource)r>   ÚwarningsÚwarnÚResourceWarningrt   )rR   r   r   r   Ú__del__S  s    
zfile_wrapper.__del__c             G   s   t j| jf|žŽ S )N)r   r    r>   )rR   r+   r   r   r   rr   Y  s    zfile_wrapper.recvc             G   s   t j| jf|žŽ S )N)r   r"   r>   )rR   r+   r   r   r   rn   \  s    zfile_wrapper.sendNc             C   s(   |t jkr|t jkr|sdS tdƒ‚d S )Nr   z-Only asyncore specific behaviour implemented.)rQ   ra   r€   ÚNotImplementedError)rR   ÚlevelZoptnameZbuflenr   r   r   rb   _  s
    

zfile_wrapper.getsockoptc             C   s(   | j dk rd S | j }d| _ t |¡ d S )Nr   r’   )r>   r   rt   )rR   r>   r   r   r   rt   j  s
    
zfile_wrapper.closec             C   s   | j S )N)r>   )rR   r   r   r   r`   q  s    zfile_wrapper.fileno)N)r   r   r   rT   r«   rr   rn   rb   r    r"   rt   r`   r   r   r   r   r¥   K  s   
r¥   c               @   s   e Zd Zddd„Zdd„ ZdS )Úfile_dispatcherNc             C   sP   t  | d |¡ d| _y| ¡ }W n tk
r4   Y nX |  |¡ t |d¡ d S )NTF)rH   rT   rN   r`   ÚAttributeErrorÚset_filer   Úset_blocking)rR   r>   r;   r   r   r   rT   v  s    
zfile_dispatcher.__init__c             C   s"   t |ƒ| _| j ¡ | _|  ¡  d S )N)r¥   rQ   r`   rK   r]   )rR   r>   r   r   r   r°     s    
zfile_dispatcher.set_file)N)r   r   r   rT   r°   r   r   r   r   r®   t  s   
r®   )r0   N)r0   N)rC   FNN)NF).Ú__doc__r%   rQ   ru   r8   r¨   r   Úerrnor   r   r   r   r   r   r   r	   r
   r   r   r   r   rŒ   r,   r1   r   r   Ú	Exceptionr   ÚKeyboardInterruptÚ
SystemExitr   r    r"   r$   r/   r?   rB   Zpoll3rG   rH   rŽ   r…   r£   rf   r¥   r®   r   r   r   r   Ú<module>/   sB   <


'

  ,
)