o
    àý°jD¡  ã                   @   s  d dl Z d dlZd dlZd dlmZ d dlZd dl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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!m"Z"m#Z# d dl$m%Z%m&Z&m'Z'm(Z(m)Z) d d	l*m+Z+m,Z,m-Z-m.Z. zd dl/Z/d d
l/m0Z0m1Z1 W n	   e 2d¡ ‚ g d¢Z3dZ4dZ5de4e5f Z6dZ7de6e7f Z8dZ9de6 Z:e  ;d¡Z<e  ;de8 e j=¡Z>e  ;de8e9e:f e j=¡Z?e  ;de9e:f e j=¡Z@d ZAdZBdZCdZDG dd„ dƒZEG dd„ deFƒZGG dd „ d eHƒZIG d!d"„ d"eHƒZJG d#d$„ d$eJƒZKdS )%é    N)Ú	unhexlify)ÚencoderÚdecoder)ÚSubstrateUnderrunError)ÚnoValue)ÚLOG)ÚFilterÚControlÚSimplePagedResultsControlÚ
ResultCodeÚScopeÚDerefAliasesÚ	OperationÚKNOWN_CONTROLSÚCONTROL_PAGEDRESULTSÚNOTIFICATION_DISCONNECTÚKNOWN_NOTIFICATIONSÚBindRequestÚSearchRequestÚSearchResultDoneÚLDAPMessageÚ
AddRequestÚModifyRequestÚModifyDNRequestÚ
DelRequest)ÚgetNTLMSSPType1ÚgetNTLMSSPType3ÚVERSIONÚhmac_md5ÚNTLMAuthChallenge)ÚSPNEGO_NegTokenInitÚSPNEGO_NegTokenRespÚSPNEGOCipherÚ	TypesMech)ÚSSLÚcryptoz*pyOpenSSL is not installed, can't continue)ÚLDAPConnectionÚLDAPFilterSyntaxErrorÚLDAPFilterInvalidExceptionÚLDAPSessionErrorÚLDAPSearchErrorr	   r
   r   r   r   r   r   r   r   r   z(?:[a-z][a-z0-9\-]*)z)(?:(?:\d|[1-9]\d+)(?:\.(?:\d|[1-9]\d+))*)z	(?:%s|%s)z(?:(?:;[a-z0-9\-]+)*)z(%s%s)z(:dn)z	(?::(%s))z
([:<>~]?=)z^%s$z
^%s%s?%s?$z^(){0}%s?%s$é   é   é   c                   @   sä   e Zd Zd4dd„Z		d5dd„Zd6d	d
„Zdd„ Zdd„ Z		d7dd„Zdd„ Z	d8dd„Z
d9dd„Zd:dd„Zd9dd„Zdd„ Zd9d d!„Zd"d#„ Zd$d%„ Zd9d&d'„Zd(d)„ Zd*d+„ Zd,d-„ Zed.d/„ ƒZed0d1„ ƒZed2d3„ ƒZdS );r&   Ú NTc              
   C   sv  d| _ d| _d| _d| _|| _|| _|| _| d¡r(d| _d| _ |dd… | _n3| d¡r>d| _d	| _ d| _|d
d… | _n| d¡rTd| _d| _ d| _|dd… | _ntd| d�‚d| _	d| _
d| _d| _d| _d| _d| _| jdury| j}n| j}t d|| j| j | jf ¡ zt || jdtj¡d \}}}}	}
t |||¡| _W n tjy½ } zt d|| jf |¡‚d}~ww | j du rË| j |
¡ dS t tj¡}| d d¡¡ d}| |¡ t || j¡| _| j |
¡ | j ¡  ddlm } | j !¡  "d¡ #¡ }t$ %| &dd¡¡}d}d}d}d| }t'|ƒj(dddd�}|}||7 }||7 }||7 }||7 }||ƒ "¡ | _
dS )zË
        LDAPConnection class

        :param string url:
        :param string baseDN:
        :param string dstIp:

        :return: a LDAP instance, if not raises a LDAPSessionError exception
        Fr   Nzldap://i…  é   zldaps://i|  Té   zgc://iÄ  é   zUnknown URL prefix: '%s'©ÚerrorStringz-Connecting to %s, port %d, SSL %s, signing %szConnection error (%s:%d)zALL:@SECLEVEL=0zutf-8i   )Úmd5Úsha256ú:r.   ó    s           s   tls-server-end-point:é   Úlittle©Ú	byteorderÚsigned))Ú_SSLÚ_dstPortÚ_dstHostÚ_socketÚ_baseDNÚ_dstIpÚ_LDAPConnection__signingÚ
