B
    u9aT                 @   s  d dl Z d dlZd dlZd dlZd dlmZ d dlZd dlmZ ej	ddgd d dl
T yejejdd	  ZW n eefk
r   dZY nX e dd
 Ze dkrdndZedk rdndZde  f Zde Zde Zddefddefddefddefdddddgefdd efd!d"d# efd$d%d& efd'd(efg	ZG d)d* d*ejZ G d+d, d,e Z!e"ed-G d.d/ d/e Z#e"ed0G d1d2 d2e Z$d3d4 Z%e&d5krese'd6d7 e%  dS )8    N)support)machinewinregwin)Zrequired_on)*z--remote      ZAMD64TF)   r   z Python Test Key [%d] - Delete Mez	SOFTWARE\zSOFTWARE\Classes\z	Int Value-   zQword Valuel   w*M	 z
String ValzA string valueZStringExpandzThe path is %path%zMulti-stringZLotsZofstringvalueszRaw Datas   binary dataz
Big Stringxi?  z
Big Binary   xi @  u   Japanese 日本u	   日本語c               @   sT   e Zd Zdd Zdd ZdefddZdefdd	Zdd
dZ	dddZ
dd ZdS )BaseWinregTestsc             C   s   |  tt d S )N)delete_treeHKEY_CURRENT_USERtest_key_name)self r   !/usr/lib/python3.7/test_winreg.pysetUp5   s    zBaseWinregTests.setUpc             C   sv   yt ||dt}W n tk
r&   d S X x6yt|d}W n tk
rN   P Y nX | || q*W t| t|| d S )Nr   )OpenKeyKEY_ALL_ACCESSOSErrorEnumKeyr   CloseKey	DeleteKey)r   rootZsubkeyhkeyZ	subsubkeyr   r   r   r   :   s    zBaseWinregTests.delete_treesub_keyc             C   s,  t |ttd ||t}| |jdk |||}x"tD ]\}}}t||d|| q8W t|\}	}
}| |	dd | |
dd t|\}	}
}| |	dd | |
t	td t
|}t| yt| | d W n tk
r   Y nX t
|}|  yt| | d W n tk
r&   Y nX d S )NzDefault valuer   r   z"Not the correct number of sub keysz Not the correct number of valueszAIt appears the CloseKey() function does not close the actual key!zBIt appears the key.Close() function does not close the actual key!)SetValuer   REG_SZ
assertTruehandle	test_data
SetValueExQueryInfoKeyassertEquallenintr   failr   Close)r   root_key	subkeystr	CreateKeykeyr   
value_name
value_data
value_typenkeysnvalues	since_modZint_sub_keyZint_keyr   r   r   _write_test_dataJ   s6    

z BaseWinregTests._write_test_datac          	   C   s.  t |t}| |dd ||t}|||}d}xDyt||}W n tk
rX   P Y nX | |tkdd |d }q4W | |ttd x<tD ]4\}	}
}t||	\}}| ||
d | ||d qW W d Q R X |  t	|d}| ||d	 yt	|d | 
d
 W n tk
r    Y nX |  d S )NzDefault valuez+Registry didn't give back the correct valuer   Tz&Didn't read back the correct test datar   z'Didn't read the correct number of itemsz!Could not directly read the valuezRead subkey value wrongz2Was able to get a second key when I only have one!)
QueryValuer   r'   	EnumValuer   r$   r(   QueryValueExr+   r   r*   )r   r,   r-   r   valr/   r   indexdatar0   r1   r2   Zread_valZread_typr   r   r   _read_test_datat   s>    



zBaseWinregTests._read_test_datac             C   s   t |tdt}t ||dt}xtD ]\}}}t|| q"W t|\}}	}
| |dd | |	dd |  t|| yt|| | 	d W n t
k
r   Y nX |  t|t yt |t}| 	d W n t
k
r   Y nX d S )Nr   zsubkey not empty before deletez Deleting the key twice succeededzCould open the non-existent key)r   r   r   r$   ZDeleteValuer&   r'   r+   r   r*   r   )r   r,   r-   r/   r   r0   r1   r2   r3   r4   r5   r   r   r   _delete_test_data   s*    



z!BaseWinregTests._delete_test_datac             C   s(   |  || | || | || d S )N)r6   r=   r>   )r   r,   r-   r   r   r   	_test_all   s    zBaseWinregTests._test_allc          	   C   s\   t ||dtd}| |jdk W d Q R X t||dtd}| |jdk W d Q R X d S )Nr   )r/   r   reservedaccess)CreateKeyExr   r"   r#   	OpenKeyEx)r   r/   r   ZckeyZokeyr   r   r   _test_named_args   s    

