
    5              
       V   d Z ddlZddlZddlZddlZddl ddlmZ ddlm	Z	 	 ej                  rddlZndZ	 es	ddlmZ d Zg d
ZdZdZdZdZdZdZdZdZdZdZdZdZdZeeeeeeeeeef
Z G d de      Z  G d de      Z! G d de      Z"y# e$ r dZY aw xY w# e$ r d	 ZY cw xY w)aL  
websocket - WebSocket client library for Python

Copyright (C) 2010 Hiroki Ohtani(liris)

    This library is free software; you can redistribute it and/or
    modify it under the terms of the GNU Lesser General Public
    License as published by the Free Software Foundation; either
    version 2.1 of the License, or (at your option) any later version.

    This library is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
    Lesser General Public License for more details.

    You should have received a copy of the GNU Lesser General Public
    License along with this library; if not, write to the Free Software
    Foundation, Inc., 51 Franklin Street, Fifth Floor,
    Boston, MA  02110-1335  USA

    N   )*)validate_utf8)Lock)XorMaskerSimplec                 6    t        |       j                  |      S N)r   process)_m_ds     "lib/third_party/websocket/_abnf.py_maskr   -   s    "2&..r22    c                     t        t        |            D ]  }||xx   | |dz     z  cc<    t        j                  r|j	                         S |j                         S )N   )rangelensixPY3tobytestostring)r   r   is      r   r   r   1   sK    s2wAqERAYE   77::<;;= r   )ABNFcontinuous_frameframe_bufferSTATUS_NORMALSTATUS_GOING_AWAYSTATUS_PROTOCOL_ERRORSTATUS_UNSUPPORTED_DATA_TYPESTATUS_STATUS_NOT_AVAILABLESTATUS_ABNORMAL_CLOSEDSTATUS_INVALID_PAYLOADSTATUS_POLICY_VIOLATIONSTATUS_MESSAGE_TOO_BIGSTATUS_INVALID_EXTENSIONSTATUS_UNEXPECTED_CONDITIONSTATUS_BAD_GATEWAYSTATUS_TLS_HANDSHAKE_ERRORi  i  i  i  i  i  i  i  i  i  i  i  i  c                       e Zd ZdZdZdZdZdZdZdZ	eeeeee	fZ
eded	ed
edede	diZdZdZdZddddeddfdZddZed        Zd Zedd       Zd Zd Zed        Zy)r   z}
    ABNF frame class.
    see http://tools.ietf.org/html/rfc5234
    and http://tools.ietf.org/html/rfc6455#section-5.2
    r   r         	   
   conttextbinaryclosepingpong~   i   l             c                     || _         || _        || _        || _        || _        || _        |d}|| _        t        j                  | _	        y)zO
        Constructor for ABNF.
        please check RFC for arguments.
        Nr5   )
finrsv1rsv2rsv3opcodemaskdataosurandomget_mask_key)selfr7   r8   r9   r:   r;   r<   r=   s           r   __init__zABNF.__init__   sK     				<D	JJr   c                    | j                   s| j                  s| j                  rt        d      | j                  t
        j                  vrt        d| j                        | j                  t
        j                  k(  r| j                  st        d      | j                  t
        j                  k(  rt        | j                        }|sy|dk(  s|dk\  rt        d      |dkD  r%|s#t        | j                  dd       st        d      d	t        j                  | j                  d
d       z  t        j                  | j                  dd       z   }| j                  |      st        d      yy)z^
        validate the ABNF frame.
        skip_utf8_validation: skip utf8 validation.
        zrsv is not implemented, yetzInvalid opcode %rzInvalid ping frame.Nr   r4   zInvalid close frame.r*      r   zInvalid close opcode.)r8   r9   r:   WebSocketProtocolExceptionr;   r   OPCODESOPCODE_PINGr7   OPCODE_CLOSEr   r=   r   r   byte2int_is_valid_close_status)rA   skip_utf8_validationlcodes       r   validatezABNF.validate   s0   
 99		TYY,-JKK;;dll*,-@$++NN;;$***488,-BCC;;$+++DIIAAvc01GHH1u1-		RSRT:V01GHHTYYq^,-/2||DIIaN/KLD..t401HII 5 ,r   c                 6    | t         v xs d| cxk  xr dk  S c S )Ni  i  )VALID_CLOSE_STATUS)rM   s    r   rJ   zABNF._is_valid_close_status   s#    ))Bdd.AT.AB.ABr   c                     dt        | j                        z   dz   t        | j                        z   dz   t        | j                        z   S )Nzfin=z opcode=z data=)strr7   r;   r=   rA   s    r   __str__zABNF.__str__   sH    DHH%t{{+,TYY( 	(r   c           	          |t         j                  k(  r+t        | t        j                        r| j                  d      } t        |ddd|d|       S )a  
        create frame to send text, binary and other data.

        data: data to send. This is string value(byte array).
            if opcode is OPCODE_TEXT and this value is unicode,
            data value is converted into unicode string, automatically.

        opcode: operation code. please see OPCODE_XXX.

        fin: fin flag. if set to 0, create continue fragmentation.
        utf-8r   r   )r   OPCODE_TEXT
