
    [4%e2p                     \   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 d dl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mZmZ d dlmZmZ 	 d dl Zd dl!m"Z" n# e#$ r  ej$                      w xY wd dl m%Z%m&Z&m'Z'm(Z( 	 d dlm)Z) n# e#$ r dZ)Y nw xY w G d de%          Z* G d de*          Z+ G d de*          Z, G d de*          Z- G d de*          Z. G d de          Z/ G d de          Z0 G d de*          Z1 G d d e*          Z2 G d! d"e*          Z3 G d# d$e*          Z4 G d% d&e*          Z5 G d' d(e*          Z6 G d) d*e*          Z7 G d+ d,e*          Z8 G d- d.e*          Z9 G d/ d0e*          Z: G d1 d2e          Z; G d3 d4e;          Z< G d5 d6e*          Z= G d7 d8e;          Z> G d9 d:e?          Z@ G d; d<e@          ZA G d= d>eAe;          ZB G d? d@eAe;          ZC G dA dBeAe;          ZD G dC dDe@e;          ZE G dE dFe?          ZF G dG dHeFejG                  ZH ejI        e)du dI           G dJ dKeFejG                              ZJ G dL dMe;          ZK G dN dOe;          ZL G dP dQe;          ZM G dR dSe;          ZNdS )T    N)Future)gen)	HTTPErrorHTTPRequest)Event)gen_logapp_log)ResolverSimpleAsyncHTTPClient)
DictLoader)AsyncHTTPTestCasegen_testbind_unused_port	ExpectLog)ApplicationRequestHandler_websocket_mask_python)WebSocketHandlerwebsocket_connectWebSocketErrorWebSocketClosedError)speedupsc                   &    e Zd ZdZddZd Zd ZdS )TestWebSocketHandlerzBase class for testing handlers that exposes the on_close event.

    This allows for tests to see the close code and reason on the
    server side.

    Nc                 "    || _         || _        d S N)close_futurecompression_options)selfr   r    s      ;lib/python3.11/site-packages/tornado/test/websocket_test.py
initializezTestWebSocketHandler.initialize3   s    (#6       c                     | j         S r   r    r!   s    r"   get_compression_optionsz,TestWebSocketHandler.get_compression_options7   s    ''r$   c                 d    | j         (| j                             | j        | j        f           d S d S r   )r   
set_result
close_codeclose_reasonr'   s    r"   on_closezTestWebSocketHandler.on_close:   s:    ((($/4;L)MNNNNN )(r$   )NN)__name__
__module____qualname____doc__r#   r(   r-    r$   r"   r   r   +   sU         7 7 7 7( ( (O O O O Or$   r   c                   .    e Zd Zej        d             ZdS )EchoHandlerc              #      K   	 |                      |t          |t                              V  d S # t          j        $ r Y d S t
          $ r Y d S w xY wr   )write_message
isinstancebytesasyncioCancelledErrorr   r!   messages     r"   
on_messagezEchoHandler.on_message@   su      	$$Wj%.H.HIIIIIII% 	 	 	DD# 	 	 	DD	s   +1 A	AAN)r.   r/   r0   r   	coroutiner=   r2   r$   r"   r4   r4   ?   s/        ]  ]  r$   r4   c                       e Zd Zd ZdS )ErrorInOnMessageHandlerc                     ddz   d S )N   r   r2   r;   s     r"   r=   z"ErrorInOnMessageHandler.on_messageK   s    	Ar$   Nr.   r/   r0   r=   r2   r$   r"   r@   r@   J   s#            r$   r@   c                       e Zd Zd ZdS )HeaderHandlerc                    t          j        | j        d          t          j        | j        d          t          j        | j        dd          t          j        | j        dd          t          j        | j        d          | j        | j        g}|D ]+}	  |             t          d          # t          $ r Y (w xY w|                     | j        j                            dd                     d S )	NzThis should not workzhttp://localhost/elsewhereX-Test 	ChocolateChipi  zdid not get expected exception)	functoolspartialwriteredirect
set_header
set_cookie
set_statusflushfinish	ExceptionRuntimeErrorr6   requestheadersget)r!   methods_to_testmethods      r"   openzHeaderHandler.openP   s    dj*@AAdm-IJJdox<<do{FCCdos33JK
 & 	 	F  @AAA   4</33HbAABBBBBs   B,,
B98B9Nr.   r/   r0   r[   r2   r$   r"   rE   rE   O   s(        C C C C Cr$   rE   c                       e Zd Zd Zd ZdS )HeaderEchoHandlerc                 2    |                      dd           d S )NX-Extra-Response-HeaderExtra-Response-Value)rO   r'   s    r"   set_default_headersz%HeaderEchoHandler.set_default_headersf   s    13IJJJJJr$   c                     | j         j                                        D ]B\  }}|                                                    d          r|                     ||           Cd S )Nzx-test)rV   rW   get_alllower
startswithrO   )r!   kvs      r"   preparezHeaderEchoHandler.preparei   sc    L(0022 	& 	&DAqwwyy##H-- &1%%%	& 	&r$   N)r.   r/   r0   rb   ri   r2   r$   r"   r^   r^   e   s5        K K K& & & & &r$   r^   c                       e Zd Zd ZdS )NonWebSocketHandlerc                 0    |                      d           d S )Nok)rM   r'   s    r"   rX   zNonWebSocketHandler.getp   s    

