Function: epa-file-insert-file-contents
epa-file-insert-file-contents is a byte-compiled function defined in
epa-file.el.gz.
Signature
(epa-file-insert-file-contents FILE &optional VISIT BEG END REPLACE)
Source Code
;; Defined in /usr/src/emacs/lisp/epa-file.el.gz
(defun epa-file-insert-file-contents (file &optional visit beg end replace)
(barf-if-buffer-read-only)
(if (and visit (or beg end))
(error "Attempt to visit less than an entire file"))
(setq file (expand-file-name file))
(let* ((local-copy
(condition-case nil
(epa-file-run-real-handler #'file-local-copy (list file))
(error)))
(local-file (or local-copy file))
(context (epg-make-context))
(buf (current-buffer))
string length entry)
(if visit
(setq buffer-file-name file))
(epg-context-set-passphrase-callback
context
(cons #'epa-file-passphrase-callback-function
local-file))
(epg-context-set-progress-callback
context
(cons #'epa-progress-callback-function
(format "Decrypting %s" file)))
(unwind-protect
(progn
(condition-case error
(setq string (epg-decrypt-file context local-file nil))
(error
(if (setq entry (assoc file epa-file-passphrase-alist))
(setcdr entry nil))
;; If the decryption program can't be found,
;; signal that as a non-file error
;; so that find-file-noselect-1 won't handle it.
;; Borrowed from jka-compr.el.
(if (and (error-has-type-p error 'file-error)
(equal (error-slot-value error 1)
"Searching for program"))
(error "Decryption program `%s' not found"
(error-slot-value error 3)))
(let ((exists (file-exists-p local-file)))
(when exists
(if-let* ((wrong-password (epa--wrong-password-p context)))
;; Don't display the *error* buffer if we just
;; have a wrong password; let the later error
;; handler notify the user.
(epa-file--error-add-context error wrong-password)
(epa-display-error context))
;; When the .gpg file isn't an encrypted file (e.g.,
;; it's a keyring.gpg file instead), then gpg will
;; say "Unexpected exit" as the error message. In
;; that case, just display the bytes.
(if (equal (error-slot-value error 2) "Unexpected; Exit")
(setq string (with-temp-buffer
(insert-file-contents-literally local-file)
(buffer-string)))
;; Hack to prevent find-file from opening empty buffer
;; when decryption failed (bug#6568). See the place
;; where `find-file-not-found-functions' are called in
;; `find-file-noselect-1'.
(setq-local epa-file-error error)
(add-hook 'find-file-not-found-functions
#'epa-file--find-file-not-found-function
nil t)))
;; FIXME: Why does it make sense to add the data fields
;; of ERROR, shifted by one position?
(signal (if exists 'file-error 'file-missing)
(cons "Opening input file" (cdr error))))))
(set-buffer buf) ;In case timer/filter changed/killed it (bug#16029)!
(setq-local epa-file-encrypt-to
(mapcar #'car (epg-context-result-for
context 'encrypted-to)))
(if (or beg end)
(setq string (substring string
(or beg 0)
(and end (min end (length string))))))
(save-excursion
;; If visiting, bind off buffer-file-name so that
;; file-locking will not ask whether we should
;; really edit the buffer.
(let ((buffer-file-name
(if visit nil buffer-file-name)))
(setq length
(if replace
(epa-file--replace-text string file visit beg end)
(epa-file-decode-and-insert
string file visit beg end replace))))
(if visit
(set-visited-file-modtime)))
;; The decoded file could still need another massage from a
;; file name handler, for example a file like
;; "folder.sym.tar.gz.gpg". (Bug#80641)
(when (find-file-name-handler
(file-name-sans-extension file)
'insert-file-contents)
(let ((tmpfile
(make-temp-file
nil nil
(file-name-extension (file-name-base file) 'period))))
(let (file-name-handler-alist) (write-region nil nil tmpfile))
(erase-buffer)
(insert-file-contents tmpfile)
(setq length (- (point-max) (point-min)))
(delete-file tmpfile))))
(if (and local-copy
(file-exists-p local-copy))
(delete-file local-copy)))
(list file length)))