-(defsubst async--value-printable-p (value)
- "Return non-nil if VALUE can be round-tripped to a string prepresentation."
- (condition-case nil
- (let* ((value-string (prin1-to-string value))
- (value-from-string (car (read-from-string value-string))))
- (equal value value-from-string))
- (error nil)))
-
-(defun async--sanitize-closure (func)
- "If FUNC is a closure, delete unprintable lexicals from it."
- (when (eq (car-safe func) 'closure)
- (setf (cadr func)
- (or (loop for obj in (cadr func)
- if (or (not (consp obj))
- (async--value-printable-p (cdr obj)))
- collect obj
- else do
- (when async-debug
- (message "Sanitized var from closure: %s=%S"
- (car obj) (cdr obj))))
- ;; A closure with no lexicals generally has this value
- ;; as its cadr, so we'll use that if everything gets
- ;; filtered out.
- '(t))))
- func)
-
-(defsubst async--get-function (func)
- "Get the function definition of FUNC, whatever it is.
-
-FUNC can be a variable name, "
- (indirect-function
- (cond
- ;; Quoted form => Extract value without evaluating since `(eval
- ;; (quote (closure ...)))' is an error.
- ((memq (car-safe func) '(quote function))
- (cadr func))
- ;; Anything else => eval it
- ;; (e.g. variable or function call)
- (t
- (eval func)))))
-