Function: tramp-gvfs-maybe-open-connection

tramp-gvfs-maybe-open-connection is a byte-compiled function defined in tramp-gvfs.el.gz.

Signature

(tramp-gvfs-maybe-open-connection VEC)

Documentation

Maybe open a connection VEC.

Does not do anything if a connection is already open, but re-opens the connection if a previous connection has died for some reason.

Source Code

;; Defined in /usr/src/emacs/lisp/net/tramp-gvfs.el.gz
(defun tramp-gvfs-maybe-open-connection (vec)
  "Maybe open a connection VEC.
Does not do anything if a connection is already open, but re-opens the
connection if a previous connection has died for some reason."
  ;; During completion, don't reopen a new connection.
  (unless (tramp-connectable-p vec)
    (throw 'non-essential 'non-essential))

  ;; For password handling, we need a process bound to the connection
  ;; buffer.  Therefore, we create a dummy process.  Maybe there is a
  ;; better solution?
  (unless (get-buffer-process (tramp-get-connection-buffer vec))
    (let ((p (make-network-process
	      :name (tramp-get-connection-name vec)
	      :buffer (tramp-get-connection-buffer vec)
	      :server t :host 'local :service t :noquery t)))
      (process-put p 'tramp-vector vec)
      (set-process-query-on-exit-flag p nil)

      ;; Set connection-local variables.
      (tramp-set-connection-local-variables vec)))

  (unless (tramp-gvfs-connection-mounted-p vec)
    (let ((method (tramp-file-name-method vec))
	  (user (tramp-file-name-user vec))
	  (host (tramp-file-name-host vec))
	  (localname (tramp-file-name-unquote-localname vec))
	  (object-path
	   (tramp-gvfs-object-path (tramp-make-tramp-file-name vec 'noloc))))

      (when (and (string-equal method "afp")
		 (string-equal localname "/"))
	(tramp-user-error vec "Filename must contain an AFP volume"))

      (when (and (string-match-p (rx "dav" (? "s")) method)
		 (string-equal localname "/"))
	(tramp-user-error vec "Filename must contain a WebDAV share"))

      (when (and (string-equal method "smb")
		 (string-equal localname "/"))
	(tramp-user-error vec "Filename must contain a Windows share"))

      (when (member method tramp-goa-methods)
	;; Ensure that GNOME Online Accounts are cached.
	(tramp-get-goa-accounts vec)
	(when (tramp-get-connection-property
	       (tramp-get-goa-account vec) "FilesDisabled" t)
	  (tramp-user-error
	   vec "There is no Online Account `%s'"
	   (tramp-make-tramp-file-name vec 'noloc))))

      (with-tramp-progress-reporter
	  vec 3
	  (if (tramp-string-empty-or-nil-p user)
	      (format "Opening connection for %s using %s" host method)
	    (format "Opening connection for %s@%s using %s" user host method))

	;; Enable `auth-source'.
	(tramp-set-connection-property
	 vec "first-password-request" tramp-cache-read-persistent-data)

	;; There will be a callback of "askPassword" when a password is needed.
	(dbus-register-method
	 :session dbus-service-emacs object-path
	 tramp-gvfs-interface-mountoperation "askPassword"
	 #'tramp-gvfs-handler-askpassword)
	(dbus-register-method
	 :session dbus-service-emacs object-path
	 tramp-gvfs-interface-mountoperation "AskPassword"
	 #'tramp-gvfs-handler-askpassword)

	;; There could be a callback of "askQuestion" when adding
	;; fingerprints or checking certificates.
	(dbus-register-method
	 :session dbus-service-emacs object-path
	 tramp-gvfs-interface-mountoperation "askQuestion"
	 #'tramp-gvfs-handler-askquestion)
	(dbus-register-method
	 :session dbus-service-emacs object-path
	 tramp-gvfs-interface-mountoperation "AskQuestion"
	 #'tramp-gvfs-handler-askquestion)

	;; The call must be asynchronously, because of the "askPassword"
	;; or "askQuestion" callbacks.
	(if (string-match-p (rx "(so)" eol) tramp-gvfs-mountlocation-signature)
	    (with-tramp-dbus-call-method vec nil
	      :session tramp-gvfs-service-daemon tramp-gvfs-path-mounttracker
	      tramp-gvfs-interface-mounttracker tramp-gvfs-mountlocation
	      (tramp-gvfs-mount-spec vec)
	      `(:struct :string ,(dbus-get-unique-name :session)
			:object-path ,object-path))
	  (with-tramp-dbus-call-method vec nil
	    :session tramp-gvfs-service-daemon tramp-gvfs-path-mounttracker
	    tramp-gvfs-interface-mounttracker tramp-gvfs-mountlocation
	    (tramp-gvfs-mount-spec vec)
	    :string (dbus-get-unique-name :session) :object-path object-path))

	;; We must wait, until the mount is applied.  This will be
	;; indicated by the "mounted" signal, i.e. the "fuse-mountpoint"
	;; file property.
	(with-timeout
	    ((or (tramp-get-method-parameter vec 'tramp-connection-timeout)
		 tramp-connection-timeout)
	     (if (tramp-string-empty-or-nil-p (tramp-file-name-user vec))
		 (tramp-error
		  vec 'file-error
		  "Timeout reached mounting %s using %s" host method)
	       (tramp-error
		vec 'file-error
		"Timeout reached mounting %s@%s using %s" user host method)))
	  (while (not (tramp-get-file-property vec "/" "fuse-mountpoint"))
	    (read-event nil nil 0.1)))

	;; If `tramp-gvfs-handler-askquestion' has returned "No", it
	;; is marked with the fuse-mountpoint "/".  We shall react.
	(when (string-equal
	       (tramp-get-file-property vec "/" "fuse-mountpoint" "") "/")
	  (tramp-error vec 'file-error "FUSE mount denied"))

	;; Save the password.
	(ignore-errors
	  (and (functionp tramp-password-save-function)
	       (funcall tramp-password-save-function)))

	;; Mark it as connected.
	(tramp-set-connection-property
	 (tramp-get-connection-process vec) "connected" t)))))