isinstancer   	text_typeencode)r=   r;   r7   s      r   create_framezABNF.create_frame   sD     T%%%*T3==*I;;w'DCAq&!T22r   c                 X   t        d | j                  | j                  | j                  | j                  fD              rt        d      | j                  t        j                  vrt        d      t        | j                        }|t        j                  k\  rt        d      t        | j                  dz  | j                  dz  z  | j                  dz  z  | j                  dz  z  | j                  z        }|t        j                  k  r4|t        | j                  dz  |z        z  }t        j                   |      }n|t        j"                  k  rM|t        | j                  dz  d	z        z  }t        j                   |      }|t%        j&                  d
|      z  }nL|t        | j                  dz  dz        z  }t        j                   |      }|t%        j&                  d|      z  }| j                  s|| j                  z   S | j)                  d      }|| j+                  |      z   S )zR
        format this object to string(byte array) to send data to server.
        c              3   $   K   | ]  }|d v 
 yw))r   r   N .0xs     r   	<genexpr>zABNF.format.<locals>.<genexpr>   s     T(S1q(Ss   z
not 0 or 1zInvalid OPCODEzdata is too long         r   r4   !H   !Q)anyr7   r8   r9   r:   
ValueErrorr;   r   rF   r   r=   	LENGTH_63chrLENGTH_7r<   r   b	LENGTH_16structpackr@   _get_masked)rA   lengthframe_headermask_keys       r   formatzABNF.format   s    T499dii(STT\**;;dll*-..TYYT^^#/00488q=!YY!^,.2ii1n=?CyyA~N![[) * DMM!C		Q 788L55.Ldnn$C		Q 566L55.LFKKf55LC		Q 566L55.LFKKf55Lyy$))++((+H$"2"28"<<<r   c                     t         j                  || j                        }t        |t        j
                        r|j                  d      }||z   S )NrV   )r   r<   r=   rX   r   rY   rZ   )rA   ru   ss      r   rr   zABNF._get_masked   s<    IIh		*h.w/H!|r   c                    |d}t        | t        j                        rt        j                  |       } t        |t        j                        rt        j                  |      }t        rt        |      }| d   dz  | d   dz  z  | d   dz  z  | d	   z  }|t        d
dt        |      dz  z
  z  d      z  }t	        j                  |d      }t	        j                  ||g      j                  d      }t        |      |kD  r|j                         d| S |j                         S t        j                  d|       }t        j                  d|      }t        ||      S )z
        mask or unmask data. Just do xor for each byte

        mask_key: 4 byte string(byte).

        data: data to mask/unmask.
        Nr5         r*      r   r+   r    r   zus-asciiuint32)dtypeB)rX   r   rY   rn   numpyr   bytes
frombufferbitwise_xorastyper   arrayr   )ru   r=   origlen	_mask_keyamaskedr   r   s           r   r<   z	ABNF.mask   s5    <Dh.uuXHdCMM*55;D$iG r)HQK2,==q@PPS[\]S^^I E#c$i!m!45zBBD  X6A&&q9+6==hGF4y7"^^%hw//>>##S(+BS$'BR= r   N)F)r   )__name__
__module____qualname____doc__OPCODE_CONTrW   OPCODE_BINARYrH   rG   OPCODE_PONGrF   
OPCODE_MAPrm   ro   rk   rB   rN   staticmethodrJ   rT   r[   rv   rr   r<   r^   r   r   r   r   i   s     KKMLKK KK)G
 	VVxgVVJ HII111#!"'"J8 C C(
 3 3"=B ! !r   r   c                   V    e Zd ZdZdZd Zd Zd Zd Zd Z	d Z
d	 Zd
 Zd Zd Zd Zy)r   re   rd   c                 l    || _         || _        g | _        | j                          t	               | _        y r	   )recvrK   recv_bufferclearr   lock)rA   recv_fnrK   s      r   rB   zframe_buffer.__init__#  s-    	$8! 