z BaseWinregTests._test_named_argsN)r   )r   )__name__
__module____qualname__r   r   r.   r6   r   r=   r>   r?   rD   r   r   r   r   r   3   s   )(

r   c               @   s   e Zd Zdd Zdd Zdd Zdd Zd	d
 Zdd Zdd Z	dd Z
dd Zdd Zeedk ddd Zdd Zdd Zdd Zdd  Zd!S )"LocalWinregTestsc             C   s   |  t |  td d S )Nu   日本-subkey)r?   r   )r   r   r   r   test_registry_works   s    
z$LocalWinregTests.test_registry_worksc             C   s:   dd }| j t|d dd }| jt|d | t d S )Nc             S   s   t | |dtS )Nr   )rB   r   )r/   r   r   r   r   <lambda>       zILocalWinregTests.test_registry_works_extended_functions.<locals>.<lambda>)r.   c             S   s   t | |dtS )Nr   )rC   KEY_READ)r/   r   r   r   r   rJ      rK   )r   )r6   r   r=   r>   )r   ZckeZoker   r   r   &test_registry_works_extended_functions   s
    z7LocalWinregTests.test_registry_works_extended_functionsc             C   s   |  tt ttt d S )N)rD   r   r   r   )r   r   r   r   test_named_arguments   s    z%LocalWinregTests.test_named_argumentsc             C   s2   t d t}| |jd |  | |jd d S )Nr   )ConnectRegistryHKEY_LOCAL_MACHINEassertNotEqualr#   r+   r'   )r   hr   r   r   ,test_connect_registry_to_local_machine_works   s    
z=LocalWinregTests.test_connect_registry_to_local_machine_worksc             C   s   dd }|  t| d S )Nc               S   s
   t dtS )NZabcdefghijkl)rO   r   r   r   r   r   rJ      rK   zBLocalWinregTests.test_inexistant_remote_registry.<locals>.<lambda>)assertRaisesr   )r   Zconnectr   r   r   test_inexistant_remote_registry   s    z0LocalWinregTests.test_inexistant_remote_registryc             C   s2   t d}| t|t | |tjd d  d S )Nz%windir%\testZwindirz\test)ZExpandEnvironmentStringsr'   typestrosenviron)r   rr   r   r   testExpandEnvironmentStrings   s    z-LocalWinregTests.testExpandEnvironmentStringsc          	   C   sT   y,t d t}| |jd tW d Q R X W n" tk
rN   | |jd Y nX d S )Nr   )rO   rP   rQ   r#   r   r'   )r   rR   r   r   r   test_context_manager   s    z%LocalWinregTests.test_context_managerc       
   
      s   d G  fdddt j}| }|  zhtttd P}xHtdD ]<}t|\}}}x(t|D ]}t||}	t	||	d  q`W qDW W d Q R X W d d |
  tttd  ttt X d S )NFc                   s   e Zd Z fddZdS )z>LocalWinregTests.test_changing_value.<locals>.VeryActiveThreadc          	      sL   t tt8}d}d}x( s<|r"dn|}| }t|dt| qW W d Q R X d S )NTA  xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxr   Zchanging_value)r.   r   r   r    r!   )r   r/   Z	use_shortZlong_strings)doner   r   run  s    zBLocalWinregTests.test_changing_value.<locals>.VeryActiveThread.runN)rE   rF   rG   r_   r   )r^   r   r   VeryActiveThread   s   r`   z\changing_valuei  r   T)	threadingZThreadstartr.   r   r   ranger&   r8   r7   joinr   )