4r$   Nr.   r/   r0   rX   r2   r$   r"   rk   rk   o   s#            r$   rk   c                       e Zd Zd ZdS )RedirectHandlerc                 0    |                      d           d S )N/echo)rN   r'   s    r"   rX   zRedirectHandler.getu   s    gr$   Nrn   r2   r$   r"   rp   rp   t   s#            r$   rp   c                       e Zd Zd ZdS )CloseReasonHandlerc                 @    d| _         |                     dd           d S )NF  goodbye)on_close_calledcloser'   s    r"   r[   zCloseReasonHandler.openz   s$    $

4#####r$   Nr\   r2   r$   r"   rt   rt   y   #        $ $ $ $ $r$   rt   c                   4    e Zd Zej        d             Zd ZdS )AsyncPrepareHandlerc              #   &   K   t           j        V  d S r   )r   momentr'   s    r"   ri   zAsyncPrepareHandler.prepare   s      jr$   c                 0    |                      |           d S r   r6   r;   s     r"   r=   zAsyncPrepareHandler.on_message   s    7#####r$   N)r.   r/   r0   r   r>   ri   r=   r2   r$   r"   r|   r|      s>        ]  ]$ $ $ $ $r$   r|   c                       e Zd Zd ZdS )PathArgsHandlerc                 0    |                      |           d S r   r   )r!   args     r"   r[   zPathArgsHandler.open   s    3r$   Nr\   r2   r$   r"   r   r      #                 r$   r   c                   >     e Zd Z fdZej        d             Z xZS )CoroutineOnMessageHandlerc                 H     t                      j        di | d| _        d S Nr   r2   superr#   sleepingr!   kwargs	__class__s     r"   r#   z$CoroutineOnMessageHandler.initialize   +    $$V$$$r$   c              #      K   | j         dk    r|                     d           | xj         dz  c_         t          j        d          V  | xj         dz  c_         |                     |           d S Nr   z%another coroutine is already sleepingrB   {Gz?r   r6   r   sleepr;   s     r"   r=   z$CoroutineOnMessageHandler.on_message   sv      =1FGGGioo7#####r$   )r.   r/   r0   r#   r   r>   r=   __classcell__r   s   @r"   r   r      sU             	]$ $ ]$ $ $ $ $r$   r   c                       e Zd Zd ZdS )RenderMessageHandlerc                 Z    |                      |                     d|                     d S )Nmessage.html)r<   )r6   render_stringr;   s     r"   r=   zRenderMessageHandler.on_message   s/    4--ng-NNOOOOOr$   NrC   r2   r$   r"   r   r      s(        P P P P Pr$   r   c                   *     e Zd Z fdZd Zd Z xZS )SubprotocolHandlerc                 H     t                      j        di | d| _        d S NFr2   )r   r#   select_subprotocol_calledr   s     r"   r#   zSubprotocolHandler.initialize   s.    $$V$$$).&&&r$   c                 L    | j         rt          d          d| _         d|v rdS d S )Nzselect_subprotocol called twiceT	goodproto)r   rT   )r!   subprotocolss     r"   select_subprotocolz%SubprotocolHandler.select_subprotocol   s9    ) 	?=>>>)-&,&&;tr$   c                 l    | j         st          d          |                     d| j        z             d S )Nzselect_subprotocol not calledzsubprotocol=%s)r   rT   r6   selected_subprotocolr'   s    r"   r[   zSubprotocolHandler.open   s?    - 	=;<<<+d.GGHHHHHr$   )r.   r/   r0   r#   r   r[   r   r   s   @r"   r   r      s]        / / / / /  I I I I I I Ir$   r   c                   D     e Zd Z fdZej        d             Zd Z xZS )OpenCoroutineHandlerc                 V     t                      j        di | || _        d| _        d S r   )r   r#   testopen_finished)r!   r   r   r   s      r"   r#   zOpenCoroutineHandler.initialize   s5    $$V$$$	"r$   c              #      K   | j         j                                        V  t          j        d          V  d| _        d S )Nr   T)r   message_sentwaitr   r   r   r'   s    r"   r[   zOpenCoroutineHandler.open   sG      i$))+++++i!r$   c                 \    | j         st          d          |                     d           d S )Nz&on_message called before open finishedrm   )r   rT   r6   r;   s     r"   r=   zOpenCoroutineHandler.on_message   s7    ! 	FDEEE4     r$   )	r.   r/   r0   r#   r   r>   r[   r=   r   r   s   @r"   r   r      sd        # # # # #
 	]" " ]"