startswithr)   Ú_LDAPConnection__bindedÚchannel_binding_valueÚsequenceNumberÚ_LDAPConnection__auth_typeÚ_LDAPConnection__gssÚ_LDAPConnection__sessionKeyÚ#_LDAPConnection__spnego_cipher_blobr   ÚdebugÚsocketÚgetaddrinfoÚSOCK_STREAMÚerrorÚconnectr$   ÚContextÚ
TLS_METHODÚset_cipher_listÚencodeÚset_optionsÚ
ConnectionÚdo_handshakeÚhashlibr4   Úget_peer_certificateÚdigestÚdecodeÚbytesÚfromhexÚreplaceÚlenÚto_bytes)ÚselfÚurlÚbaseDNÚdstIpÚsigningÚ
targetHostÚafÚsocktypeÚprotoÚ_ÚsaÚeÚctxÚ(SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATIONr4   Úpeer_cert_digest_strÚpeer_cert_digest_bytesÚchannel_binding_structÚinitiator_addressÚacceptor_addressÚapplication_data_rawÚlen_application_dataÚapplication_data© rx   ú…/root/aizidognhua/tmp/workspace/projects/ec89d86c-575f-41c9-af57-ac45cbdbf775/venv/lib/python3.10/site-packages/impacket/ldap/ldap.pyÚ__init__N   s~   




"€ÿ


zLDAPConnection.__init__c           0      C   s  |dks|dkr0t |ƒd rd| }t |ƒd rd| }z
t|ƒ}t|ƒ}W n	 ty/   Y nw ddlm} ddlm}m}m}m	}m
} ddlm}m}m}m} ddlm}m}m} dd	lm} dd
lm}m}m} ddl}|dusv|	durxd}
d| j }|
rŠ| |||¡\}}}}	|||jjjd�}|du rª|	du r©||||||||ƒ\}} }!}"n|d }|d } |d }"|	du rÑ|||jj jd�}#||#|||| |"ƒ\}$} }!}"n|	d }$|	d } |	d }"t!ƒ }%t"d g|%d< t#j$|$|ƒ d�d }$|ƒ }&|& %|$d ¡ |ƒ }'d|'d< t&|j'jjƒ|'d< g }(| (|(¡|'d< ||'d|&j)ƒ |ƒ })d|)d< ||)d< ||)d|j*ƒ |j +|j,j-¡}*|*j.|)d< | )|*¡|)d< t/|)d< d |)d d!< |ƒ }+d"|+d#< ||B |+d$< | j0�rg| j1du�rg| j1|+d%< | j2�r{|+d$  |O  < |+d$  |O  < |+ 3¡ |)d d&< d|)d'< t4 5|)¡},|  6|"d(|,d¡}-t/|'d)< | j7|'d) d*< |-|'d) d< t4 5|'¡|%d+< t8ƒ }.d,|.d-< d.|.d/< d0|.d1 d2 d3< |% 3¡ |.d1 d2 d4< |  9|.¡d d5 }/|/d6 d7 t:d8ƒk�rðt;d9|/d6 d7  <¡ |/d6 d: f d;�‚d<| _=d=| _>| j2�r|"| _?|| ƒ| _@d=S )>a6  
        logins into the target system explicitly using Kerberos. Hashes are used if RC4_HMAC is supported.

        :param string user: username
        :param string password: password for the user
        :param string domain: domain where the account is valid for (required)
        :param string lmhash: LMHASH used to authenticate using hashes (password is not used)
        :param string nthash: NTHASH used to authenticate using hashes (password is not used)
        :param string aesKey: aes256-cts-hmac-sha1-96 or aes128-cts-hmac-sha1-96 used for Kerberos authentication
        :param string kdcHost: hostname or IP Address for the KDC. If None, the domain will be used (it needs to resolve tho)
        :param struct TGT: If there's a TGT available, send the structure here and it will be used
        :param struct TGS: same for TGS. See smb3.py for the format
        :param bool useCache: whether or not we should use the ccache for credentials lookup. If TGT or TGS are specified this is False

        :return: True, raises a LDAPSessionError if error.
        r.   r,   Ú0r   )ÚCCache)ÚGSSAPIÚGSS_C_CONF_FLAGÚGSS_C_INTEG_FLAGÚGSS_C_SEQUENCE_FLAGÚGSS_C_REPLAY_FLAG)ÚAP_REQÚAuthenticatorÚTGS_REPÚseq_set)ÚgetKerberosTGTÚgetKerberosTGSÚCheckSumField)Ú	constants)Ú	PrincipalÚKerberosTimeÚTicketNFzldap/%s)ÚtypeÚKDC_REPÚcipherÚ