F	r   c                 .    d | _         d | _        d | _        y r	   )headerrs   r<   rS   s    r   r   zframe_buffer.clear,  s    	r   c                     | j                   d u S r	   )r   rS   s    r   has_received_headerz frame_buffer.has_received_header1      {{d""r   c                 &   | j                  d      }|d   }t        j                  rt        |      }|dz	  dz  }|dz	  dz  }|dz	  dz  }|dz	  dz  }|dz  }|d   }t        j                  rt        |      }|dz	  dz  }	|d	z  }
||||||	|
f| _        y )
Nr*   r   rc   r   rd   re   r      rg   )recv_strictr   PY2ordr   )rA   r   b1r7   r8   r9   r:   r;   b2has_masklength_bitss              r   recv_headerzframe_buffer.recv_header4  s    !!!$AY77RBAgkQw{Qw{Qw{cAY77RB7Q;4iD$fhLr   c                 V    | j                   sy| j                   t        j                     S )NF)r   r   _HEADER_MASK_INDEXrS   s    r   r   zframe_buffer.has_maskJ  s!    {{{{<::;;r   c                     | j                   d u S r	   )rs   rS   s    r   has_received_lengthz frame_buffer.has_received_lengthO  r   r   c                 *   | j                   t        j                     }|dz  }|dk(  r0| j                  d      }t	        j
                  d|      d   | _        y |dk(  r0| j                  d      }t	        j
                  d|      d   | _        y || _        y )Nrg   r4   r*   rf   r   r+   rh   )r   r   _HEADER_LENGTH_INDEXr   rp   unpackrs   )rA   bitsr   vs       r   recv_lengthzframe_buffer.recv_lengthR  s    {{<<<=Tk$  #A --a03DKD   #A --a03DK%DKr   c                     | j                   d u S r	   )r<   rS   s    r   has_received_maskzframe_buffer.has_received_mask^  s    yyD  r   c                 `    | j                         r| j                  d      | _        y d| _        y )Nr   r5   )r   r   r<   rS   s    r   	recv_maskzframe_buffer.recv_maska  s"    +/==?D$$Q'		r   c           
      ,   | j                   5  | j                         r| j                          | j                  \  }}}}}}}| j	                         r| j                          | j                  }| j                         r| j                          | j                  }	| j                  |      }
|rt        j                  |	|
      }
| j                          t        |||||||
      }|j                  | j                         d d d        |S # 1 sw Y   S xY wr	   )r   r   r   r   r   r   rs   r   r   r<   r   r   r   rN   rK   )rA   r7   r8   r9   r:   r;   r   _rs   r<   payloadframes               r   
recv_framezframe_buffer.recv_framed  s    YY'')  ";?;;8S$dFHa '')  "[[F %%' 99D &&v.G))D'2 JJLdD$'JENN44453 6 7 6 s   C2D		Dc                 v   |t        d | j                  D              z
  }|dkD  rJ| j                  t        d|            }| j                  j	                  |       |t        |      z  }|dkD  rJt        j                  d      j                  | j                        }|dk(  r	g | _        |S ||d  g| _        |d | S )Nc              3   2   K   | ]  }t        |        y wr	   )r   r_   s     r   rb   z+frame_buffer.recv_strict.<locals>.<genexpr>  s      B1AAQ1As   r   i @  r5   )	sumr   r   minappendr   r   rn   join)rA   bufsizeshortagebytes_unifieds        r   r   zframe_buffer.recv_strict  s    S B1A1A BBBl YYs5(34F##F+F#H l %%)..!1!12q=!DN ' 12D8G$$r   N)r   r   r   r   r   rB   r   r   r   r   r   r   r   r   r   r   r^   r   r   r   r     sG    
#M,<
#
&!C>%r   r   c                   *    e Zd Zd Zd Zd Zd Zd Zy)r   c                 <    || _         || _        d | _        d | _        y r	   )fire_cont_framerK   	cont_datarecving_frames)rA   r   rK   s      r   rB   zcontinuous_frame.__init__  s!    .$8!"r   c                     | j                   s(|j                  t        j                  k(  rt	        d      | j                   r8|j                  t        j
                  t        j                  fv rt	        d      y y )NzIllegal frame)r   r;   r   r   rE   rW   r   rA   r   s     r   rN   zcontinuous_frame.validate  sc    ""u||t7G7G'G,_==!1!143E3E FF,_== G r   c                 <   | j                   r"| j                   dxx   |j                  z  cc<   nZ|j                  t        j                  t        j
                  fv r|j                  | _        |j                  |j                  g| _         |j                  rd | _        y y )Nr   )r   r=   r;   r   rW   r   r   r7   r   s     r   addzcontinuous_frame.add  sr    >>NN1+|| 0 0$2D2DEE&+ll##llEJJ7DN99"&D r   c                 6    |j                   xs | j                  S r	   )r7   r   r   s     r   is_firezcontinuous_frame.is_fire  s    yy0D000r   c                    | j                   }d | _         |d   |_        | j                  sX|d   t        j                  k(  rB| j
                  s6t        |j                        s!t        dt        |j                        z         |d   |gS )Nr   r   zcannot decode: )	r   r=   r   r   rW   rK   r   WebSocketPayloadExceptionrepr)rA   r   r=   s      r   extractzcontinuous_frame.extract  s    ~~!W
##Q43C3C(CDLeLen{  }B  }G  }G  oH+!D$446 6 Qr   N)r   r   r   rB   rN   r   r   r   r^   r   r   r   r     s    #>	'1 r   r   )#r   r   r>   rp   r   _exceptions_utilsr   	threadingr   r   r   ImportErrorwsaccel.xormaskr   r   __all__r   r   r   r   r    r!   r"   r#   r$   r%   r&   r'   r(   rP   objectr   r   r   r^   r   r   <module>r      s  *  	  
  ! 
ww!3	3$   # "      "  !    s!6 s!lx%6 x%v% v % k  E  	!!	!s"   B B BBB('B(