+
    THi6]                       a  R! t10 t ^ RIt^ RIt^ RIt^ RIHt ^ RIHtHt ^ RI	H
t
 ^ RIHtHt ^ RIHt ^ RIHt ^ RIHtHtHt ^ R	IHt . R"Ot]! ^^^$^0^<R
7      tR tR tR#R lt]]3t ]!]"3t#]!! 4       t$] ^ k R$R lt% ! R R4      t&]! RRRRR7      t' ! R R]&4      t(R%R lt)R t* ! R R]4      t+]+! 4       t,R& F  t-],P]                  ]-R]- R24       K  	   ! R R]&4      t/R%R  lt0R# )'    N)defaultdict)HashableMutableMapping)	resources)ceillog2)exc)logger)
getrandstrrng
to_unicode)memoized_property)unsafeweakfairstrongsecurec                `    \        V 4      P                  pW"P                  V4      ^,           R # )z2return remaining classes in object's MRO after clsN)type__mro__index)objclsmros   && -/usr/lib/python3/dist-packages/passlib/pwd.py_superclassesr   %   s*    
s)

Cyy~!#$$    c                ^    \        V 4      p\        \        4      pV  F  pW#;;,          ^,          uu&   K  	  Vf   VP	                  4       p\        V4      pMVP	                  4       pV'       g   ^ # \        V4      \        R V 4       4      V,          ,
          #   \         d    Rp Li ; i)a  
returns 'rate of self-information' --
i.e. average (per-symbol) entropy of the sequence **source**,
where probability of a given symbol occurring is calculated based on
the number of occurrences within the sequence itself.

if all elements of the source are unique, this should equal ``log(len(source), 2)``.

:arg source:
    iterable containing 0+ symbols
    (e.g. list of strings or ints, string of characters, etc).

:returns:
    float bits of entropy
Nc              3   D   "   T F  q\        V4      ,          x  K  	  R # 5iN)r   ).0values   & r   	<genexpr>"_self_info_rate.<locals>.<genexpr>L   s     DVEDK//Vs    )len	TypeErrorr   intvaluessumr   )sourcesizecountscharr(   s   &    r   _self_info_rater.   +   s     6{ F |6{ :DVDDtKKK  s   B B,+B,c                |   V'       d&   \         P                  ! V4      ! \        V 4      4      # \        P                  P                  V 4      '       d   \        V R4      # V P                  R4      w  r#pV'       g   \        RV : 24      h\        P                  ! V4      P                  V4      P                  R4      # )z
:param asset_path:
    string containing absolute path to file,
    or package-relative path using format
    ``"python.module:relative/file/path"``.

:returns:
    filehandle opened in 'rb' mode
    (unless encoding explicitly specified)
rb:zIasset path must be absolute file path or use 'pkg.name:sub/path' format: )codecs	getreader_open_asset_pathospathisabsopen	partition
ValueErrorr   filesjoinpath)r6   encodingpackagesepsubpaths   &&   r   r4   r4   W   s     )*:4*@AA	ww}}TD$ NN3/G'226;
 	
 ??7#,,W5::4@@r   c                   \         pRp W9   d   R#  \        V \        4      '       g#   \	        \        V 4      4      \	        V 4      8X  dI   V'       d?   \        P                  ! \        4      ;_uu_ 4        VP                  V 4       RRR4       R# R# \        4       p\        4       pV  F  pWd9   d   TMTP                  V4       K  	  \        V4      p^p\	        V4      V8  d   ^pRP                  R VRV  4       4      p\	        V4      V8  d!   VR\	        V4      V,
          ,          ,          p\        RV RV 24      h  \         d    Rp ELAi ; i  + '       g   i     R# ; i)	z
helper for generators --
Throws ValueError if source elements aren't unique.
Error message will display (abbreviated) repr of the duplicates in a string/list
TFN, c              3   J   "   T F  p\        \        V4      4      x  K  	  R # 5ir    )reprstrr!   words   & r   r#   !_ensure_unique.<locals>.<genexpr>   s     B\Tc$i\s   !#z, ... plus %d others`z%` cannot contain duplicate elements: )_ensure_unique_cacher&   
isinstance
_set_typesr%   set
contextlibsuppressaddsortedjoinr:   )	r*   paramcachehashableseendupselemtruncdup_reprs	   &&       r   _ensure_uniquer[   w   s:    !EH?  &*%%S[)9S[)H$$Y// 		&! 0  5D5D4,,T2 $<DE
4y5yyBT&5\BBH
4y5*c$i%.?@@ qDXJO
PP5   0/ s   E 5EEEE)	c                      a a ] tR t^t oRtRtRt]tRtRV 3R llt	]
R 4       t]
R 4       tR tRR ltR	 tR
tVtV ;t# )SequenceGeneratora  
Base class used by word & phrase generators.

These objects take a series of options, corresponding
to those of the :func:`generate` function.
They act as callables which can be used to generate a password
or a list of 1+ passwords. They also expose some read-only
informational attributes.

Parameters
----------
:param entropy:
    Optionally specify the amount of entropy the resulting passwords
    should contain (as measured with respect to the generator itself).
    This will be used to auto-calculate the required password size.

:param length:
    Optionally specify the length of password to generate,
    measured as count of whatever symbols the subclass uses (characters or words).
    Note if ``entropy`` requires a larger minimum length,
    that will be used instead.

:param rng:
    Optionally provide a custom RNG source to use.
    Should be an instance of :class:`random.Random`,
    defaults to :class:`random.SystemRandom`.

Attributes
----------
.. autoattribute:: length
.. autoattribute:: symbol_count
.. autoattribute:: entropy_per_symbol
.. autoattribute:: entropy

Subclassing
-----------
Subclasses must implement the ``.__next__()`` method,
and set ``.symbol_count`` before calling base ``__init__`` method.
Nr   c                2  < V P                   f   Q R4       hVf   Vfh   Vf   V P                  p\        P                  W4      pV^ 8:  d   \	        R4      h\        \        WP                  ,          4      4      pVe   W%8  d   TpWn        V^8  d   \	        R4      hW n        Ve   W0n	        V'       dR   \        V \        4      \        38X  d8   \        RP                  RP                  VP!                  4       4      4      4      h\"        SV `H  ! R/ VB  R # )Nzsubclass must set .symbol_countz!`entropy` must be positive numberz!`length` must be positive integerzUnexpected keyword(s): {}rB    )symbol_countrequested_entropyentropy_aliasesgetr:   r'   r   entropy_per_symbollengthr   r   r]   objectr&   formatrR   keyssuper__init__)selfentropyre   r   kwds
min_length	__class__s   &&&&, r   rj   SequenceGenerator.__init__   s      ,O.OO, &.00%))';G!| !DEET',C,C"CDEJ~!4#!(A:@AA ?H M$(9:viG7>>tyy?UVWW 4 r   c                ,    \        V P                  4      # )zJ
Average entropy per symbol (assuming all symbols have equal probability)
)r   r`   rk   s   &r   rd   $SequenceGenerator.entropy_per_symbol   s    
 D%%&&r   c                <    V P                   V P                  ,          # )a  
Effective entropy of generated passwords.

This value will always be a multiple of :attr:`entropy_per_symbol`.
If entropy is specified in constructor, :attr:`length` will be chosen so
so that this value is the smallest multiple >= :attr:`requested_entropy`.
)re   rd   rr   s   &r   rl   SequenceGenerator.entropy   s     {{T4444r   c                    \        R4      h)z;main generation function, should create one password/phrasezimplement in subclass)NotImplementedErrorrr   s   &r   __next__SequenceGenerator.__next__  s    !"9::r   c                    Vf   \        V 4      # \        V\        4      '       d%   \        V4       Uu. uF  p\        V 4      NK  	  up# V\        J d   V # \
        P                  ! VRR4      hu upi )z>
frontend used by genword() / genphrase() to create passwords
z<None>, int, or <iter>returns)nextrK   r'   rangeiterr	   ExpectedTypeError)rk   r{   _s   && r   __call__SequenceGenerator.__call__	  sd     ?:gs##(-g71DJ77d?K##G-EyQQ 8s   A.c                    V # r    r_   rr   s   &r   __iter__SequenceGenerator.__iter__  s    r   )re   ra   r   NNNr    )__name__
__module____qualname____firstlineno____doc__re   ra   r   r`   rj   r   rd   rl   rx   r   r   __static_attributes____classdictcell____classcell__ro   __classdict__s   @@r   r]   r]      sj     &R F ! C L!< ' ' 5 5;
R r   r]   zH0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ!@#$%^&*?/>0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ2234679abcdefghjkmnpqrstuvwxyzACDEFGHJKMNPQRTUVWXYZ0123456789abcdef)ascii_72ascii_62ascii_50hexc                   X   a a ] tR tRt oRtRtRtR	V 3R llt]R 4       t	R t
RtVtV ;t# )
WordGeneratori&  a  
Class which generates passwords by randomly choosing from a string of unique characters.

