U
    î¤ùd  ã                   @   s¬   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Zd dlZd dl	Z
d dlZ
d dlmZ d dlmZmZmZmZmZ G dd„ deƒZG dd„ deƒZG dd	„ d	eƒZdS )
é    N)ÚNullContext)ÚQUIC_MAX_DATAGRAMÚAsyncQuicConnectionÚAsyncQuicManagerÚBaseQuicStreamÚUnexpectedEOFc                       sX   e Zd Z‡ fdd„Zdd„ Zddd„Zdd	d
„Zdd„ Zdd„ Zdd„ Z	dd„ Z
‡  ZS )ÚTrioQuicStreamc                    s   t ƒ  ||¡ t ¡ | _d S ©N)ÚsuperÚ__init__ÚtrioÚ	ConditionÚ_wake_up)ÚselfÚ
connectionÚ	stream_id©Ú	__class__© ú2/tmp/pip-unpacked-wheel-pk5slln3/dns/quic/_trio.pyr      s    zTrioQuicStream.__init__c              
   Ã   sR   | j  |¡rd S || _| j4 I d H š | j ¡ I d H  W 5 Q I d H R X d| _q d S ©Nr   )Ú_bufferZhaveZ
_expectingr   Úwait)r   Úamountr   r   r   Úwait_for   s     zTrioQuicStream.wait_forNc              
   Ã   s‚   |d krt d ƒ}n
t |¡}|P |  d¡I d H  t d| j d¡¡\}|  |¡I d H  | j |¡W  5 Q R £ S Q R X tj	j
‚d S )Né   z!H)r   r   Úmove_on_afterr   ÚstructÚunpackr   ÚgetÚdnsÚ	exceptionÚTimeout)r   ÚtimeoutÚcontextÚsizer   r   r   Úreceive'   s    

zTrioQuicStream.receiveFc                 Ã   s&   |   |¡}| j | j||¡I d H  d S r	   )Z_encapsulateÚ_connectionÚwriteZ
_stream_id)r   ÚdatagramÚis_endÚdatar   r   r   Úsend3   s    
zTrioQuicStream.sendc              
   Ã   s:   |   ||¡r6| j4 I d H š | j ¡  W 5 Q I d H R X d S r	   )Z_common_add_inputr   Únotify)r   r+   r*   r   r   r   Ú
_add_input7   s    zTrioQuicStream._add_inputc                 Ã   s   |   ¡  d S r	   )Ú_close©r   r   r   r   Úclose<   s    zTrioQuicStream.closec                 Ã   s   | S r	   r   r0   r   r   r   Ú
__aenter__A   s    zTrioQuicStream.__aenter__c              
   Ã   s<   |   ¡ I d H  | j4 I d H š | j ¡  W 5 Q I d H R X dS ©NF)r1   r   r-   )r   Úexc_typeÚexc_valÚexc_tbr   r   r   Ú	__aexit__D   s    zTrioQuicStream.__aexit__)N)F)Ú__name__Ú
__module__Ú__qualname__r   r   r&   r,   r.   r1   r2   r7   Ú__classcell__r   r   r   r   r      s   	

r   c                       sR   e Zd Zd‡ fdd„	Zdd„ Zdd„ Zdd	d
„Zdd„ Zddd„Zdd„ Z	‡  Z
S )ÚTrioQuicConnectionNc                    sj   t ƒ  ||||||¡ tj | jtjd¡| _| jrLtj t	j
 | j| j¡¡ t ¡ | _t ¡ | _d | _d S r   )r
   r   r   ÚsocketZ_afÚ
SOCK_DGRAMÚ_socketÚ_sourceÚbindr    ZinetZlow_level_address_tupleÚEventÚ_handshake_completeÚ	_run_doneÚ_worker_scope)r   r   ÚaddressÚportÚsourceÚsource_portÚmanagerr   r   r   r   L   s    

