com.sshtools.ssh2.Ssh2PasswordAuthentication Maven / Gradle / Ivy
The newest version!
/**
* Copyright 2003-2016 SSHTOOLS Limited. All Rights Reserved.
*
* For product documentation visit https://www.sshtools.com/
*
* This file is part of J2SSH Maverick.
*
* J2SSH Maverick is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* J2SSH Maverick is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with J2SSH Maverick. If not, see .
*/
package com.sshtools.ssh2;
import java.io.IOException;
import com.sshtools.ssh.PasswordAuthentication;
import com.sshtools.ssh.SshAuthentication;
import com.sshtools.ssh.SshException;
import com.sshtools.util.ByteArrayWriter;
/**
*
* Implements Password authentication as defined in the SSH Authenticaiton
* Protocol. To use password authentication first construct an instance and set
* the username and password fields.
*
*
* PasswordAuthentication pwd = new PasswordAuthentication();
*
* pwd.setUsername("username");
* pwd.setPassword("password");
*
* int result = ssh.authenticate(pwd);
*
*
*
When the authentication returns the result should be evaluated.
* If the authentication has completed no further processing is required,
* however if the result is failed you should check the password change flag to
* determine if the attempt failed because the user is required to change their
* password. If this is required set the new password on the instance using setNewPassword and call the authentication
* procedure again. If the authenticaiton fails again the password may not be
* acceptable.
*
*
* if (result == SshAuthentication.FAILED) {
* if (pwd.requiresPasswordChange()) {
* pwd.setNewPassword("foo");
*
* // Perform authentication again
* result = ssh.authenticate(pwd);
* }
* }
*
*
*
*
*
*
* @author Lee David Painter
*/
public class Ssh2PasswordAuthentication extends PasswordAuthentication
implements AuthenticationClient {
String newpassword;
boolean passwordChangeRequired = false;
final static int SSH_MSG_USERAUTH_PASSWD_CHANGEREQ = 60;
/**
* Construct the method
*/
public Ssh2PasswordAuthentication() {
}
/**
* After performing an initial authentication attempt a flag may be set to
* indicate that a password change is required. Use this method to set the
* new password and retry the authentication attempt.
*
* @param newpassword
*/
public void setNewPassword(String newpassword) {
this.newpassword = newpassword;
}
/**
* Indicates whether the users password requires changing. This will always
* return false
until after an initial authentication attempt.
* Then it MAY be true
so should always be checked upon a
* failed attempt.
*
* @return true
if the user must change their password
* otherwise false
.
*/
public boolean requiresPasswordChange() {
return passwordChangeRequired;
}
/**
* Implementation of the authentication method.
*
* @param authentication
* @param servicename
* @throws IOException
* @throws AuthenticationResult
*/
public void authenticate(AuthenticationProtocol authentication,
String servicename) throws SshException, AuthenticationResult {
try {
if (getUsername() == null || getPassword() == null) {
throw new SshException("Username or password not set!",
SshException.BAD_API_USAGE);
}
if (passwordChangeRequired && newpassword == null) {
throw new SshException("You must set a new password!",
SshException.BAD_API_USAGE);
}
ByteArrayWriter msg = new ByteArrayWriter();
try {
msg.writeBoolean(passwordChangeRequired);
msg.writeString(getPassword());
if (passwordChangeRequired) {
msg.writeString(newpassword);
}
authentication.sendRequest(getUsername(), servicename,
"password", msg.toByteArray());
} finally {
try {
msg.close();
} catch (IOException e) {
}
}
// We need to read the response since we may have password change.
byte[] response = authentication.readMessage();
if (response[0] != SSH_MSG_USERAUTH_PASSWD_CHANGEREQ) {
authentication.transport.disconnect(
TransportProtocol.PROTOCOL_ERROR,
"Unexpected message received");
throw new SshException(
"Unexpected response from Authentication Protocol",
SshException.PROTOCOL_VIOLATION);
}
passwordChangeRequired = true;
throw new AuthenticationResult(SshAuthentication.FAILED);
} catch (IOException ex) {
throw new SshException(ex, SshException.INTERNAL_ERROR);
}
}
}