sessionKeyzMS KRB5 - Microsoft Kerberos 5Ú	MechTypes©Úasn1SpecÚticketr1   Úpvnozmsg-typez
ap-optionszauthenticator-vnoÚcrealmÚcnameÚcusecÚctimeÚcksumi€  Ú	cksumtypeé   ÚLgthÚFlagsÚBndÚchecksumz
seq-numberé   ÚauthenticatorÚetypeÚ	MechTokenr-   ÚversionÚuserÚnameú
GSS-SPNEGOÚauthenticationÚsaslÚ	mechanismÚcredentialsÚ
protocolOpÚbindResponseÚ
resultCodeÚsuccessúError in bindRequest -> %s: %sÚdiagnosticMessager2   ÚKRB5T)Ar`   r   Ú	TypeErrorÚimpacket.krb5.ccacher|   Úimpacket.krb5.gssapir}   r~   r   r€   r�   Úimpacket.krb5.asn1r‚   rƒ   r„   r…   Úimpacket.krb5.kerberosv5r†   r‡   rˆ   Úimpacket.krb5r‰   Úimpacket.krb5.typesrŠ   r‹   rŒ   Údatetimer?   Ú	parseFileÚPrincipalNameTypeÚNT_PRINCIPALÚvalueÚNT_SRV_INSTr    r#   r   r\   Ú	from_asn1ÚintÚApplicationTagNumbersÚencodeFlagsÚto_asn1Úcomponents_to_asn1ÚnowÚtimezoneÚutcÚmicrosecondr   r=   rF   rC   ÚgetDatar   rU   ÚencryptÚenctyper   ÚsendReceiver   r)   ÚprettyPrintrH   rE   rJ   rI   )0rb   r¦   ÚpasswordÚdomainÚlmhashÚnthashÚaesKeyÚkdcHostÚTGTÚTGSÚuseCacher|   r}   r~   r   r€   r�   r‚   rƒ   r„   r…   r†   r‡   rˆ   r‰   rŠ   r‹   rŒ   r»   Ú
targetNameÚuserNameÚtgtr�   ÚoldSessionKeyr�   Ú
serverNameÚtgsÚblobr”   ÚapReqÚoptsr¢   rÇ   ÚchkFieldÚencodedAuthenticatorÚencryptedEncodedAuthenticatorÚbindRequestÚresponserx   rx   ry   ÚkerberosLogin¬   s¾   ÿ
ÿ€ÿ



ÿÿ
zLDAPConnection.kerberosLoginrª   c                 C   s–  t ƒ }d|d< |dkr8d|v r|d | |d< n|r#|d | |d< n||d< ||d d< |  |¡d	 d
 }�nê|dkrQ||d< d|d d< |  |¡d	 d
 }�nÑ|dkrò|dks]|dkr…t|ƒd rgd| }t|ƒd rqd| }z
t|ƒ}t|ƒ}W n	 ty„   Y nw ||d< td|ƒ}	|	 ¡ |d d< |  |¡d	 d
 }|d d tdƒkr¼td|d d  	¡ |d d f d�‚|d d }
d}| j
rÏ| jdurÏ| j}t|	t|
ƒ||||||d�\}}| ¡ |d d< |  |¡d	 d
 }�n0|dk�r|dk�s|dk�r,t|ƒd �rd| }t|ƒd �rd| }z
t|ƒ}t|ƒ}W n
 t�y+   Y nw d|d< tƒ | _d\| jd< | jd< | jd< td|| jd | jd!�}	tƒ }td" g|d#< |	 ¡ |d$< d%|d d d&< | ¡ |d d d'< |  |¡d	 d
 }|d d td(ƒk�r–td|d d  	¡ |d d f d�‚|d d) }t| ¡ ƒ}|d* }
d}| j
�rµ| jdu�rµ| j}t|	|
|||||d+| jd |d,�\}}t||	 ¡ t|
ƒ ¡  | ¡  ƒ}||d-< tƒ }| ¡ |d*< | j�rÿt|	d. |d/�| _| jjd0d	d d1� ¡ |d2< d%|d d d&< | ¡ |d d d'< |  |¡d	 d
 }ntd3| d�‚|d d tdƒk�r@td4|d d  	¡ |d d f d�‚d5|› �| _d | _d S )6a)  
        logins into the target system

        :param string user: username
        :param string password: password for the user
        :param string domain: domain where the account is valid for
        :param string lmhash: LMHASH used to authenticate using hashes (password is not used)
        :param string nthash: NTHASH used to authenticate using hashes (password is not used)
        :param string authenticationChoice: type of authentication protocol to use (default NTLM)

        :return: True, raises a LDAPSessionError if error.
        r-   r¥   ÚsimpleÚ.ú@r§   ú\r©   r   r­   ÚsicilyPackageDiscoveryr.   ÚsicilyNegotiater,   r{   r®   r¯   r°   zCError in bindRequest during the NTLMAuthNegotiate request -> %s: %sr²   r2   Ú	matchedDNr7   N)rF   ÚsicilyResponserª   )é
   r   iaJ  ÚProductMajorVersionÚProductMinorVersionÚProductBuildT)ÚsigningRequiredÚ
use_ntlmv2r¥   z2NTLMSSP - Microsoft NTLM Security Support Providerr‘   r¤   r¨   r«   r¬   ÚsaslBindInProgressÚserverSaslCredsÚResponseTokenÚldap)Úservicer¥   rõ   rF   ÚMICÚflags)rü   ÚrandomSessionKeys   0
+‚7
)Úreset_cipherÚmechListMICz"Unknown authenticationChoice: '%s'r±   zNTLM-)r   rÎ   r`   r   r´   r   rË   r   r)   rÏ   r=   rF   r   r]   r   r¥   rC   r    r#   r!   ÚasOctetsr   r   r"   rK   ÚsignrH   rE   )rb   r¦   rÐ   rÑ   rÒ   rÓ   ÚauthenticationChoicerå   ræ   Ú	negotiateÚtype2rF   Útype3ÚexportedSessionKeyrß   r÷   ÚspnegoTokenRespÚnewmicrx   rx   ry   ÚloginB  sÌ   ÿ