zTrioQuicConnection.__init__c              	   Ã   sâ   zÊ| j | j¡I d H  | j sÈ|  d¡\}}tjt 	¡ | d4| _
| j t¡I d H }| j || jd t ¡ ¡ W 5 Q R X d | _
|  |¡ | j t ¡ ¡}|D ]\}}| j |¡I d H  qœ|  ¡ I d H  qW 5 d| _ | j ¡  X d S )NTF)Údeadliner   )Ú_donerC   Úsetr?   ÚconnectÚ_peerZ_get_timer_valuesr   ZCancelScopeÚcurrent_timerE   Úrecvr   r'   Zreceive_datagramÚtimeZ_handle_timerZdatagrams_to_sendr,   Ú_handle_events)r   Z
expirationÚintervalr)   Z	datagramsÚ_r   r   r   Ú_workerU   s,    
ÿ  ÿ
zTrioQuicConnection._workerc                 Ã   sÊ   d}| j  ¡ }|d krd S t|tjjjƒrT| j |j	¡}|r | 
|j|j¡I d H  nLt|tjjjƒrp| j ¡  n0t|tjjjƒst|tjjjƒr d| _| j ¡  |d7 }|dkrd}t d¡I d H  qd S )Nr   Té   é
   )r'   Z
next_eventÚ
isinstanceÚaioquicZquicÚeventsZStreamDataReceivedÚ_streamsr   r   r.   r+   Z
end_streamZHandshakeCompletedrC   rM   ZConnectionTerminatedZStreamResetrL   r?   r1   r   Úsleep)r   ÚcountÚeventÚstreamr   r   r   rS   k   s,    
 ÿþ
z!TrioQuicConnection._handle_eventsFc                 Ã   s(   | j  |||¡ | jd k	r$| j ¡  d S r	   )r'   Zsend_stream_datarE   Úcancel)r   r`   r+   r*   r   r   r   r(   ‚   s    
zTrioQuicConnection.writec              
   Ã   sF   | j r
d S t ¡ 4 I d H š}| | j¡ W 5 Q I d H R X | j ¡  d S r	   )Ú_closedr   Zopen_nurseryÚ
start_soonrV   rD   rM   )r   Únurseryr   r   r   Úrun‡   s
    zTrioQuicConnection.runc              
   Ã   s~   |d krt d ƒ}n
t |¡}|L | j ¡ I d H  | jr<t‚| j d¡}t	| |ƒ}|| j
|< |W  5 Q R £ S Q R X tjj‚d S r3   )r   r   r   rC   r   rL   r   r'   Zget_next_available_stream_idr   r\   r    r!   r"   )r   r#   r$   r   r`   r   r   r   Úmake_streamŽ   s    



zTrioQuicConnection.make_streamc                 Ã   sX   | j sT| j | jd | jd ¡ d| _ | j ¡  | jd k	rD| j ¡  | j 	¡ I d H  d S )Nr   rW   T)
rb   Ú_managerÚclosedrO   r'   r1   rE   ra   rD   r   r0   r   r   r   r1      s    


zTrioQuicConnection.close)N)F)N)r8   r9   r:   r   rV   rS   r(   re   rf   r1   r;   r   r   r   r   r<   K   s   	

r<   c                       s@   e Zd Zdejdf‡ fdd„	Zddd„Zdd	„ Zd
d„ Z‡  Z	S )ÚTrioQuicManagerNc                    s   t ƒ  ||t|¡ || _d S r	   )r
   r   r<   Ú_nursery)r   rd   ÚconfÚverify_modeZserver_namer   r   r   r   ¨   s    zTrioQuicManager.__init__éU  r   c                 C   s*   |   ||||¡\}}|r&| j |j¡ |S r	   )Ú_connectrj   rc   re   )r   rF   rG   rH   rI   r   Ústartr   r   r   rN   ®   s    zTrioQuicManager.connectc                 Ã   s   | S r	   r   r0   r   r   r   r2   ´   s    zTrioQuicManager.__aenter__c                 Ã   s*   t | j ¡ ƒ}|D ]}| ¡ I d H  qdS r3   )ÚlistZ_connectionsÚvaluesr1   )r   r4   r5   r6   Úconnectionsr   r   r   r   r7   ·   s    zTrioQuicManager.__aexit__)rm   Nr   )
r8   r9   r:   ÚsslÚCERT_REQUIREDr   rN   r2   r7   r;   r   r   r   r   ri   §   s     ÿ
ri   )r=   rs   r   rR   Zaioquic.quic.configurationrZ   Zaioquic.quic.connectionZaioquic.quic.eventsr   Zdns.exceptionr    Zdns.inetZdns._asyncbackendr   Zdns.quic._commonr   r   r   r   r   r   r<   ri   r   r   r   r   Ú<module>   s   	2\