! ! ! ! ! ! !r$   r   c                       e Zd Zd ZdS )ErrorInOpenHandlerc                      t          d          )Nboom)rT   r'   s    r"   r[   zErrorInOpenHandler.open   s    r$   Nr\   r2   r$   r"   r   r      r   r$   r   c                       e Zd Zd ZdS )ErrorInAsyncOpenHandlerc                 X   K   t          j        d           d {V  t          d          )Nr   r   )r9   r   rT   r'   s    r"   r[   zErrorInAsyncOpenHandler.open   s6      mAr$   Nr\   r2   r$   r"   r   r      s#                 r$   r   c                       e Zd Zd ZdS )NoDelayHandlerc                 Z    |                      d           |                     d           d S )NThello)set_nodelayr6   r'   s    r"   r[   zNoDelayHandler.open   s0    7#####r$   Nr\   r2   r$   r"   r   r      rz   r$   r   c                   .    e Zd Zej        d             ZdS )WebSocketBaseTestCasec              +   z   K   t          d|                                 |fz  fi |V }t          j        |          )Nzws://127.0.0.1:%d%s)r   get_http_portr   Return)r!   pathr   wss       r"   
ws_connectz WebSocketBaseTestCase.ws_connect   sU      $!T%7%7%9%94$@@
 
DJ
 
 
 
 jnnr$   N)r.   r/   r0   r   r>   r   r2   r$   r"   r   r      s/        ]  ]  r$   r   c                       e Zd Zd Zd Z fdZd Zd Zd Ze	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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#e	d!             Z$e	d"             Z%e	d#             Z&e	d$             Z'e	d%             Z( xZ)S )&WebSocketTestc                 "   t                      | _        t          dt          t	          | j                  fdt
          fdt          fdt          t	          | j                  fdt          t	          | j                  fdt          t	          | j                  fdt          t	          | j                  fd	t          t	          | j                  fd
t          t	          | j                  fdt          t	          | j                  fdt          t	          | j                  fdt          t	          | j                  fdt           t	          | j        |           fdt"          fdt$          fdt&          fgt)          ddi                    S )Nrr   )r   /non_ws	/redirectz/headerz/header_echo/close_reason/error_in_on_message/async_preparez/path_args/(.*)
/coroutine/render/subprotocol/open_coroutine)r   r   /error_in_open/error_in_async_open/nodelayr   z<b>{{ message }}</b>)template_loader)r   r   r   r4   dictrk   rp   rE   r^   rt   r@   r|   r   r   r   r   r   r   r   r   r   r'   s    r"   get_appzWebSocketTest.get_app   s   "HH+t9J'K'K'KL/0o.M4T=N+O+O+OP"%d&7888 $&d&7888 ++d&7888 %'d&7888 &#d&7888 !-d&7888
 0$DDU2V2V2VW"&d&7888 &(d&7dCCC
 "#56')@A^,a1d '8N'OPPg4
 4
 4
 4	