ÿÿÿ 
ÿ
ÿÿÿ$"
ÿÿzLDAPConnection.loginc                 C   s–   | j dkr#| j | j|| j¡\}}|| }t|ƒjdddd�| }|S | j dkrD| j |¡\}}| 	¡ | }t|ƒjdddd�| }|S d| j › d�‚)	Nr³   r8   ÚbigFr:   ú	NTLM-saslzEncryption not implemented for ú	 protocol)
rH   rI   ÚGSS_Wrap_LDAPrJ   rG   r`   ra   rK   rÌ   rË   )rb   ÚdataÚ	signaturerx   rx   ry   rÌ   Ë  s   

úÿzLDAPConnection.encryptc                 C   sl   | j dkr|dd … }| jj| j|ddd�\}}|S | j dkr/|dd … }| j |¡\}}|S d| j › d�‚)	Nr³   r8   r   Úinit)Ú	directionr  zDecryption not implemented for r  )rH   rI   ÚGSS_Unwrap_LDAPrJ   rK   Údecrypt)rb   r  rk   r  rx   rx   ry   r  Ø  s   

ûÿzLDAPConnection.decryptr   Fú(objectClass=*)c                 C   sX  t |tjƒstdtjt|ƒf ƒ‚|d u r| j}|d u r tdƒ}|d u r(tdƒ}|d u r.g }tƒ }||d< ||d< ||d< ||d< ||d< ||d	< |  	|¡|d
< |d j
|Ž  d}g }|sª|  ||	¡}|D ]B}|d  ¡ }| tƒ ¡r™|d tdƒkr„|  |	|d ¡}qett|d ƒd|d  ¡ |d f |d�‚|
d u r£| |¡ qe|
|ƒ qe|r]|S )NzsearchFilter must be %s, got %sÚwholeSubtreeÚneverDerefAliasesÚ
baseObjectÚscopeÚderefAliasesÚ	sizeLimitÚ	timeLimitÚ	typesOnlyÚfilterÚ
attributesFr­   r¯   r°   Úcontrolsz Error in searchRequest -> %s: %sr²   )rP   r3   Úanswers)Ú
isinstanceÚsixÚ	text_typer(   r�   rA   r   r   r   Ú_parseFilterÚsetComponentsrÎ   ÚgetComponentÚisSameTypeWithr   r   Ú_handleControlsr*   rÂ   rÏ   Úappend)rb   Ú
searchBaser  r  r  r  r  ÚsearchFilterr  ÚsearchControlsÚperRecordCallbackÚsearchRequestÚdoner   ræ   ÚmessageÚsearchResultrx   rx   ry   Úsearchä  sP   
ÿü
îzLDAPConnection.searchc                 C   sš   d}|d urK|D ]B}|d urJ|D ]9}t |d ƒtkrHt |d ƒtkrGt|dƒdur8tjt |¡tt ƒ d�d }| ¡ r>d}| 	| ¡ ¡  nq	 qq|S )NTÚcontrolTypeÚ	getCookier’   r   F)
Ústrr   Úhasattrr   r\   r   rU   r   r4  Ú	setCookie)rb   ÚrequestControlsÚresponseControlsr/  ÚrequestControlÚresponseControlrx   rx   ry   r(    s*   ÿÿù
€zLDAPConnection._handleControlsc           
      C   s  t ƒ }||d< d|d d d< |d d d j|Ž  d}| ¡ D ]:\}}||d | d< t|tƒrB|d | d jdd	„ |D ƒŽ  n|d | d  t|tƒrSt|ƒn|¡ |d7 }q |  ||¡d d
 }	|	d d tdƒkr‹t	t|	d d ƒd|	d d  
¡ › d|	d d › �d�‚dS )a•  
        Add an entry to the LDAP directory.

        :param dn: Distinguished Name of the entry to add
        :param objectClass: Tuple or list of object classes for the entry
        :param attributes: Dictionary of attributes for the entry
        :param controls: LDAP controls to include in the request
        :return: True if the entry was added successfully, else raises LDAPSessionError
        ÚentryÚobjectClassr  r   r�   Úvalsr+   c                 s   s&   � | ]}t |tƒrt|ƒn|V  qd S ©N©r!  rÂ   r5  ©Ú.0Úvalrx   rx   ry   Ú	<genexpr>=  s   €$ z%LDAPConnection.add.<locals>.<genexpr>r­   ÚaddResponser¯   r°   zError in addRequest -> ú: r²   ©rP   r3   T)r   r%  Úitemsr!  ÚlistrÂ   r5  rÎ   r   r)   rÏ   )
rb   Údnr=  r  r  Ú
addRequestÚindexÚkeyr¿   ræ   rx   rx   ry   Úadd*  s$   

"(
"þzLDAPConnection.addc                 C   s`  t ƒ }||d< d}| ¡ D ]p\}}|D ]i}|d ttttfvr-td|d › d|› d�d�‚|d |d | d< ||d | d	 d
< g }	t|d tƒrW|	 	dd„ |d D ƒ¡ n|	 
t|d tƒrft|d ƒn|d ¡ |d | d	 d j|	Ž  |d7 }qq|  ||¡d d }
|
d d tdƒkr®tt|
d d ƒd|
d d  ¡ › d|
d d › �d�‚dS )a  
        Modify an entry in the LDAP directory.
        RFC 4511 Section 4.6

        :param dn: Distinguished Name of the entry to modify
        :param modifications: Dictionary of modifications of form {attribute: [(operation, values), ...]}.
                Operation: 0 - add, 1 - delete, 2 - replace, 3 - increment.
                Values: single value or list of values.
        :param controls: LDAP controls to include in the request
        :return: True if the entry was modified successfully, else raises LDAPSessionError
        Úobjectr   z Invalid modification operation 'z' for attribute 'ú'r2   ÚchangesÚ	operationÚmodificationr�   r+   c                 S   s"   g | ]}t |tƒrt|ƒn|‘qS rx   r@  rA  rx   rx   ry   Ú
