123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146 |
- (defcustom password-cache t
- "Whether to cache passwords."
- :group 'password
- :type 'boolean)
- (defcustom password-cache-expiry 16
- "How many seconds passwords are cached, or nil to disable expiring.
- Whether passwords are cached at all is controlled by `password-cache'."
- :group 'password
- :type '(choice (const :tag "Never" nil)
- (integer :tag "Seconds")))
- (defvar password-data (make-vector 7 0))
- (defun password-read-from-cache (key)
- "Obtain passphrase for KEY from time-limited passphrase cache.
- Custom variables `password-cache' and `password-cache-expiry'
- regulate cache behavior."
- (and password-cache
- key
- (symbol-value (intern-soft key password-data))))
- (defun password-in-cache-p (key)
- "Check if KEY is in the cache."
- (and password-cache
- key
- (intern-soft key password-data)))
- (defun password-read (prompt &optional key)
- "Read password, for use with KEY, from user, or from cache if wanted.
- KEY indicate the purpose of the password, so the cache can
- separate passwords. The cache is not used if KEY is nil. It is
- typically a string.
- The variable `password-cache' control whether the cache is used."
- (or (password-read-from-cache key)
- (read-passwd prompt)))
- (defun password-read-and-add (prompt &optional key)
- "Read password, for use with KEY, from user, or from cache if wanted.
- Then store the password in the cache. Uses `password-read' and
- `password-cache-add'. Custom variables `password-cache' and
- `password-cache-expiry' regulate cache behavior.
- Warning: the password is cached without checking that it is
- correct. It is better to check the password before caching. If
- you must use this function, take care to check passwords and
- remove incorrect ones from the cache."
- (let ((password (password-read prompt key)))
- (when (and password key)
- (password-cache-add key password))
- password))
- (make-obsolete 'password-read-and-add 'password-read "23.1")
- (defun password-cache-remove (key)
- "Remove password indexed by KEY from password cache.
- This is typically run by a timer setup from `password-cache-add',
- but can be invoked at any time to forcefully remove passwords
- from the cache. This may be useful when it has been detected
- that a password is invalid, so that `password-read' query the
- user again."
- (let ((sym (intern-soft key password-data)))
- (when sym
- (let ((password (symbol-value sym)))
- (when (stringp password)
- (if (fboundp 'clear-string)
- (clear-string password)
- (fillarray password ?_)))
- (unintern key password-data)))))
- (defun password-cache-add (key password)
- "Add password to cache.
- The password is removed by a timer after `password-cache-expiry' seconds."
- (when (and password-cache-expiry (null (intern-soft key password-data)))
- (run-at-time password-cache-expiry nil
- #'password-cache-remove
- key))
- (set (intern key password-data) password)
- nil)
- (defun password-reset ()
- "Clear the password cache."
- (interactive)
- (fillarray password-data 0))
- (provide 'password-cache)
|