r$   c                     t                      S r   r   r'   s    r"   get_http_clientzWebSocketTest.get_http_client  s    $&&&r$   c                     t                                                       t          j                                         d S r   )r   tearDownr   _template_loadersclear)r!   r   s    r"   r   zWebSocketTest.tearDown  s4    (..00000r$   c                 f    |                      d          }|                     |j        d           d S )Nrr     fetchassertEqualcoder!   responses     r"   test_http_requestzWebSocketTest.test_http_request!  s1    ::g&&,,,,,r$   c                 r    |                      ddddd          }|                     |j        d           d S )Nrr   Upgrade	WebSocket13
Connectionr   zSec-WebSocket-VersionrW   r   r   r   s     r"   test_missing_websocket_keyz(WebSocketTest.test_missing_websocket_key&  P    ::'&)-   
 
 	,,,,,r$   c                 r    |                      ddddd          }|                     |j        d           d S )Nrr   r   r   12r   r   i  r   r   s     r"   test_bad_websocket_versionz(WebSocketTest.test_bad_websocket_version1  r   r$   c              #      K   |                      d          V }|                    d          V  |                                V }|                     |d           d S )Nrr   r   r   r6   read_messager   r!   r   r   s      r"   test_websocket_genz WebSocketTest.test_websocket_gen<  sh      ??7++++w'''''****7+++++r$   c                 
    t          d                                 z   j                                                                                    }|                    d           |                     j                                                                                    }                     |d            j        	                     fd           |
                                                                   d S )Nws://127.0.0.1:%d/echo)callbackr   c                 ,                                     S r   )stop)fr!   s    r"   <lambda>z8WebSocketTest.test_websocket_callbacks.<locals>.<lambda>L  s    diikk r$   )r   r   r   r   resultr6   r   r   r   add_done_callbackry   r   s   `  r"   test_websocket_callbacksz&WebSocketTest.test_websocket_callbacksC  s    $t'9'9';';;di	
 	
 	
 	
 YY[[!!
!!!
	"""99;;%%''7+++++,A,A,A,ABBB



		r$   c              #      K   |                      d          V }|                    dd           |                                V }|                     |d           d S )Nrr   s   hello Tbinaryr   r   s      r"   test_binary_messagez!WebSocketTest.test_binary_messageP  sg      ??7++++
t444****=11111r$   c              #      K   |                      d          V }|                    d           |                                V }|                     |d           d S Nrr   u   hello ér   r   s      r"   test_unicode_messagez"WebSocketTest.test_unicode_messageW  sb      ??7++++
(((****>22222r$   c              #      K   |                      d          V }|                                 |                     t                    5  |                    d           d d d            d S # 1 swxY w Y   d S r  )r   ry   assertRaisesr   r6   r!   r   s     r"   )test_error_in_closed_client_write_messagez7WebSocketTest.test_error_in_closed_client_write_message^  s      ??7++++



344 	- 	-^,,,	- 	- 	- 	- 	- 	- 	- 	- 	- 	- 	- 	- 	- 	- 	- 	- 	- 	-s   A++A/2A/c              #      K   |                      d          V }|                    d           |                                V }|                     |d           d S )Nr   r   z<b>hello</b>r   r   s      r"   test_render_messagez!WebSocketTest.test_render_messagee  sb      ??9----
!!!****>22222r$   c              #     K   |                      d          V }|                    d           t          t          d          5  |                                V }d d d            n# 1 swxY w Y   |                     |d            d S )Nr   r   Uncaught exception)r   r6   r   r	   r   assertIsr   s      r"   test_error_in_on_messagez&WebSocketTest.test_error_in_on_messagel  s      ??#9::::
!!!w 455 	/ 	/__....H	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/h%%%%%s   A''A+.A+c              #      K   |                      t                    5 }|                     d          V  d d d            n# 1 swxY w Y   |                     |j        j        d           d S )Nz	/notfoundi  )r	  r   r   r   	exceptionr   )r!   cms     r"   test_websocket_http_failz&WebSocketTest.test_websocket_http_failt  s      y)) 	/R//+.....	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/*C00000s   AAAc              #      K   |                      t                    5  |                     d          V  d d d            d S # 1 swxY w Y   d S )Nr   )r	  r   r   r'   s    r"   test_websocket_http_successz)WebSocketTest.test_websocket_http_successz  s      ~.. 	- 	-//),,,,,	- 	- 	- 	- 	- 	- 	- 	- 	- 	- 	- 	- 	- 	- 	- 	- 	- 	-   AA	Ac              #      K   |                      t                    5  |                     d          V  d d d            d S # 1 swxY w Y   d S )Nr   )r	  r   r   r'   s    r"   test_websocket_http_redirectz*WebSocketTest.test_websocket_http_redirect  s      y)) 	/ 	///+.....	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/ 	/r  c              #   D  K   t                      \  }}|                                 |                     t                    5  t	          t
          dd          5  t          d|z  d          V  d d d            n# 1 swxY w Y   d d d            d S # 1 swxY w Y   d S )Nz.*F)requiredzws://127.0.0.1:%d/i  )connect_timeout)r   ry   r	  IOErrorr   r   r   )r!   sockports      r"   test_websocket_network_failz)WebSocketTest.test_websocket_network_fail  s/     %''
d

w'' 	 	7D5999  '(4/                   	 	 	 	 	 	 	 	 	 	 	 	 	 	 	 	 	 	s6   BA=1B=B	BB	BBBc              #      K   t          d|                                 z            V }|                    d           |                    d           |j                                         d S )Nr   r   world)r   r   r6   streamry   r
  s     r"   "test_websocket_close_buffered_dataz0WebSocketTest.test_websocket_close_buffered_data  sk      $%=@R@R@T@T%TUUUU
!!!
!!!
	r$   c              #      K   t          t          d|                                 z  ddi                    V }|                                V }|                     |d           d S )Nzws://127.0.0.1:%d/headerrG   r   r   )r   r   r   r   r   r   s      r"   test_websocket_headersz$WebSocketTest.test_websocket_headers  s       %*T-?-?-A-AA!7+  
 
 
 
 ****7+++++r$   c              #   0  K   t          t          d|                                 z  ddi                    V }|                     |j                            d          d           |                     |j                            d          d           d S )Nzws://127.0.0.1:%d/header_echozX-Test-Hellor   r   r`   ra   )r   r   r   r   rW   rX   r
  s     r"   test_websocket_header_echoz(WebSocketTest.test_websocket_header_echo  s      
 %/$2D2D2F2FF'1  
 
 
 
 	77AAAJNN4557M	
 	
 	
 	
 	
r$   c              #   @  K   |                      d          V }|                                V }|                     |d            |                     |j        d           |                     |j        d           | j        V \  }}|                     |d           d S )Nr   rv   rw   )r   r   r  r   r+   r,   r   )r!   r   msgr   reasons        r"   test_server_close_reasonz&WebSocketTest.test_server_close_reason  s      ???3333OO%%%%c4   ---)444!...f 	t$$$$$r$   c              #      K   |                      d          V }|                    dd           | j        V \  }}|                     |d           |                     |d           d S )Nrr   rv   rw   )r   ry   r   r   )r!   r   r   r,  s       r"   test_client_close_reasonz&WebSocketTest.test_client_close_reason  su      ??7++++
y!!!!...ft$$$+++++r$   c              #      K   |                      d          V }|                                V }|                     |d            |                     t                    5  |                    d           d d d            d S # 1 swxY w Y   d S )Nr   r   )r   r   r  r	  r   r6   )r!   r   r+  s      r"   test_write_after_closez$WebSocketTest.test_write_after_close  s      ???3333OO%%%%c4   344 	& 	&W%%%	& 	& 	& 	& 	& 	& 	& 	& 	& 	& 	& 	& 	& 	& 	& 	& 	& 	&s    BB
Bc              #      K   |                      d          V }|                    d           |                                V }|                     |d           d S )Nr   r   r   r!   r   ress      r"   test_async_preparez WebSocketTest.test_async_prepare  se       ??#34444
!!!OO%%%%g&&&&&r$   c              #      K   |                      d          V }|                                V }|                     |d           d S )Nz/path_args/hellor   r   r   r   r3  s      r"   test_path_argszWebSocketTest.test_path_args  sO      ??#56666OO%%%%g&&&&&r$   c              #   D  K   |                      d          V }|                    d          V  |                    d          V  |                                V }|                     |d           |                                V }|                     |d           d S )Nr   hello1hello2r   r3  s      r"   test_coroutinezWebSocketTest.test_coroutine  s      ??<0000x(((((x(((((OO%%%%h'''OO%%%%h'''''r$   c              #     K   |                                  }d|z  }dd|z  i}t          t          ||                    V }|                    d           |                                V }|                     |d           d S )Nr   Originzhttp://127.0.0.1:%dr   r   r   r   r   r6   r   r   r!   r   urlrW   r   r   s         r"   test_check_origin_valid_no_pathz-WebSocketTest.test_check_origin_valid_no_path  s      !!##&-2T9:$[g%F%F%FGGGG
!!!****7+++++r$   c              #     K   |                                  }d|z  }dd|z  i}t          t          ||                    V }|                    d           |                                V }|                     |d           d S )Nr   r>  zhttp://127.0.0.1:%d/somethingr   r   r?  r@  s         r"   !test_check_origin_valid_with_pathz/WebSocketTest.test_check_origin_valid_with_path  s      !!##&-<tCD$[g%F%F%FGGGG
!!!****7+++++r$   c              #   .  K   |                                  }d|z  }dd|z  i}|                     t                    5 }t          t	          ||                    V  d d d            n# 1 swxY w Y   |                     |j        j        d           d S )Nr   r>  z127.0.0.1:%dr     r   r	  r   r   r   r   r  r   r!   r   rA  rW   r  s        r"   %test_check_origin_invalid_partial_urlz3WebSocketTest.test_check_origin_invalid_partial_url  s      !!##&-^d23y)) 	GR#KW$E$E$EFFFFF	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	G*C00000s   !A**A.1A.c              #   (  K   |                                  }d|z  }ddi}|                     t                    5 }t          t	          ||                    V  d d d            n# 1 swxY w Y   |                     |j        j        d           d S )Nr   r>  zhttp://somewhereelse.comr   rF  rG  rH  s        r"   test_check_origin_invalidz'WebSocketTest.test_check_origin_invalid  s      !!##&- 78y)) 	GR#KW$E$E$EFFFFF	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	*C00000s   !A''A+.A+c              #     K   |                                  }t                                          d|          V }t          d |D                       }t          j        |vr|                     d           d S d|z  }ddi}|                     t                    5 }t          t          ||                    V  d d d            n# 1 swxY w Y   |                     |j        j        d           d S )	N	localhostc              3   &   K   | ]}|d          V  dS )r   Nr2   ).0addrs     r"   	<genexpr>zEWebSocketTest.test_check_origin_invalid_subdomains.<locals>.<genexpr>$  s&      444tAw444444r$   z"localhost does not resolve to ipv4zws://localhost:%d/echor>  zhttp://subtenant.localhostr   rF  )r   r
   resolvesetsocketAF_INETskipTestr	  r   r   r   r   r  r   )r!   r   addrinfofamiliesrA  rW   r  s          r"   $test_check_origin_invalid_subdomainsz2WebSocketTest.test_check_origin_invalid_subdomains  sJ     !!##
 "++K>>>>44844444>))MM>???F&- 9:y)) 	GR#KW$E$E$EFFFFF	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	G 	*C00000s   !C		CCc              #      K   |                      dddg          V }|                     |j        d           |                                V }|                     |d           d S )Nr   badprotor   )r   zsubprotocol=goodproto)r   r   r   r   r3  s      r"   test_subprotocolszWebSocketTest.test_subprotocols3  s      ??*k)B # 
 
 
 
 	0+>>>OO%%%%566666r$   c              #      K   |                      d          V }|                     |j        d            |                                V }|                     |d           d S )Nr   zsubprotocol=None)r   r  r   r   r   r3  s      r"   test_subprotocols_not_offeredz+WebSocketTest.test_subprotocols_not_offered<  sf      ??>2222b-t444OO%%%%011111r$   c              #     K   t                      | _        |                     d          V }|                    d          V  | j                                         |                                V }|                     |d           d S )Nr   r   rm   )r   r   r   r6   rS  r   r   r3  s      r"   test_open_coroutinez!WebSocketTest.test_open_coroutineC  s      !GG??#45555w'''''OO%%%%d#####r$   c              #      K   t          t          d          5  |                     d          V }|                                V }d d d            n# 1 swxY w Y   |                     |           d S )Nr  r   r   r	   r   r   assertIsNoner3  s      r"   test_error_in_openz WebSocketTest.test_error_in_openL  s      w 455 	* 	*'78888B))))C	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	#   .AAAc              #      K   t          t          d          5  |                     d          V }|                                V }d d d            n# 1 swxY w Y   |                     |           d S )Nr  r   rb  r3  s      r"   test_error_in_async_openz&WebSocketTest.test_error_in_async_openS  s      w 455 	* 	*'=>>>>B))))C	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	* 	#re  c              #      K   |                      d          V }|                                V }|                     |d           d S )Nr   r   r7  r3  s      r"   test_nodelayzWebSocketTest.test_nodelayZ  sN      ??:....OO%%%%g&&&&&r$   )*r.   r/   r0   r   r   r   r   r   r   r   r   r   r  r  r  r  r  r  r  r  r!  r%  r'  r)  r-  r/  r1  r5  r8  r<  rB  rD  rI  rK  rY  r\  r^  r`  rd  rg  ri  r   r   s   @r"   r   r      s       6
 6
 6