<listcomp>f  s   " z)LDAPConnection.modify.<locals>.<listcomp>r>  r­   ÚmodifyResponser¯   r°   zError in modifyRequest -> rF  r²   rG  T)r   rH  Ú
MODIFY_ADDÚMODIFY_DELETEÚMODIFY_REPLACEÚMODIFY_INCREMENTr)   r!  rI  Úextendr)  rÂ   r5  r%  rÎ   r   rÏ   )rb   rJ  Úmodificationsr  ÚmodifyRequestÚidxÚattrÚopsÚopr>  ræ   rx   rx   ry   ÚmodifyJ  s.   (
ò"þzLDAPConnection.modifyc                 C   s’   t ƒ }||d< ||d< ||d< |dur||d< |  ||¡d d }|d d	 td
ƒkrGtt|d d	 ƒd|d d	  ¡ › d|d d › �d�‚dS )a,  
        Modify the Distinguished Name of an entry in the LDAP directory.
        RFC 4511 Section 4.9

        :param dn: Current Distinguished Name of the entry
        :param newrdn: New Relative Distinguished Name for the entry
        :param deleteoldrdn: Whether to delete the old RDN from the entry
        :param newSuperior: New superior DN if moving the entry to a different container
        :param controls: LDAP controls to include in the request
        :return: True if the DN was modified successfully, else raises LDAPSessionError
        r<  ÚnewrdnÚdeleteoldrdnNÚnewSuperiorr   r­   ÚmodDNResponser¯   r°   zError in modifyDNRequest -> rF  r²   rG  T)r   rÎ   r   r)   rÂ   rÏ   )rb   rJ  rb  rc  rd  r  ÚmodifyDNRequestræ   rx   rx   ry   Ú	modify_dnt  s   "þzLDAPConnection.modify_dnc                 C   sl   t |ƒ}|  ||¡d d }|d d tdƒkr4tt|d d ƒd|d d  ¡ › d|d d › �d	�‚d