Parameters
----------
:param chars:
    custom character string to draw from.

:param charset:
    predefined charset to draw from.

:param \*\*kwds:
    all other keywords passed to the :class:`SequenceGenerator` parent class.

Attributes
----------
.. autoattribute:: chars
.. autoattribute:: charset
.. autoattribute:: default_charsets
r   Nc                  < V'       d   V'       d   \        R 4      hM+V'       g   V P                  pV'       g   Q h\        V,          pW n        \        VRR7      p\	        VRR7       Wn        \        SV `  ! R/ VB  R# )z,`chars` and `charset` are mutually exclusivecharsrS   Nr_   )r&   charsetdefault_charsetsr   r[   r   ri   rj   )rk   r   r   rm   ro   s   &&&,r   rj   WordGenerator.__init__B  sk     NOO  ,,w$W-E50uG,
 	 4 r   c                ,    \        V P                  4      # r    )r%   r   rr   s   &r   r`   WordGenerator.symbol_countU      4::r   c                X    \        V P                  V P                  V P                  4      # r    )r   r   r   re   rr   s   &r   rx   WordGenerator.__next__Y  s     $((DJJ<<r   )r   r   )NN)r   r   r   r   r   r   r   rj   r   r`   rx   r   r   r   r   s   @@r   r   r   &  s;     , G E!&  = =r   r   c                0    \        RRVRV /VB pV! V4      # )a	  Generate one or more random passwords.