p' ' '1 1 1 1 1- - -
	- 	- 	-	- 	- 	- , , X,   2 2 X2 3 3 X3 - - X- 3 3 X3 & & X& 1 1 X1
 - - X- / / X/   X   X 	, 	, X	, 
 
 X
 % % X% , , X, & & X& ' ' X' ' ' X'
 ( ( X( 	, 	, X	, 	, 	, X	, 1 1 X1 1 1 X1 1 1 X1, 7 7 X7 2 2 X2 $ $ X$   X   X ' ' X' ' ' ' 'r$   r   c                   $     e Zd Z fdZd Z xZS )NativeCoroutineOnMessageHandlerc                 H     t                      j        di | d| _        d S r   r   r   s     r"   r#   z*NativeCoroutineOnMessageHandler.initializeb  r   r$   c                    K   | j         dk    r|                     d           | xj         dz  c_         t          j        d           d {V  | xj         dz  c_         |                     |           d S r   r   r;   s     r"   r=   z*NativeCoroutineOnMessageHandler.on_messagef  s      =1FGGGioo7#####r$   )r.   r/   r0   r#   r=   r   r   s   @r"   rk  rk  a  sG            $ $ $ $ $ $ $r$   rk  c                   *    e Zd Zd Zed             ZdS )WebSocketNativeCoroutineTestc                 0    t          dt          fg          S )N/native)r   rk  r'   s    r"   r   z$WebSocketNativeCoroutineTest.get_appp  s    Y(GHIJJJr$   c              #   D  K   |                      d          V }|                    d          V  |                    d          V  |                                V }|                     |d           |                                V }|                     |d           d S )Nrq  r:  r;  r   r3  s      r"   test_native_coroutinez2WebSocketNativeCoroutineTest.test_native_coroutines  s      ??9----x(((((x(((((OO%%%%h'''OO%%%%h'''''r$   N)r.   r/   r0   r   r   rs  r2   r$   r"   ro  ro  o  sA        K K K ( ( X( ( (r$   ro  c                       e Zd ZdZd Zd Zd Zdededdfd	Ze	d
e
j        fd            Ze	d
e
j        fd            ZdS )CompressionTestMixinzHello world. Testing 123 123c           	           G d dt                     }t          dt          t          |                                           fd|t          |                                           fg          S )Nc                   *    e Zd Zed             Zd ZdS )4CompressionTestMixin.get_app.<locals>.LimitedHandlerc                     dS )N   r2   r'   s    r"   max_message_sizezECompressionTestMixin.get_app.<locals>.LimitedHandler.max_message_size  s    tr$   c                 d    |                      t          t          |                               d S r   )r6   strlenr;   s     r"   r=   z?CompressionTestMixin.get_app.<locals>.LimitedHandler.on_message  s*    ""3s7||#4#455555r$   N)r.   r/   r0   propertyr{  r=   r2   r$   r"   LimitedHandlerrx    s<          X6 6 6 6 6r$   r  rr   r&   /limited)r   r   r4   r   get_server_compression_options)r!   r  s     r"   r   zCompressionTestMixin.get_app  s    	6 	6 	6 	6 	61 	6 	6 	6  T-P-P-R-RSSS "T-P-P-R-RSSS
 
 	
r$   c                     d S r   r2   r'   s    r"   r  z3CompressionTestMixin.get_server_compression_options      tr$   c                     d S r   r2   r'   s    r"   get_client_compression_optionsz3CompressionTestMixin.get_client_compression_options  r  r$   bytes_in	bytes_outreturnNc                     t                      r   NotImplementedErrorr!   r  r  s      r"   verify_wire_bytesz&CompressionTestMixin.verify_wire_bytes      !###r$   r!   c              #   B  K   |                      d|                                           V }t          d          D ]M}|                    | j                   |                                V }|                     || j                   N|                     |j        j        t          | j                  dz             |                     |j        j
        t          | j                  dz             |                     |j        j        |j        j                   d S )Nrr   r&      )r   r  ranger6   MESSAGEr   r   protocol_message_bytes_outr~  _message_bytes_inr  _wire_bytes_in_wire_bytes_outr!   r   ir   s       r"   test_message_sizesz'CompressionTestMixin.test_message_sizes  s     ??)L)L)N)N # 
 
 
 

 q 	5 	5AT\***__....HXt|44447T\9J9JQ9NOOO6DL8I8IA8MNNNr{92;;VWWWWWr$   c              #   b  K   |                      d|                                           V }|                    d           |                                V }|                     |d           |                    d           |                                V }|                     |           d S )Nr  r&   ڀaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa128   aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa)r   r  r6   r   r   rc  r   s      r"   test_size_limitz$CompressionTestMixin.test_size_limit  s      ??D,O,O,Q,Q # 
 
 
 
 	###****5))) 	$$$****(#####r$   )r.   r/   r0   r  r   r  r  intr  r   typingAnyr  r  r2   r$   r"   ru  ru    s        ,G
 
 
0    $# $# $$ $ $ $ $ X X X X XX $fj $ $ $ X$ $ $r$   ru  c                   (    e Zd ZdZdej        fdZdS )UncompressedTestMixinzESpecialization of CompressionTestMixin when we expect no compression.r!   c                     |                      |dt          | j                  dz   z             |                      |dt          | j                  dz   z             d S )Nr        )r   r~  r  r  s      r"   r  z'UncompressedTestMixin.verify_wire_bytes  s\    AT\):):Q)>$?@@@1DL(9(9A(=#>?????r$   N)r.   r/   r0   r1   r  r  r  r2   r$   r"   r  r    s>        OO@
 @ @ @ @ @ @r$   r  c                       e Zd ZdS )NoCompressionTestN)r.   r/   r0   r2   r$   r"   r  r    s        Dr$   r  c                       e Zd Zd ZdS )ServerOnlyCompressionTestc                     i S r   r2   r'   s    r"   r  z8ServerOnlyCompressionTest.get_server_compression_options      	r$   N)r.   r/   r0   r  r2   r$   r"   r  r    #            r$   r  c                       e Zd Zd ZdS )ClientOnlyCompressionTestc                     i S r   r2   r'   s    r"   r  z8ClientOnlyCompressionTest.get_client_compression_options  r  r$   N)r.   r/   r0   r  r2   r$   r"   r  r    r  r$   r  c                        e Zd Zd Zd Zd ZdS )DefaultCompressionTestc                     i S r   r2   r'   s    r"   r  z5DefaultCompressionTest.get_server_compression_options  r  r$   c                     i S r   r2   r'   s    r"   r  z5DefaultCompressionTest.get_client_compression_options  r  r$   c                     |                      |dt          | j                  dz   z             |                      |dt          | j                  dz   z             |                     ||dz              d S )Nr  r  r     )
assertLessr~  r  r   r  s      r"   r  z(DefaultCompressionTest.verify_wire_bytes  sr    	1DL(9(9A(=#>???!s4<'8'81'<"=>>>HrM22222r$   N)r.   r/   r0   r  r  r  r2   r$   r"   r  r    sA            3 3 3 3 3r$   r  c                   8    e Zd ZdededefdZdej        fdZdS )MaskFunctionMixinmaskdatar  c                     t                      r   r  r!   r  r  s      r"   r  zMaskFunctionMixin.mask  r  r$   r!   c                    |                      |                     dd          d           |                      |                     dd          d           |                      |                     dd          d           |                      |                     dd          d	           |                      |                     d
d          d           |                      |                     dd          d           d S )Ns   abcdr$      b   s   54321s   TVPVPs   ZXCVs   98765432s   c`t`olpds    s   s   s   s    s   )r   r  r'   s    r"   	test_maskzMaskFunctionMixin.test_mask  s    7C00#6667D117;;;7H55x@@@7K88+FFF 	II)+FGG'	
 	
 	
 	II)+FGG'	
 	
 	
 	
 	