S )a0  
        Delete an entry from the LDAP directory.
        RFC 4511 Section 4.8

        :param dn: Distinguished Name of the entry to delete
        :param controls: LDAP controls to include in the request
        :return: True if the entry was deleted successfully, else raises LDAPSessionError
        r   r­   ÚdelResponser¯   r°   zError in deleteRequest -> rF  r²   rG  T)r   rÎ   r   r)   rÂ   rÏ   )rb   rJ  r  ÚdeleteRequestræ   rx   rx   ry   Údelete�  s   	"þzLDAPConnection.deletec                 C   s   | j d ur| j  ¡  d S d S r?  )r@   Úclose©rb   rx   rx   ry   rk  ¢  s   
ÿzLDAPConnection.closec                 C   sz   t ƒ }t dd¡|d< |d  | ¡ |¡ |d ur |d j|Ž  t |¡}| jr7| j	r7|  
|¡}|  jd7  _| j |¡S )Nr+   iÿÿÿÚ	messageIDr­   r  )r   ÚrandomÚ	randrangeÚsetComponentByTypeÚ	getTagSetr%  r   rU   rE   rC   rÌ   rG   r@   Úsendall)rb   Úrequestr  r0  r  rx   rx   ry   Úsend¦  s   

zLDAPConnection.sendc                 C   sº   d}d}d}|s| j  |¡}t|ƒ|k rd}||7 }|r| jr[| jr[t d|d d… ¡d }|t|ƒd krVd}|sN| j  |¡}t|ƒ|k rHd}||7 }|r:|t|ƒd ks6|  |¡}|S )Ni    r7   FTz!Ir8   r   )r@   Úrecvr`   rE   rC   ÚstructÚunpackr  )rb   ÚREQUEST_SIZEr  r/  ÚrecvDataÚmessage_lengthrx   rx   ry   Úrecv_raw´  s,   üüþ
zLDAPConnection.recv_rawc                 C   sô   g }|   ¡ }t|ƒdkrxztj|tƒ d�\}}W n ty'   ||   ¡  }Y nIw |d dkrk|d d d p9|d }t |d| ¡}|tkrJ|  	¡  t
t|d d d ƒd	||d d d  ¡ |d d d
 f d�‚| |¡ |}t|ƒdks|S )Nr   r’   rm  r­   ÚextendedRespÚresponseNamezUnsolicited Notification '%s'r¯   z%s -> %s: %sr²   rG  )r{  r`   r   r\   r   r   r   Úgetr   rk  r)   rÂ   rÏ   r)  )rb   ræ   r  r0  Ú	remainingr§   Únotificationrx   rx   ry   ru  Í  s0   þþþ