This function uses :mod:`random.SystemRandom` to generate
one or more passwords using various character sets.
The complexity of the password can be specified
by size, or by the desired amount of entropy.

Usage Example::

    >>> # generate a random alphanumeric string with 48 bits of entropy (the default)
    >>> from passlib import pwd
    >>> pwd.genword()
    'DnBHvDjMK6'

    >>> # generate a random hexadecimal string with 52 bits of entropy
    >>> pwd.genword(entropy=52, charset="hex")
    '310f1a7ac793f'

:param entropy:
    Strength of resulting password, measured in 'guessing entropy' bits.
    An appropriate **length** value will be calculated
    based on the requested entropy amount, and the size of the character set.

    This can be a positive integer, or one of the following preset
    strings: ``"weak"`` (24), ``"fair"`` (36),
    ``"strong"`` (48), and ``"secure"`` (56).

    If neither this or **length** is specified, **entropy** will default
    to ``"strong"`` (48).

:param length:
    Size of resulting password, measured in characters.
    If omitted, the size is auto-calculated based on the **entropy** parameter.

    If both **entropy** and **length** are specified,
    the stronger value will be used.

:param returns:
    Controls what this function returns:

    * If ``None`` (the default), this function will generate a single password.
    * If an integer, this function will return a list containing that many passwords.
    * If the ``iter`` constant, will return an iterator that yields passwords.

:param chars:

    Optionally specify custom string of characters to use when randomly
    generating a password. This option cannot be combined with **charset**.

:param charset:

    The predefined character set to draw from (if not specified by **chars**).
    There are currently four presets available:

    * ``"ascii_62"`` (the default) -- all digits and ascii upper & lowercase letters.
      Provides ~5.95 entropy per character.

    * ``"ascii_50"`` -- subset which excludes visually similar characters
      (``1IiLl0Oo5S8B``). Provides ~5.64 entropy per character.

    * ``"ascii_72"`` -- all digits and ascii upper & lowercase letters,
      as well as some punctuation. Provides ~6.17 entropy per character.

    * ``"hex"`` -- Lower case hexadecimal.  Providers 4 bits of entropy per character.

:returns:
    :class:`!str` string containing randomly generated password;
    or list of 1+ passwords if :samp:`returns={int}` is specified.
re   rl   r_   )r   rl   re   r{   rm   gens   &&&, r   genwordr   _  s&    L 
?v
?w
?$
?Cw<r   c                   \        V R4      ;_uu_ 4       pR V 4       p\        ;QJ d    . R V 4       F  NK  	  5M! R V 4       4      pRRR4       \        P                  ! R\	        X4      V 4       V#   + '       g   i     L3; i)a  
load wordset from compressed datafile within package data.
file should be utf-8 encoded

:param asset_path:
    string containing  absolute path to wordset file,
    or "python.module:relative/file/path".

:returns:
    tuple of words, as loaded from specified words file.
zutf-8c              3   @   "   T F  qP                  4       x  K  	  R # 5ir    )striprF   s   & r   r#    _load_wordset.<locals>.<genexpr>  s     +zz||s   c              3   8   "   T F  q'       g   K  Vx  K  	  R # 5ir    r_   rF   s   & r   r#   r     s     3stdddss   	
Nz!loaded %d-element wordset from %r)r4   tupler
   debugr%   )