r$   N)r.   r/   r0   r8   r  r  r  r  r2   r$   r"   r  r    sZ        $ $e $ $ $ $ $

 
 
 
 
 
 
r$   r  c                       e Zd Zd ZdS )PythonMaskFunctionTestc                 "    t          ||          S r   r   r  s      r"   r  zPythonMaskFunctionTest.mask   s    %dD111r$   Nr.   r/   r0   r  r2   r$   r"   r  r    s#        2 2 2 2 2r$   r  z#tornado.speedups module not presentc                       e Zd Zd ZdS )CythonMaskFunctionTestc                 ,    t          j        ||          S r   )r   websocket_maskr  s      r"   r  zCythonMaskFunctionTest.mask  s    &tT222r$   Nr  r2   r$   r"   r  r    s#        3 3 3 3 3r$   r  c                   *    e Zd Zd Zed             ZdS )ServerPeriodicPingTestc                 P     G d dt                     }t          d|fgd          S )Nc                       e Zd Zd ZdS )3ServerPeriodicPingTest.get_app.<locals>.PingHandlerc                 0    |                      d           d S )Ngot pongr   r!   r  s     r"   on_pongz;ServerPeriodicPingTest.get_app.<locals>.PingHandler.on_pong      "":.....r$   N)r.   r/   r0   r  r2   r$   r"   PingHandlerr    #        / / / / /r$   r  /r   )websocket_ping_intervalr   r   r!   r  s     r"   r   zServerPeriodicPingTest.get_app  sJ    	/ 	/ 	/ 	/ 	/. 	/ 	/ 	/ S+./NNNNr$   c              #      K   |                      d          V }t          d          D ].}|                                V }|                     |d           /d S )Nr  r  r  )r   r  r   r   r  s       r"   test_server_pingz'ServerPeriodicPingTest.test_server_ping  sj      ??3''''q 	3 	3A__....HXz2222	3 	3r$   N)r.   r/   r0   r   r   r  r2   r$   r"   r  r  
  sA        O O O 3 3 X3 3 3r$   r  c                   *    e Zd Zd Zed             ZdS )ClientPeriodicPingTestc                 L     G d dt                     }t          d|fg          S )Nc                       e Zd Zd ZdS )3ClientPeriodicPingTest.get_app.<locals>.PingHandlerc                 0    |                      d           d S )Ngot pingr   r  s     r"   on_pingz;ClientPeriodicPingTest.get_app.<locals>.PingHandler.on_ping  r  r$   Nr.   r/   r0   r  r2   r$   r"   r  r    r  r$   r  r  r  r  s     r"   r   zClientPeriodicPingTest.get_app  sE    	/ 	/ 	/ 	/ 	/. 	/ 	/ 	/ S+./000r$   c              #      K   |                      dd          V }t          d          D ].}|                                V }|                     |d           /|                                 d S )Nr  r   )ping_intervalr  r  )r   r  r   r   ry   r  s       r"   test_client_pingz'ClientPeriodicPingTest.test_client_ping#  su      ??3d?;;;;q 	3 	3A__....HXz2222