ìzLDAPConnection.recvc                 C   s   |   ||¡ |  ¡ S r?  )rt  ru  )rb   rs  r  rx   rx   ry   rÎ   è  s   zLDAPConnection.sendReceivec                 C   s.   t t|ƒƒ}|  |¡}|rtd|d  ƒ‚|S )Núunexpected token: '%s'éÿÿÿÿ)rI  ÚreversedÚ_consumeCompositeFilterr'   )rb   Ú	filterStrÚ
filterListr+  rx   rx   ry   r$  ì  s
   
zLDAPConnection._parseFilterc                 C   s  z|  ¡ }W n ty   tdƒ‚w |dkr!| |¡ td| ƒ‚z|  ¡ }W n ty2   tdƒ‚w |dvrC| ||g¡ |  |¡S g }	 z
| |  |¡¡ W n	 tyY   Y nw qFz|  ¡ }W n tyl   tdƒ‚w |dkr|| |¡ td| ƒ‚|  ||¡S )NúEOL while parsing search filterú(r�  )ú!ú&ú|Tú))ÚpopÚ
IndexErrorr'   r)  rZ  Ú_consumeSimpleFilterr„  Ú_compileCompositeFilter)rb   r†  ÚcÚoperatorÚfiltersrx   rx   ry   r„  ó  sB   ÿ
ÿ
ÿýÿ
z&LDAPConnection._consumeCompositeFilterc                 C   sæ   z|  ¡ }W n ty   tdƒ‚w |dkr!| |¡ td| ƒ‚g }	 z|  ¡ }W n ty5   tdƒ‚w |dkr;n|dkrH| |¡ tdƒ‚| |¡ q$d |¡}zt |d¡\}}}W n tyk   td	| ƒ‚w |  	|||¡S )
Nr‡  rˆ  r�  TrŒ  zunexpected token: '('r.   r+   zinvalid filter: '(%s)')
r�  rŽ  r'   r)  ÚjoinÚRE_OPERATORÚsplitÚ
ValueErrorr(   Ú_compileSimpleFilter)rb   r†  r‘  r  r…  Ú	attributer’  r¿   rx   rx   ry   r�    s:   ÿ
ÿ

