
    h                      X   d Z ddlmZ ddlmZ ddlmZ ddlZddlZddlmZ ddlmZ ej                  Z	dZ
d	Zd
ZeZdZdZdZdZeez  ez  ZdZdZej*                  Zej,                  ej.                  _        g ej.                  _        ej.                  Z G d de      Z G d de      Zy)z.Utilities for encryption functions on Windows.    )absolute_import)division)unicode_literalsN)windll)wintypesi      z.Microsoft Enhanced Cryptographic Provider v1.0l      ` i   i   @      c                         e Zd Zd fd	Z xZS )WindowsExceptionc                 ^    t               }d|z  }|r|d|z  z  }t        t        |   |       y )NzWindows Error: 0x%0xz
Extra Info: %s)get_last_errorsuperr   __init__)self
extra_datawindows_error_codemessage	__class__s       >lib/googlecloudsdk/api_lib/compute/windows_encryption_utils.pyr   zWindowsException.__init__6   s:    ')$'99G#j00g	
D*73    N)__name__
__module____qualname__r   __classcell__)r   s   @r   r   r   4   s    4 4r   r   c                   0    e Zd ZdZd Zd Zd ZddZd Zy)	WinCryptz,Base Class for Windows encryption functions.c                    t         j                  | _        t        j                  | j                  _        t        j                  t        j                  t        j                  t        j                  t        j                  g| j                  _	        t         j                  | _        t        j                  | j                  _        t        j                  t        j                  g| j                  _	        t         j                  | _        t        j                  | j                  _        t        j                  t        j                  t        j                  t        j                  t        j                        g| j                  _	        t         j                   | _        t        j                  | j"                  _        t        j                  g| j"                  _	        t         j$                  | _        t        j                  | j&                  _        t        j                  t        j                  t        j                  t        j                  t        j                  t        j(                        t        j                  t        j                        g| j&                  _	        t         j*                  | _        t        j                  | j,                  _        t        j                  t        j                  t        j                  t        j                  t        j                  t        j(                        t        j                  t        j                        g| j,                  _	        y r   )advapi32CryptAcquireContextWcrypt_acquire_contextr   BOOLrestypeHANDLELPCWSTRDWORDargtypesCryptReleaseContextcrypt_release_contextCryptGenKeycrypt_gen_keyctypesPOINTERCryptDestroyKeycrypt_destroy_keyCryptDecryptcrypt_decryptBYTECryptExportKeycrypt_export_key)r   s    r   r   zWinCrypt.__init__A   s   !)!>!>D)1D&+3??+3+;+;+3+;+;+3>>+3>>	+;D' "*!=!=D)1D&+3??+3>>+;D' "--D!)D#+??#+>>#+>>#)>>(//#B#DD
 &55D%-]]D"'/&7D#!..D!)D#+??#+??#+==#+>>#)>>(--#@#)>>(..#A#CD %33D$,MMD!&.oo&.oo&.nn&.nn&,nnX]]&C&,nnX^^&D&FD"r   c                 4   t        j                         }d}t        }t        }t        }t
        }t        j                         }| j                  t        j                  |      ||||      st        t        dz  }| j                  ||||      s
t               |S )z%Returns a handle for an RSA key pair.N   )r   r%   MS_ENHANCED_PROVPROV_RSA_FULLCRYPT_VERIFYCONTEXTCALG_RSA_KEYXr"   r-   byrefr   RSA_KEY_LENGTHr,   )	r   crypt_provider_handlekey_container_nameproviderprovider_typeacquire_context_flagsalgorithm_id
key_handlegen_key_flagss	            r   
GetKeyPairzWinCrypt.GetKeyPairl   s     %OO-H!M/ L"J %%fll3H&I&8&.&3&;	=
  #b(M3*+(* r   c           
         d}t         }d}d}t        j                         }| j                  |||||t        j                  |             t
        j                  |j                  z  } |       }| j                  |||||t        j                  |            s
t               t        j                  |j                  z  j                  |      }|S )z=Returns the public key for the referenced private key handle.Nr   )PUBLICKEYBLOBr-   c_ulongr5   r<   r   r3   valuer   c_charfrom_buffer)	r   keyuser_crypto_keykey_typeexport_key_flagskey_datakey_lenbyte_array_type
public_keys	            r   GetPublicKeyzWinCrypt.GetPublicKey   s    OH HnnG#)"*" ,,w/1 mmgmm3O H  !0!)!1!)!'g!68 --'--/<<XFJr   c           
         t        j                  |      }|ddd   }t        j                  t	        |            }t
        j                  |j                  z  j                  |      }d}d}	t        }
| j                  |||	|
|t        j                  |            st        |      t        j                  |j                  z  j                  |      }|r| j                  |       |j                  S )a  Returns a decrypted message from the given encrypted message and key.

    Can optionally destroy the key (used only on Windows).

    Args:
      key: An openssl key pair (private key) or a Windows key handle.
      enc_message: A base64 encoded encrypted message.
      destroy_key: If True, the key pointed to by the key handle is destroyed.

    Returns:
      Decrypted version of enc_message

    Raises:
      WindowsException: If message fails to decrypt
    NT)base64	b64decoder-   rI   lenr   r3   rJ   from_buffer_copy
CRYPT_OAEPr2   r<   r   rK   rL   r0   )r   rM   enc_messagedestroy_keydecoded_messagelittle_endian_messagedata_lendata_bufhash_objectfinaldecrypt_flagsr   s               r   DecryptMessagezWinCrypt.DecryptMessage   s      &&{3O+DbD1~~c"789H.@@H KEMc)#+&$ll846 X&&}}x~~-::8DG
S!==r   c                     |dd ddd   }|dd ddd   }t        j                  |      }t        j                  |      }||fS )zBReturns a base64 encoded modulus and exponent from the public key.   NrW   r7   )rX   	b64encode)r   rT   modulusexponentb64_modb64_exps         r   GetModulusExponentFromPublicKeyz(WinCrypt.GetModulusExponentFromPublicKey   sX     odd#G"R 2&Hw'Gx(GWr   N)T)	r   r   r   __doc__r   rF   rU   rf   rn    r   r   r   r   >   s!    4)FV<<'Rr   r   )ro   
__future__r   r   r   rX   r-   r   r   r    r=   r9   MS_ENHANCED_PROV_Wr8   r:   ALG_CLASS_KEY_EXCHANGEALG_TYPE_RSAALG_SID_RSA_ANYr;   r\   rH   kernel32r'   GetLastErrorr$   r(   r   	Exceptionr   objectr   rp   r   r   <module>rz      s    5 &  '    ?? E %    '4_D
 ?? (   !#   &&4y 4`v `r   