r$   N)r.   r/   r0   r   r   r  r2   r$   r"   r  r    s>        1 1 1   X  r$   r  c                   *    e Zd Zd Zed             ZdS )ManualPingTestc                 L     G d dt                     }t          d|fg          S )Nc                       e Zd Zd ZdS )+ManualPingTest.get_app.<locals>.PingHandlerc                 Z    |                      |t          |t                               d S )Nr  )r6   r7   r8   r  s     r"   r  z3ManualPingTest.get_app.<locals>.PingHandler.on_ping0  s+    ""4
40G0G"HHHHHr$   Nr  r2   r$   r"   r  r  /  s(        I I I I Ir$   r  r  r  r  s     r"   r   zManualPingTest.get_app.  sM    	I 	I 	I 	I 	I. 	I 	I 	I S+./000r$   c              #   ~  K   |                      d          V }|                     t          |j        d           |                    d           |                                V }|                     |d           |                    d           |                                V }|                     |d           d S )Nr  ~aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaar   s   hellos   binary hello)r   r	  
ValueErrorpingr   r   )r!   r   resps      r"   test_manual_pingzManualPingTest.test_manual_ping5  s      ??3''''*bgy999
__&&&&x(((
   __&&&&/////r$   N)r.   r/   r0   r   r   r  r2   r$   r"   r  r  -  s>        1 1 1 0 0 X0 0 0r$   r  c                   *    e Zd Zd Zed             ZdS )MaxMessageSizeTestc                 4    t          dt          fgd          S )Nr  rz  )websocket_max_message_size)r   r4   r'   s    r"   r   zMaxMessageSizeTest.get_appF  s    S+./DQQQQr$   c              #     K   |                      d          V }d}|                    |           |                                V }|                     ||           |                    |dz              |                                V }|                     |d            |                     |j        d           |                     |j        d           d S )Nr     aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaabi  zmessage too big)r   r6   r   r   r  r+   r,   )r!   r   r+  r  s       r"   test_large_messagez%MaxMessageSizeTest.test_large_messageI  s      ??3'''' 
__&&&&s### 	s###__&&&&dD!!!---*;<<<<<r$   N)r.   r/   r0   r   r   r  r2   r$   r"   r  r  E  sA        R R R = = X= = =r$   r  )Or9   rK   rT  	tracebackr  unittesttornado.concurrentr   tornador   tornado.httpclientr   r   tornado.locksr   tornado.logr   r	   tornado.netutilr
   tornado.simple_httpclientr   tornado.templater   tornado.testingr   r   r   r   tornado.webr   r   tornado.websockettornado.utilr   ImportError	print_excr   r   r   r   r   r   r4   r@   rE   r^   rk   rp   rt   r|   r   r   r   r   r   r   r   r   r   r   rk  ro  objectru  r  r  r  r  r  r  TestCaser  skipIfr  r  r  r  r  r2   r$   r"   <module>r     s               % % % % % %       5 5 5 5 5 5 5 5       ( ( ( ( ( ( ( ( $ $ $ $ $ $ ; ; ; ; ; ; ' ' ' ' ' ' T T T T T T T T T T T T 3 3 3 3 3 3 3 3	
3333333 
 
 

 I	
                     HHHO O O O O+ O O O(    &       2   
C C C C C( C C C,& & & & &, & & &    .   
    n   
$ $ $ $ $- $ $ $$ $ $ $ $. $ $ $         *      
$ $ $ $ $ 4 $ $ $P P P P P/ P P P
I I I I I- I I I&! ! ! ! !/ ! ! !$         -      
         2      $ $ $ $ $) $ $ $    -   ~' ~' ~' ~' ~') ~' ~' ~'B$ $ $ $ $&: $ $ $( ( ( ( (#8 ( ( ( @$ @$ @$ @$ @$6 @$ @$ @$F@ @ @ @ @0 @ @ @	 	 	 	 	-/D 	 	 	
     57L   
     57L   
3 3 3 3 313H 3 3 3
 
 
 
 
 
 
 
.2 2 2 2 2.0A 2 2 2
 T!#HII3 3 3 3 3.0A 3 3 JI3
3 3 3 3 32 3 3 3"    2   $0 0 0 0 0* 0 0 00= = = = =. = = = = =s   "
A- -BB B$#B$