r   r`   Zthreadr/   _num_subkeys
num_valuestinamer   )r^   r   test_changing_value   s     

$z$LocalWinregTests.test_changing_valuec             C   sj   d}z@t tt,}t||td t|\}}}t|d W d Q R X W d ttdt|f ttt X d S )NA   xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxr   r   \)	r.   r   r   r    r!   r&   r   r   rd   )r   rj   r/   rf   rg   rh   r   r   r   test_long_key  s    zLocalWinregTests.test_long_keyc          
   C   s^   yt td W n@ tk
rN } z"|jtjtjfkr<| d  W d d }~X Y nX ttd d S )Nr   zMaccess denied to registry key (are you running in a non-interactive session?) )r8   ZHKEY_PERFORMANCE_DATAr   errnoZEPERMZEACCESZskipTestr9   )r   er   r   r   test_dynamic_key(  s    
z!LocalWinregTests.test_dynamic_key)   r   zRequires Windows XPc          	   C   s   zt tt}| |jd W d Q R X ttt}| |jd | t t| W d Q R X | t t	| W d Q R X | t t
| W d Q R X | t ttt W d Q R X W d ttt X d S )Nr   )r.   r   r   rQ   r#   r   rT   NotImplementedErrorDisableReflectionKeyEnableReflectionKeyQueryReflectionKeyDeleteKeyExr   )r   ckr/   r   r   r   test_reflection_unsupported6  s    
z,LocalWinregTests.test_reflection_unsupportedc          	   C   sJ   z8t tt$}| |jd t|dd td W d Q R X W d ttt X d S )Nr   	test_namel        )r.   r   r   rQ   r#   r%   	REG_DWORDr   )r   rx   r   r   r   test_setvalueex_value_rangeJ  s
    z,LocalWinregTests.test_setvalueex_value_rangec          	   C   st   zbt ttN}| |jd d}t|dd t| t|d\}}| |t | || W d Q R X W d t	tt X d S )Nr   l        rz   )
r.   r   r   rQ   r#   r%   r{   r9   r'   r   )r   rx   test_valret_valret_typer   r   r   test_queryvalueex_return_valueV  s    z/LocalWinregTests.test_queryvalueex_return_valuec          	   C   st   zbt ttN}| |jd d }t|ddt| t|d\}}| |t | || W d Q R X W d t	tt X d S )Nr   rz   )
r.   r   r   rQ   r#   r%   
REG_BINARYr9   r'   r   )r   rx   r}   r~   r   r   r   r   #test_setvalueex_crash_with_none_argf  s    z4LocalWinregTests.test_setvalueex_crash_with_none_argc          	   C   st   zbt ttN}| |jd d}t|ddt| t|d\}}| |t | |d W d Q R X W d t	tt X d S )Nr   zA string  with a nullrz   zA string)
r.   r   r   rQ   r#   r%   r!   r9   r'   r   )r   rx   r}   r~   r   r   r   r    test_read_string_containing_nulls  s    z1LocalWinregTests.test_read_string_containing_nullN)rE   rF   rG   rI   rM   rN   rS   rU   r[   r\   rk   rm   rq   unittest
skipUnlessWIN_VERry   r|   r   r   r   r   r   r   r   rH      s   	 rH   zSkipping remote registry testsc               @   s   e Zd Zdd ZdS )RemoteWinregTestsc             C   s   t tt}| | d S )N)rO   REMOTE_NAMEr   r?   )r   Z
remote_keyr   r   r   test_remote_registry_works  s    
z,RemoteWinregTests.test_remote_registry_worksN)rE   rF   rG   r   r   r   r   r   r     s   r   zx64 specific registry testsc               @   sL   e Zd Zdd Zdd Zeeddd Zeeddd	 Z	d
d Z
dS )Win64WinregTestsc             C   s    |  tt ttttdd d S )Nr   )r/   r   rA   r@   )rD   r   r   rw   r   )r   r   r   r   rN     s    z%Win64WinregTests.test_named_argumentsc          	   C   sR   t td>}| t| | t| | t| | t| W d Q R X d S )NZSoftware)r   rP   r"   rv   ZassertIsNoneru   rt   )r   r/   r   r   r   test_reflection_functions  s
    z*Win64WinregTests.test_reflection_functionszOS doesn't support reflectionc             C   s  zt ttdttB d}| |jd tttdttB }| |jd W d Q R X t|ddt	d dd }| 
t| W d Q R X tttdttB 6}| |jd | dt|d t|ddt	d W d Q R X tttdttB }| dt|d W d Q R X W d ttttd X d S )Nr   rn   Z32KEYc               S   s   t ttdttB S )Nr   )r   r   test_reflect_key_namerL   KEY_WOW64_64KEYr   r   r   r   rJ     s   z2Win64WinregTests.test_reflection.<locals>.<lambda>Z64KEY)rB   r   r   r   KEY_WOW64_32KEYrQ   r#   r   r%   r!   rT   r   r   r'   r7   rL   rw   )r   created_keyr/   	open_failr   r   r   test_reflection  s(     z Win64WinregTests.test_reflectionc             C   s   zt ttdttB >}t|}| t|t | 	| t
| | t| W d Q R X dd }| t| tttdttB }| |jd W d Q R X W d ttttd X d S )Nr   c               S   s   t ttdttB S )Nr   )rC   r   r   rL   r   r   r   r   r   rJ     s   z:Win64WinregTests.test_disable_reflection.<locals>.<lambda>)rB   r   r   r   r   rv   r'   rV   boolZassertFalsert   r"   rT   r   rC   rL   rQ   r#   rw   )r   r   Zdisabledr   r/   r   r   r   test_disable_reflection  s    
z(Win64WinregTests.test_disable_reflectionc          	   C   s$   |  t}ttd W d Q R X d S )NZsome_value_that_does_not_exist)rT   FileNotFoundErrorr7   ZHKEY_CLASSES_ROOT)r   Zctxr   r   r   test_exception_numbers  s    z'Win64WinregTests.test_exception_numbersN)rE   rF   rG   rN   r   r   r   HAS_REFLECTIONr   r   r   r   r   r   r   r     s
   
,r   c               C   s   t ttt d S )N)r   Zrun_unittestrH   r   r   r   r   r   r   	test_main  s    r   __main__z)Remote registry calls can be tested usingz('test_winreg.py --remote \\machine_name')(rX   sysro   r   Ztestr   ra   platformr   import_moduler   argvr;   r   
IndexError
ValueErrorZgetwindowsversionr   ZWIN64_MACHINEr   getpidZtest_key_baser   r   r{   Z	REG_QWORDr!   ZREG_EXPAND_SZZREG_MULTI_SZr   r$   ZTestCaser   rH   r   r   r   r   rE   printr   r   r   r   <module>   sN   
  9`
