private RemoteRepositoryServerHandle getRepositoryServerHandle(String defaultUserID,
			TaskMonitor monitor)
			throws IOException, LoginException, CancelledException {

		GhidraServerHandle gsh = getGhidraServerHandle(server, monitor);

		Callback[] callbacks = null;
		try {
			boolean loopOK = allowLoginRetry;
			String loginError = null;
			callbacks = gsh.getAuthenticationCallbacks();

			SignatureCallback pkiSignatureCb = null;
			boolean hasSSHSignatureCallback = false;
			if (callbacks != null) {
				for (Callback cb : callbacks) {
					if (cb instanceof SignatureCallback) {
						pkiSignatureCb = (SignatureCallback) cb;
					}
					else if (cb instanceof SSHSignatureCallback) {
						hasSSHSignatureCallback = true;
					}
				}
			}

			AnonymousCallback onlyAnonymousCb = null;
			while (true) {
				try {
					if (callbacks != null) {
						if (onlyAnonymousCb != null) {
							// First try using no-authentication must have failed - 
							// go ahead and request anonymous access without asking
							onlyAnonymousCb.setAnonymousAccessRequested(true);
							loopOK = false; // final try
						}
						else if (callbacks.length == 1 &&
							callbacks[0] instanceof AnonymousCallback) {
							// Anonymous option available with No-Authentication mode
							// Give no-authentication a chance to work with user-id
							// If it fails, a second try will be done using anonymous access
							onlyAnonymousCb = (AnonymousCallback) callbacks[0];
							loopOK = true;
						}
						else if (hasSSHSignatureCallback && ClientUtil.isSSHKeyAvailable()) {
							// SSH option only available in conjunction with password
							// based authentication which will be used if SSH attempt fails
							hasSSHSignatureCallback = false; // only try SSH once
							ClientUtil.processSSHSignatureCallback(callbacks,
								server.getServerName(), defaultUserID);
						}
						else if (pkiSignatureCb != null) {
							// when using PKI - no other authentication callback will be used
							// if anonymous access allowed, let server validate certificate
							// first and assume anonymous access if user unknown but cert is valid

							if (!ApplicationKeyManagerFactory.initialize()) {
								throw new IOException(
									"Client PKI certificate has not been installed");
							}

							if (ApplicationKeyManagerFactory.usingGeneratedSelfSignedCertificate()) {
								Msg.warn(this,
									"Server connect - client is using self-signed PKI certificate");
							}

							loopOK = false; // only try once
							ClientUtil.processSignatureCallback(server.getServerName(),
								pkiSignatureCb);
						}
						else {
							// assume all other callback scenarios are password based
							// anonymous option must be explicitly chosen over username/password
							// when processing password callback
							if (!ClientUtil.processPasswordCallbacks(callbacks,
								server.getServerName(), defaultUserID, loginError)) {
								return null; // Cancelled by user
							}
						}
					}
					else {
						loopOK = false;
					}
					final RemoteRepositoryServerHandle rsh =
						gsh.getRepositoryServer(getLocalUserSubject(), callbacks);
					if (rsh.isReadOnly()) {
						Msg.showInfo(this, null, "Anonymous Server Login",
							"You have been logged-in anonymously to " + server.getServerName() +
								"\nRead-only permission is granted to repositories which allow anonymous access");
					}
					return rsh;
				}
				catch (FailedLoginException e) {
					if (loopOK) {
						loginError = "Access denied: " + server;
					}
					else {
						throw e;
					}
				}
			}
		}
		catch (AccessException e) {
			throw new IOException(e.getMessage());
		}
		finally {
			if (callbacks != null) {
				for (Callback callback : callbacks) {
					if (callback instanceof PasswordCallback) {
						((PasswordCallback) callback).clearPassword();
					}
				}
			}
		}
	}
Attempts server connection and completes any necessary authentication.
@param defaultUserID default user ID (actual ID used established during authentication)
@param monitor task monitor for connection cancellation
@return server handle or null if authentication or connection attempt was cancelled by user
@throws IOException if server connection fails
@throws LoginException  login failure
Ghidra/Framework/FileSystem/src/main/java/ghidra/framework/client/ServerConnectTask.java