õ
ÿz#LDAPConnection._consumeSimpleFilterc                 C   s�   t ƒ }| dkrt|ƒdkrtdƒ‚|d j|Ž  |S | dkr1t|ƒdkr(tdƒ‚|d j|Ž  |S | d	krFt|ƒdkr?td
ƒ‚|d j|Ž  |S )Nr‰  r+   z*'not' filter must have exactly one elementÚnotrŠ  r   z+'and' filter must have at least one elementÚandr‹  z*'or' filter must have at least one elementÚor)r   r`   r(   r%  )r’  r“  r+  rx   rx   ry   r�  5  s    
÷ûz&LDAPConnection._compileCompositeFilterc                 C   s  t ƒ }|dkrEt | ¡pt | ¡}|std|  ƒ‚| ¡ \} }}| r(| |d d< |r2t|ƒ|d d< |r:||d d< t |¡|d d< |S t	 | ¡sPtd|  ƒ‚|dkr^|d	kr^| |d
< |S d|v rÁ|d	krÁdd„ | 
d¡D ƒ}|d d  ¡ }g }	|d r‹|	 | ¡  d|d ¡¡ |dd… D ]}
|	 | ¡  d|
¡¡ q‘|d r°|	 | ¡  d|d ¡¡ | |d d< |d d j|	Ž  |S d|v�rt |¡}|d	krÙ|d  | |¡ |S |dkrç|d  | |¡ |S |dkrõ|d  | |¡ |S |dk�r|d  | |¡ |S td| ||f ƒ‚)Nz:=zinvalid filter attribute: '%s'ÚextensibleMatchr�   ÚdnAttributesÚmatchingRuleÚ
matchValueÚ*ú=Úpresentc                 S   s   g | ]}t  |¡‘qS rx   )r&   Ú_processLdapString)rB  Ú	assertionrx   rx   ry   rT  \  s    z7LDAPConnection._compileSimpleFilter.<locals>.<listcomp>Ú
substringsr   Úinitialr+   r‚  ÚanyÚfinalÚequalityMatchz~=ÚapproxMatchz>=ÚgreaterOrEqualz<=ÚlessOrEqualzinvalid filter '(%s%s%s)')r   ÚRE_EX_ATTRIBUTE_1ÚmatchÚRE_EX_ATTRIBUTE_2r(   ÚgroupsÚboolr&   r¤  ÚRE_ATTRIBUTEr–  ÚgetComponentTyper)  ÚcloneÚsetComponentByNamer%  )r™  r’  r¿   r+  r¯  rJ  rŸ  Ú
assertionsÚchoicer¦  r¥  rx   rx   ry   r˜  G  s^   
ãç
ó

÷ù
ûþz#LDAPConnection._compileSimpleFilterc                 C   s    dd„ }t  d¡}t  |||¡S )Nc                 S   s   t t|  d¡dƒƒS )Nr+   rœ   )ÚchrrÂ   Úgroup)r¯  rx   rx   ry   Úreplace_escaped_charsy  s   z@LDAPConnection._processLdapString.<locals>.replace_escaped_charsz\\([0-9a-fA-F]{2}))ÚreÚcompileÚsub)ÚclsÚldapstrr»  Úescaped_charsrx   rx   ry   r¤  w  s   
z!LDAPConnection._processLdapString)r.   NT)r.   r.   r.   r.   NNNT)r.   r.   r.   r.   r.   rª   )
NNNr   r   Fr  NNN)NNr?  )TNN)Ú__name__Ú
__module__Ú__qualname__rz   rç   r	  rÌ   r  r2  r(  rN  ra  rg  rj  rk  rt  r{  ru  rÎ   r$  r„  r�  Ústaticmethodr�  r˜  Úclassmethodr¤  rx   rx   rx   ry   r&   M   s@    
^
ÿ 
 

ÿ2

 
*


" 

/r&   c                   @   ó   e Zd ZdS )r'   N©rÂ  rÃ  rÄ  rx   rx   rx   ry   r'   €  ó    r'   c                   @   rÇ  )r(   NrÈ  rx   rx   rx   ry   r(   „  rÉ  r(   c                   @   s:   e Zd ZdZddd„Zdd„ Zdd	„ Zd
d„ Zdd„ ZdS )r)   z9
    This is the exception every client should catch
    r   r.   c                 C   s    t  | ¡ || _|| _|| _d S r?  )Ú	Exceptionrz   rP   Úpacketr3   )rb   rP   rË  r3   rx   rx   ry   rz   �  s   

zLDAPSessionError.__init__c                 C   ó   | j S r?  )rP   rl  rx   rx   ry   ÚgetErrorCode“  ó   zLDAPSessionError.getErrorCodec                 C   rÌ  r?  )rË  rl  rx   rx   ry   ÚgetErrorPacket–  rÎ  zLDAPSessionError.getErrorPacketc                 C   rÌ  r?  r2   rl  rx   rx   ry   ÚgetErrorString™  rÎ  zLDAPSessionError.getErrorStringc                 C   rÌ  r?  r2   rl  rx   rx   ry   Ú__str__œ  rÎ  zLDAPSessionError.__str__N)r   r   r.   )	rÂ  rÃ  rÄ  Ú__doc__rz   rÍ  rÏ  rÐ  rÑ  rx   rx   rx   ry   r)   ˆ  s    
r)   c                   @   s   e Zd Zddd„Zdd„ ZdS )	r*   r   r.   Nc                 C   s&   t  | |||¡ |d u rg }|| _d S r?  )r)   rz   r   )rb   rP   rË  r3   r   rx   rx   ry   rz   ¡  s   
zLDAPSearchError.__init__c                 C   rÌ  r?  )r   rl  rx   rx   ry   Ú
getAnswers§  rÎ  zLDAPSearchError.getAnswers)r   r   r.   N)rÂ  rÃ  rÄ  rz   rÓ  rx   rx   rx   ry   r*      s    
r*   )Lr¼  rv  rM   Úbinasciir   rn  r"  Úpyasn1.codec.berr   r   Úpyasn1.errorr   Úpyasn1.type.univr   Úimpacketr   Úimpacket.ldap.ldapasn1r   r	   r
   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   r   Úimpacket.ntlmr   r   r   r   r   Úimpacket.spnegor    r!   r"   r#   ÚOpenSSLr$   r%   ÚcriticalÚ__all__ÚDESCRIPTIONÚNUMERIC_OIDÚOIDÚOPTIONSÚ	ATTRIBUTEÚDNÚMATCHING_RULEr½  r•  ÚIr³  r®  r°  rV  rW  rX  rY  r&   ÚSyntaxErrorr'   rÊ  r(   r)   r*   rx   rx   rx   ry   Ú<module>   s\   T

      9