asset_pathfhr   wordss   &   r   _load_wordsetr     se     
*g	.	."++3s33s33 
/$ LL4c%j*ML' 
/	.s   6A66B	c                   x   a a ] tR tRt oRtRtRtV 3R ltR tR t	R t
R t]R	 4       tR
 tR tR tRtVtV ;t# )WordsetDicti  z
Special mapping used to store dictionary of wordsets.
Different from a regular dict in that some wordsets
may be lazy-loaded from an asset path.
Nc                D   < / V n         / V n        \        SV `  ! V/ VB  R # r    )paths_loadedri   rj   )rk   argsrm   ro   s   &*,r   rj   WordsetDict.__init__  s#    
$'$'r   c                     V P                   V,          #   \         d     Mi ; iT P                  T,          p\        T4      ;q0P                   T&   T# r    )r   KeyErrorr   r   )rk   keyr6   r"   s   &&  r   __getitem__WordsetDict.__getitem__  sP    	<<$$ 		zz#$1$$77S!s    ##c                "    W P                   V&   R# )z+
set asset path to lazy-load wordset from.
N)r   )rk   r   r6   s   &&&r   set_pathWordsetDict.set_path  s     

3r   c                "    W P                   V&   R # r    )r   )rk   r   r"   s   &&&r   __setitem__WordsetDict.__setitem__  s    !Sr   c                    W9   d,   V P                   V V P                  P                  VR 4       R # V P                  V R # r    )r   r   poprk   r   s   &&r   __delitem__WordsetDict.__delitem__  s0    ;S!JJNN3%

3r   c                f    \        V P                  4      pVP                  V P                  4       V# r    )rM   r   updater   )rk   rh   s   & r   _keysetWordsetDict._keyset  s%    4<< DJJr   c                ,    \        V P                  4      # r    )r~   r   rr   s   &r   r   WordsetDict.__iter__  s    DLL!!r   c                ,    \        V P                  4      # r    )r%   r   rr   s   &r   __len__WordsetDict.__len__   s    4<<  r   c                J    WP                   9   ;'       g    WP                  9   # r    r   r   r   s   &&r   __contains__WordsetDict.__contains__  s    ll"77cZZ&77r   r   )r   r   r   r   r   r   r   rj   r   r   r   r   propertyr   r   r   r   r   r   r   r   s   @@r   r   r     sY      E G(
"   
"!8 8r   r   zpasslib:_data/wordsets/z.txtc                   \   a a ] tR tRt oRtRtRtRtR
V 3R llt]	R 4       t
R tR	tVtV ;t# )PhraseGeneratori  a  class which generates passphrases by randomly choosing
from a list of unique words.

:param wordset:
    wordset to draw from.
:param preset:
    name of preset wordlist to use instead of ``wordset``.
:param spaces:
    whether to insert spaces between words in output (defaults to ``True``).
:param \*\*kwds:
    all other keywords passed to the :class:`SequenceGenerator` parent class.

.. autoattribute:: wordset
eff_longN c                X  < Ve   Ve   \        R4      hM'Vf   V P                  pV'       g   Q h\        V,          pWn        \        V\        4      '       g   \        V4      p\        VRR7       W n        Vf   V P                  p\        VRR7      pW0n        \        SV `,  ! R/ VB  R # )Nz,`words` and `wordset` are mutually exclusiver   r   r?   r_   )r&   wordsetdefault_wordsetsrK   _sequence_typesr   r[   r   r?   r   ri   rj   )rk   r   r   r?   rm   ro   s   &&&&,r   rj   PhraseGenerator.__init__*  s    " NOO # ,,w$W-E %11%LEuG,
 ;((CE* 	 4 r   c                ,    \        V P                  4      # r    )r%   r   rr   s   &r   r`   PhraseGenerator.symbol_countG  r   r   c                x   a  V 3R  l\        S P                  4       4       pS P                  P                  V4      # )c              3   n   <"   T F*  pSP                   P                  SP                  4      x  K,  	  R # 5ir    )r   choicer   )r!   r   rk   s   & r   r#   +PhraseGenerator.__next__.<locals>.<genexpr>L  s'     I6H,,6Hs   25)r}   re   r?   rR   )rk   r   s   f r   rx   PhraseGenerator.__next__K  s)    IeDKK6HIxx}}U##r   )r?   r   r   r   )r   r   r   r   r   r   r   r?   rj   r   r`   rx   r   r   r   r   s   @@r   r   r     sB       G E C!:  $ $r   r   c                0    \        RRV RV/VB pV! V4      # )aR  Generate one or more random password / passphrases.

This function uses :mod:`random.SystemRandom` to generate
one or more passwords; it can be configured to generate
alphanumeric passwords, or full english phrases.
The complexity of the password can be specified
by size, or by the desired amount of entropy.

Usage Example::

    >>> # generate random phrase with 48 bits of entropy
    >>> from passlib import pwd
    >>> pwd.genphrase()
    'gangly robbing salt shove'

    >>> # generate a random phrase with 52 bits of entropy
    >>> # using a particular wordset
    >>> pwd.genword(entropy=52, wordset="bip39")
    'wheat dilemma reward rescue diary'

:param entropy:
    Strength of resulting password, measured in 'guessing entropy' bits.
    An appropriate **length** value will be calculated
    based on the requested entropy amount, and the size of the word set.

    This can be a positive integer, or one of the following preset
    strings: ``"weak"`` (24), ``"fair"`` (36),
    ``"strong"`` (48), and ``"secure"`` (56).

    If neither this or **length** is specified, **entropy** will default
    to ``"strong"`` (48).

:param length:
    Length of resulting password, measured in words.
    If omitted, the size is auto-calculated based on the **entropy** parameter.

    If both **entropy** and **length** are specified,
    the stronger value will be used.

:param returns:
    Controls what this function returns:

    * If ``None`` (the default), this function will generate a single password.
    * If an integer, this function will return a list containing that many passwords.
    * If the ``iter`` builtin, will return an iterator that yields passwords.

:param words:

    Optionally specifies a list/set of words to use when randomly generating a passphrase.
    This option cannot be combined with **wordset**.

:param wordset:

    The predefined word set to draw from (if not specified by **words**).
    There are currently four presets available:

    ``"eff_long"`` (the default)

        Wordset containing 7776 english words of ~7 letters.
        Constructed by the EFF, it offers ~12.9 bits of entropy per word.

        This wordset (and the other ``"eff_"`` wordsets)
        were `created by the EFF <https://www.eff.org/deeplinks/2016/07/new-wordlists-random-passphrases>`_
        to aid in generating passwords.  See their announcement page
        for more details about the design & properties of these wordsets.

    ``"eff_short"``

        Wordset containing 1296 english words of ~4.5 letters.
        Constructed by the EFF, it offers ~10.3 bits of entropy per word.

    ``"eff_prefixed"``

        Wordset containing 1296 english words of ~8 letters,
        selected so that they each have a unique 3-character prefix.
        Constructed by the EFF, it offers ~10.3 bits of entropy per word.

    ``"bip39"``

        Wordset of 2048 english words of ~5 letters,
        selected so that they each have a unique 4-character prefix.
        Published as part of Bitcoin's `BIP 39 <https://github.com/bitcoin/bips/blob/master/bip-0039/english.txt>`_,
        this wordset has exactly 11 bits of entropy per word.

        This list offers words that are typically shorter than ``"eff_long"``
        (at the cost of slightly less entropy); and much shorter than
        ``"eff_prefixed"`` (at the cost of a longer unique prefix).

:param sep:
    Optional separator to use when joining words.
    Defaults to ``" "`` (a space), but can be an empty string, a hyphen, etc.

:returns:
    :class:`!str` containing randomly generated passphrase;
    or list of 1+ passphrases if :samp:`returns={int}` is specified.
rl   re   r_   )r   r   s   &&&, r   	genphraser   P  s&    B 
A'
A&
AD
ACw<r   c                V    V ^8  d   Qh/ ^ \         9   d   \        \        ,          ;R&   # )   rJ   )__conditional_annotations__rM   r   )rg   s   "r   __annotate__r      s    f , +c(m +g r   )r   r   r   r   r    )r*   r   )r   	eff_shorteff_prefixedbip39)2r   r2   rN   r5   collectionsr   collections.abcr   r   	importlibr   mathr   r   passlibr	   passlib._loggingr
   passlib.utilsr   r   r   passlib.utils.decorr   __all__dictrb   r   r.   r4   listr   r   rM   	frozensetrL   rJ   r[   r]   r   r   r   r   r   r   namer   r   r   r   )r   s   @r   <module>r      s     	 # 4    # 5 5 1 		%!LXA2 -9
 '*e  +&QRv vt WMA	 6=% 6=rGT F98. 98| =  ?Dd&=dV4$HI ?<$' <$~br   