jsch-0.1.53/0000755000000000000000000000000012534213235011225 5ustar rootrootjsch-0.1.53/ChangeLog0000644000000000000000000013500612534213037013004 0ustar rootrootChangeLog of JSch ==================================================================== Last modified: Fri Jun 5 03:22:57 UTC 2015 Changes since version 0.1.52: - bugfix: the rekey initiated by the remote may crash the session. - change: Logjam: use ecdh-sha2-nistp* if available, ecdh-sha2-nistp256,ecdh-sha2-nistp384,ecdh-sha2-nistp521, diffie-hellman-group14-sha1, diffie-hellman-group-exchange-sha256, diffie-hellman-group-exchange-sha1,diffie-hellman-group1-sha1 - change: Logjam: diffie-hellman-group-exchange-sha256 and diffie-hellman-group-exchange-sha1 will use 2048-bit key on Java8's SunJCE, thanks to JDK-6521495 and JDK-7044060. - change: key words for OpenSSH's config file should be case-insensitive. - change: there should be the host name in "WARNING: REMOTE HOST IDENTIFICATION HAS CHANGED" message. Changes since version 0.1.51: - bugfix: resource leak: duplicate keys in LocalIdentityRepository. - feature: added the support for SSH ECC defined in RFC5656, ecdsa-sha2-nistp256, ecdsa-sha2-nistp384, ecdsa-sha2-nistp521, ecdh-sha2-nistp256, ecdh-sha2-nistp384, ecdh-sha2-nistp521 This functionality requires Java7 or later. - feature: added the support for server host keys in ecdsa-sha2-nistp256, ecdsa-sha2-nistp384, ecdsa-sha2-nistp521 - feature: generating key-pairs in ecdh-sha2-nistp256, ecdh-sha2-nistp384, ecdh-sha2-nistp521 - change: aes192-ctr, aes256-ctr and diffie-hellman-group-exchange-sha256 have been enabled by the default. - change: key exchange methods, ecdh-sha2-nistp256, ecdh-sha2-nistp384 and ecdh-sha2-nistp521 have been enabled by the default. - change: the support for host keys in ecdsa-sha2-nistp256, ecdsa-sha2-nistp384 and ecdsa-sha2-nistp521 have been enabled by the default. - change: 'examples/KeyGen.java' demonstrates how to generate ecdsa-sha2-* key-pairs. - change: updating copyright messages; 2014 -> 2015 - TODO: The ECC support is not functional on Java6 with BouncyCastle. Changes since version 0.1.50: - bugfix: reproducibility of "verify: false". FIXED. Hundreds of thousands of connections had caused that exception. - bugfix: resource leaks at the failure of making local port forwarding. FIXED. - bugfix: NPE in connecting to the non-standard TCP port. FIXED. This problem had appeared if a host-key does not exist in "known_host" file. - bugfix: TCP connection may not be dropped if error messages from the remote are too long. FIXED. - bugfix: SftpATTRS#getAtimeString() returns the wrong string. FIXED. - bugfix: bytes to be added by SSH_MSG_CHANNEL_WINDOW_ADJUST must be in unsigned integer. FIXED. - bugfix: Util#checkTilde() should not convert a tilde in "C:\PROGRA~1\". FIXED. - bugfix: A long long command for ChannelExec will cause an ArrayIndexOutOfBoundsException. FIXED. - bugfix: ChannelSftp should not send bulk request greedily even if the remote window has the enough space. FIXED. - bugfix: Util.createSocket() should throw an exception with 'cause'. FIXED. - bugfix: failed to parse .ssh/config in the EBCDIC environment. FIXED. - bugfix: com.jcraft.jsch.jcraft.HMACSHA1(used only for MacOSX) is not reusable. FIXED. - bugfix: NPE caused by the delayed response for channel opening requests. FIXED. - bugfix: hung-up in uploading huge data to ProFTPd without the config 'SFTPClientMatch "JSCH.*" channelWindowSize 1GB' FIXED. - bugfix: Cipher#init() may cause an infinite loop with 100% cpu use due to https://bugs.openjdk.java.net/browse/JDK-8028627 FIXED. - bugfix: in some case, JSche#setKnowHosts(InputStream stream) may fail to close the given stream. FIXED - change: com.jcraft.jsch.jcraft.HMAC* will not be used. It seems Java6 on Mac OS X has fixed some memory leak bug in JCE, so there is no reason to use c.j.j.j.HMAC* introduced at 0.1.30. - change: updating copyright messages; 2013 -> 2014 - change: allowed to create the symbolic/hard link to the relative path by ChannelSftp#symlink(String oldpath, String newpath) ChannelSftp#hardlink(String oldpath, String newpath) - change: the availability of ciphers listed in "CheckCiphers" config will not be checked if they are not used. - change: Util#fromBase64() will throw JSchException in stead of RuntimeException, if the given string is not in base64 format. - feature: added the support for private keys in PKCS#8 format. - feature: introduced the interface com.jcraft.jsch.PBKDF to abstract the implementation of Password-Based Key Derivation Function, and added its implementation com.jcraft.jsch.jce.PBKDF by using JCE. Changes since version 0.1.49: - bugfix: "verify: false" error on Java7u6(and later). FIXED. http://stackoverflow.com/questions/12279836/ssh-using-jschexception-verify-false-sometimes-fails https://issues.apache.org/jira/browse/IVY-1374 - bugfix: Session#setPortForwardingL(String bind_address, int lport, String host, int rport) will not work for the long host name. FIXED. - change: changed JSch#getIdentityRepository() to be public. - feature: added the following method to choose a canceled remote port-forwarding with the specified bind address, Session#delPortForwardingR(String bind_address, int rport) - feature: added support for following OpenSSH's sftp extensions, posix-rename@openssh.com, statvfs@openssh.com, hardlink@openssh.com, and some methods and a class to use those functionalities, ChannelSftp#hardlink(String oldpath, String newpath), ChannelSftp#statVFS(String path) SftpStatVFS - feature: added support for OpenSSH's configuration file, JSch#setConfigRepository(ConfigRepository configRepository) JSch#getConfigRepository() OpenSSHConfig class Session#getSession(String host) and added an example to demonstrate how to use it, examples/OpenSSHConfig.java OpenSSHConfig class will recognize the following keywords, Host User Hostname Port PreferredAuthentications IdentityFile NumberOfPasswordPrompts ConnectTimeout HostKeyAlias UserKnownHostsFile KexAlgorithms HostKeyAlgorithms Ciphers Macs Compression CompressionLevel ForwardAgent RequestTTY ServerAliveInterval LocalForward RemoteForward ClearAllForwardings - feature: added support for "diffie-hellman-group-exchange-sha256" - feature: allowed to use tilde(~) in the file name, JSch#setIdentity(String prvkey, String pubkey) JSch#setKnownHosts(String prvkey, String pubkey) - feature: added support for known_hosts file, which may include markers(@revoke) and comments. HostKey(String host, int type, byte[] key, String comment) HostKey(String marker, String host, int type, byte[] key, String comment) HostKey#getComment() HostKey#getMarker() - feature: added following methods to KeyPar class, writePrivateKey(java.io.OutputStream out, byte[] passphrase) writePrivateKey(String name, byte[] passphrase) - feature: allowed to set the connection timeout for the local port-forwarding, and added following methods, Session#setPortForwardingL(String bind_address, int lport, String host, int rport, ServerSocketFactory ssf, int connectTimeout) ChannelDirectTCPIP#connect(int connectTimeout) - feature: added the following method to Session class getStreamForwarder(String host, int port) and updated example/StreamForwarding.java to use that method. - feature: added following methods to Session class, setPortForwardingL(String conf) setPortForwardingR(String conf) - feature: allowed to have the session local HostkeyRepository, Session#setHostKeyRepository(HostKeyRepository hostkeyRepository) Session#getHostKeyRepository() - feature: added support for OpenSSH's local extension, "no-more-sessions@openssh.com" and the method, Session#noMoreSessionChannels() Changes since version 0.1.48: - bugfix: Some sftp servers will sometimes fail to handle bulk requests, and whenever detecting such failures, we should re-send requests again and again. FIXED - bugfix: KeyPair#getFingerPrint() should return a fingerprint instead of keysize + " " + fingerprint. FIXED - bugfix: KeyPair#getKeySize() should return its key size. FIXED - bugfix: SftpATTRS#isDir() should return false for unix domain socket files. FIXED - change: improved the heuristics for the password prompt in the keyboard-interactive authentication. It may not be started with "password:". - change: ChannelSftp#put(InputStream src, String dst) will not check if dst is directory or not, and if an exception is thrown, the check will be done. - change: if the compression is enabled without jzlib.jar, an exception will be thrown. - feature: JSch#addIdentity() and KeyPair#load() methods will accept Putty's private key files. Note that Putty encrypts its private key with "aes256-cbc". So, to handle such key files, "Java Cryptography Extension (JCE) Unlimited Strength Jurisdiction Policy Files" must be installed. - feature: hmac-sha2-256 defined in RFC6668 is supported. - feature: added following methods to KeyPair class, byte[] getSignature(byte[] data) Signature getVerifier() byte[] forSSHAgent() void setPublicKeyComment(String comment) - feature: added following methods to SftpATTR class, boolean isChr() boolean isBlk() boolean isFifo() boolean isSock() Changes since version 0.1.47: - change: the file transfer speed with ChannelSftp#get(String src) has been improved; sending multiple requests at any one time. - change: by the default, at most, 16 requests will be sent at any one time in ChannelSftp. - feature: added Session#{setIdentityRepository(),getIdentityRepository()} Changes since version 0.1.46: - bugfix: failed to initialize channels for the stream forwarding. FIXED - change: Session#getHostKey() will return the given hostkey even if session is not established. - change: Logger will record additional messages about algorithm negotiations. - feature: added ChannelSftp#ls(String path, LsEntrySelector selector) method. - feature: added IdentityRepository#{getName(),getStatus()} methods. Changes since version 0.1.45: - bugfix: in the agent forwarding mode, "ssh-add -l" on the remote will freeze. FIXED - bugfix: requests should not be sent to the closed channel. FIXED - bugfix: ChannelShell#setAgentForwarding(true) will cause resource leaks. FIXED - change: for the efficiency, channel opening will be delayed in local port forwarding. - change: added examples/Sudo.java to demonstrate sudo on exec channel. - change: authentication trials will be failed at 6 failures by the default. - change: updating copyright messages; 2011 -> 2012 - feature: added JSch#setIdentityRepository(IdentityRepository irepo) to integrate with jsch-agent-proxy. Changes since version 0.1.44: - bugfix: fields referred by multiple threads simultaneously should be volatile. FIXED - bugfix: use local window size offered by the remote in sftp put. FIXED - bugfix: SftpProgressMonitor#init was not invoked in sftp-put for input-stream. FIXED - bugfix: sftp protocol version 3, 4 and 5 should allow only UTF-8 encoding. FIXED - bugfix: Channel Subsystem had failed to set X forwarding flag. FIXED - bugfix: Channel X11 had leaked some resources. FIXED - bugfix: packet compression may break sessions in some case(transferring deflated data). FIXED - bugfix: failed to set dev-null for logger FIXED - bugfix: even in sftp protocol version 3 session, some sftpd sends data packets defined in sftp protocol 6 ;-( working around it. FIXED - bugfix: ChannelSftp file globbing logic had missed the string "foo\\\*bar" as a pattern. FIXED - bugfix: sequential accesses to ChannelSftp by multiple threads may break its I/O channel. https://bugs.eclipse.org/bugs/show_bug.cgi?id=359184 FIXED - bugfix: KeyPair.load can not handle private keys cyphered with AES. FIXED - change: to improve sftp-put performance, send multiple packet at one time. - change: wait/notify will be used instead of sleep loop in establishing channel connections. - change: increasing local window size for sftp get. - change: updating copyright messages; 2010 -> 2011 - change: src/com -> src/main/java/com - feature: key-exchange method "diffie-hellman-group14-sha1" (RFC4253#section-8.2) - feature: KeyPair#getPlulicKeyCommment() is added. Changes since version 0.1.43: - bugfix: hmac-md5-96 and hmac-sha1-96 are broken. FIXED. - bugfix: working around OOME in parsing broken data from the remote. FIXED. - bugfix: failed to send very long command for exec channels. FIXED. - bugfix: in some case, failed to get the response for remote port-forwarding request. FIXED. - feature: support for private keys ciphered with aes192-cbc and aes128-cbc. Changes since version 0.1.42: - bugfix: the remote window size must be in unsigned int. FIXED. - bugfix: support for EBCDIC environment. FIXED. - bugfix: data may be written to the closed channel. FIXED. - bugfix: NPE in closing channels. FIXED. - bugfix: the private key file may include garbage data before its header. FIXED. - bugfix: the session down may not be detected during the re-keying process. FIXED. - change: try keyboard-interactive auth with the given password if UserInfo is not given. - change: working around the wrong auth method list sent by some SSHD in the partial auth success. - change: working around the CPNI-957037 Plain-text Recovery Attack. - change: in searching for [host]:non-default port in known_hosts, host:22 should be also checked. - change: updating copyright messages; 2009 -> 2010 Changes since version 0.1.41: - bugfix: making exec request during re-keying process will cause the dead lock for the session. FIXED. Many thanks for PanLi at Prominic dot NET and www.prominic.net, US based hosting company. Without their testing JSch with hundreds of hosts and their bug reports, this problem was not fixed. - change: updating copyright messages; 2008 -> 2009 Changes since version 0.1.40: - bugfix: canceling the remote port-forwarding with the incorrect bind-address. FIXED. - bugfix: sftp had missed to close the file in some case. FIXED. - bugfix: ls(sftp) will throw an exception for the empty directory in connecting to some sftpd server. FIXED. - change: dropping the session gently in accepting incorrect packets. - change: by the default, aes128-ctr will be chosen if it is available on the local and the remote. - feature: adding the support for the private key ciphered in AES256. - feature: new ciphers: aes128-ctr,aes192-ctr,aes256-ctr, 3des-ctr,arcfour,arcfour128 ,arcfour256 Changes since version 0.1.39: - bugfix: ProxySOCKS4 had not been functional. FIXED. - bugfix: NPE at closing the session when it is not opened. FIXED. - change: JSch#getConfing has become public. Changes since version 0.1.38: - bugfix: session will be dropped at rekeying. FIXED. - bugfix: NPE should not be thrown at unexpected session drop. FIXED. - change: Channel#getSession() may throw JSchExecption. Changes since version 0.1.37: - bugfix: NPE should not be thrown at unexpected session drop. FIXED. - bugfix: AIOOBE at Session#connect(). FIXED. - bugfix: Even if 'true' is given for Channel#setOutputStream(OutputStream out, boolean dontclose) as the second paramter, 'out' will be closed. FIXED. - change: 'examples/Sftp.java' has been modified to demonstrate ChannelSftp#reaplpath(String path) - change: setEnv(Hashtable env) for exec and shell channels have been marked as @deprecated - feature: setEnv(String name, String value) has been added to exec and shell channels. - feature: setEnv(byte[] name, byte[] value) has been added to exec and shell channels. - feature: ChannelSftp#realpath(String path) has been added. - feature: ChannelExec#setCommand(byte[] command) has been added. - feature: com.jcraft.jsch.ChannelSftp.LsEntry has implemented java.lang.Comparable - feature: Session#getServerAliveInterval(), Session#getServerAliveCountMaX() have been added. Changes since version 0.1.36: - bugfix: some sftpd will send invalid data in sftp protocol point of view, and we need to work around such data. FIXED. - bugfix: the stream forwarding had been broken since 0.1.30. FIXED. - bugfix: failed to detect 'SSH_MSG_CHANNEL_OPEN_FAILURE'. FIXED. - bugfix: ChannelSftp will generate the unfavorable absolute pathname in some case. FIXED. - bugfix: failed to ignore the invalid public-key file. FIXED. - change: ignoring empty data sent by 'SSH_MSG_CHANNEL_DATA' and 'SSH_MSG_CHANNEL_EXTENDED_DATA'. - change: updating copyright messages; 2007 -> 2008 - change: build.xml will enable 'javac.debug' option by the default. - change: added logging messages to IndentityFile and Session class. - change: followings are deprecated methods, InputStream ChannelSftp#get(String src, int mode) InputStream ChannelSftp#get(String src, SftpProgressMonitor, int mode) - feature: following method is added, InputStream ChannelSftp#get(String src, SftpProgressMonitor monitor, long skip) Changes since version 0.1.35: - bugfix: ChannelSftp can not handle the local filenames correctly on Windows. FIXED. - bugfix: '/' must be handled as the file separator on JVM for Windows. FIXED. - change: the system property "javax.security.auth.useSubjectCredsOnly" will be set to "false" for "gssapi-with-mic" if that property is not given explicitly. - change: added changes about ChannelSftp#{pwd(), home()} to ChangeLog; 'Changes since version 0.1.34:' section. Changes since version 0.1.34: - bugfix: the OutputStream from the channel may make the JVM lockup in some case. FIXED. There was a possibility that Channel#connect() may be failed to initialize its internal without throwing the JSchException. On such case, the write operation for OutputStream from that channel will cause the system(JVM) to lock up. - bugfix: ChannelSftp had problems filename globbing. FIXED. - bugfix: the message included in SSH_FXP_STATUS must be UTF-8. FIXED. - change: ChannelSftp supports the filename globbing for the filename in multi-byte characters. - change: ChannelSftp will internally handle filenames in UTF-8 encoding. - change: ChannelSftp#pwd() may throw an SftpException. - change: ChannelSftp#home() may throw an SftpException. - feature: following methods have been added in ChannelSftp String getServerVersion() String getClientVersion() void setFilenameEncoding(String encoding) String getExtension(String key) Changes since version 0.1.33: - bugfix: there had a possibility that the session may be broken if ciphers for upward/downward streams are different. FIXED. - bugfix: the authentication method "keyboard-interactive" had not been tried without UserInfo. FIXED. - bugfix: ChannelShell#setTerminalMode(byte[] terminal_mode) had not been functional. FIXED. - bugfix: the remote port-forwarding to the daemon had been broken since 0.1.30. FIXED. - change: the cipher "aes128-cbc" will be used if AES is available. - change: the interface 'com.jcraft.jsch.ForwardedTCPIPDaemon' has been changed. - change: the data transfer rate will be improved on some environment. - feature: ChannelExec can control the size of pty; ChannelExec#setPtySize(int col, int row, int wp, int hp) is added. - feature: the property "CheckCiphers" has been added. Refer to 'examples/AES.java'. - feature: Session#setConfig(String key, String value), JSch#setConfig(String key, String value) have been added. Changes since version 0.1.32: - bugfix: freeze in 'diffie-hellman-group-exchange-sha1'. FIXED. By the default, 'diffie-hellman-group1-sha1' will be used and if you have not chosen 'diffie-hellman-group-exchange-sha1' explicitly, you don't have to worry about it. - bugfix: there should be timeout mechanism in opening a socket for remote port forwarding. FIXED. At the failure or timeout, 'SSH_MSG_CHANNEL_OPEN_FAILURE' will be sent to sshd. - bugfix: there should be timeout mechanism in opening a socket for X11 forwarding. FIXED. At the failure or timeout, 'SSH_MSG_CHANNEL_OPEN_FAILURE' will be sent to sshd. Changes since version 0.1.31: - bugfix: remote port forwarding will be hanged at its closing. FIXED. - bugfix: X forwarding channels will be hanged and some resources will be leaked whenever they are closed. FIXED. - bugfix: failed to detect "Connection refused". FIXED. - bugfix: at the failure for keyboard-interactive auth method, a session will be terminated. FIXED. - bugfix: due to the cancel for keyboard-interactive auth method, a session will be terminated. FIXED. - change: com.jcraft.jsch.jcraft.Compression#uncompress will respect the argument "start". - change: "gssapi-with-mic" will choose the default credential. - feature: Session#setPortForwardingL will return the assigned local TCP port number; TCP port will be assigned dynamically if lport==0. - feature: support for SSH_MSG_UNIMPLEMENTED. - feature: support for PASSWD_CHANGEREQ. Changes since version 0.1.30: - bugfix: a problem in padding for ciphered private key. PKCS#5 padding should be used. FIXED. - bugfix: crash in parsing invalid public key file. FIXED. - bugfix: a public key may not have a comment. FIXED. - bugfix: output stream from ChannelSftp#put will hang if it is closed twice. FIXED. - feature: agent forwarding. To enable this functionality, Channel{Exec,Shell,Sftp}#setAgentForwarding(boolean enable) are added. - feature: ChannelShell#setTerminalMode(byte[] terminal_mode) is added. - feature: Session#setDaemonThread(boolean true) to run internal threads as daemon threads. - feature: an option "PreferredAuthentications" is added. The default value is "gssapi-with-mic,publickey,keyboard-interactive,password". - change: if alias-name is given, non-standard TCP port number will not be saved in 'known_hosts' file. Changes since version 0.1.29: - bugfix: ChannelSftp#cd() will not throw an exception even if a file is given. FIXED. - bugfix: ChannelSftp#put() has a bug which will appear in using on the slow network. FIXED. - bugfix: ChannelSftp#ls() has a bug which will appear in using on the slow network. FIXED. - bugfix: a bug had sneaked in the remote port forwarding. FIXED. - bugfix: some APIs from JCE have the memory leak on Mac OS X, so we have re-written the code(com.jcraft.jsch.jcraft.HMAC* classes) without them. On Mac OS X, such new classes will be used automatically. FIXED. - bugfix: the session will be crashed by the long banner message. FIXED. - change: '/dev/random' will not be referred on Gnu/Linux. - change: if non-standard TCP port number is used, that number will be saved in known_hosts file as recent OpenSSH's ssh client does. - change: Channel#getOutputStream will not use Piped{Output,Input}Stream. - change: com.jcraft.jsch.HostKeyRepository interface has been slightly modified. - feature: Session#setPortForwardingR(String bind_address, ...) has been added. - feature: the packet compression method 'zlib@openssh.com' has been supported. - feature: the hashed known_hosts file has been supported. Refer to 'examples/KnownHosts.java'. - feature: the authentication method 'gssapi-with-mic' has been experimentally supported. - feature: com.jcraft.jsch.Logger interface and JSch#setLogger(Logger logger) have been added. Refer to 'examples/Logger.java' for the usage. Changes since version 0.1.28: - bugfix: ChannelSftp#put will stack in some situations FIXED. - bugfix: ChannelSftp invoked 'glob_remote' redundantly. FIXED. - bugfix: ChannelSftp failed to make globbing for some file names. FIXED. - bugfix: ChannelSftp did not carefully read its input-stream. FIXED. - bugfix: ChannelSftp#lstat did not try globbing for given path. FIXED. - bugfix: at closing channel, eof_lcoal and eof_remote did not become true. FIXED. - bugfix: IdentityFile did not carefully read file input-streams. FIXED. - bugfix: KeyPair did not carefully read file input-streams. FIXED. - bugfix: ProxySOCKS4 did not carefully read file input-streams. FIXED. - bugfix: ProxySOCKS5 did not carefully read file input-streams. FIXED. - bugfix: ForwardedTCPIPDaemom may fail in some situation. FIXED. - bugfix: X forwarding failed to handle the magic-cookie in some case FIXED. Thanks to Walter Pfannenmller. - bugfix: setKnownHosts in KnownHosts.java doesn't read the last line if linefeed is missing FIXED. Thanks to Henrik Langos. - bugfix: With StrictHostKeyChecking set to yes connect() shouldn't ask. FIXED. Thanks to Henrik Langos. - change: Identity#setPassphrase(String passphrase) is replaced with Identity#setPassphrase(byte[] passphrase). - change: IdentityFile will clear its internal secrets at finalizing. - change: KeyPair will clear its internal secrets at finalizing. - change: KeyPair will clear its internal secrets at finalizing. - change: MAC#doFinal() is replaced with MAC#doFile(byte[] buf, int offset) - change: at TCP socket reading timeout, keep-alive message will be sent to the remote sshd. To disable this functionality, invoke explicitly Session.setServerAliveCountMax(0) - change: PortWatcher stops to use InetAddress.getByAddress(). - change: in the user authentication, username, password and passphrase will be encoded in UTF-8. - change: JSch#addIdentity will check duplicate keys. - change: SftpException#message has been deleted. - change: SftpException#getMessage() will return the detailed message. - feature: IdentityFile#setPassphrase(byte[] passphrase) is added. - feature: IdentityFile#clear() is added to clear its internal secrets. - feature: KeyPair#decrypt(byte[] passphrase) is added. - feature: JSch#addIdentity(String path, byte[] passphrase) is added. - feature: JSch#getIdentityNames() is added. - feature: JSch#removeIdentity(String name) is added. - feature: JSch#removeAllIdentity() is added. - feature: ChannelSftp#readlink(String path) is added. - feature: ChannelSftp#getHome() is added. - feature: Channel#connect(int connectTimeout) is added. - feature: ChannelShell#setPtyType(String ttype) is added. - feature: Session#setPassword(byte[] password) is added. - feature: Session#setHostKeyAlias(String alias) is added. - feature: KeepAlive is implemented and Session#setServerAliveInterval(int interval) and Session#setServerAliveCountMax(int count) are added. - feature: Session#sendKeepAliveMsg() is added. - feature: JSchException#getCause() may return a reason. - feature: SftpException#getCause() may return a reason. - feature: ChannelExec#setErrStream(OutputStream out, boolean dontclose) is added. Changes since version 0.1.27: - bugfix: ChannelSftp#localAbsolutePath did not work correctly. FIXED. - bugfix: ChannelSftp#chmod did not work for directory. FIXED. - bugfix: ProxyHTTP had a bug in processing HTTP headers. FIXED. - bugfix: messages before server's version string should be ignored. FIXED. - feature: Environment Variable Passing. Changes since version 0.1.26: - bugfix: there was a session crash bug. That occurrence is rare, but depends on the thread scheduling. FIXED. - bugfix: problems in generating remote/local absolute paths on sftp. FIXED. - bugfix: problems in handling cancel operations for sftp. FIXED. - bugfix: ChannelX11s were not terminated for a wrong cookie. FIXED. - bugfix: NoSuchAlgorithmException should be thrown if JCE is not accessible. FIXED. - bugfix: ProxyHTTP should check the return code from proxy. FIXED. - bugfix: server's version string should be checked carefully. FIXED. - feature: some more improvements on sftp uploading. - feature: 'getUserName' method is added to Session class. Changes since version 0.1.25: - bugfix: infinite loop/hang on connection at unexpected error during key-exchanging operation. FIXED - bugfix: delays on sftp uploading. FIXED - bugfix: failed to purge a host-key from its repository in some case. FIXED. - feature: SOCKS4 proxy Changes since version 0.1.24: - bugfix: remote port forwarding is not established. FIXED. - bugfix: failed to parse known_hosts file if it has a long public key blob. FIXED. - bugfix: sftp put/get operations keep failing. FIXED. - bugfix: ChannelShell.setXForwarding always set xforwarding to be true. FIXED. - change: ChannelShell.setPty is added. - change: Proxy interface is free from session object. - change: added examples/ScpToNoneCipher.java to demonstrate NONE Cipher switching. - feature: added NONE Cipher switching support. - feature: timeout check will be enabled for proxy connections. Changes since version 0.1.23: - bugfix: there was resource leak problems in closing local port forwardings. FIXED. - bugfix: there was a session crash problems in using aes-cbc cipher. FIXED. - change: ChannelSession.setPtySize was redefined. - feature: added SocketFactory for remote port forwarding. Session.setPortForwardingR(int rport, String host, int lport, SocketFactory sf) - feature: added ServerSocketFactory for local port forwarding. Session.setPortForwardingL(String boundaddress, int lport, String host, int rport, ServerSocketFactory ssf) Changes since version 0.1.22: - bugfix: there was a freeze problem at fails on key-exchanging. FIXED. - bugfix: race-condition forcefully disconnects session in closing channels. FIXED. Changes since version 0.1.21: - bugfix: there is a bug in read() method implementation for the input-stream returned from ChannelSftp.get(). FIXED. - bugfix: at fail on requesting for the remote port forwarding, an exception should be thrown. FIXED. - bugfix: SSH_MSG_CHANNEL_OPEN request for the X11 forwarding should not be accepted if clients don not expect it. FIXED. - bugfix: there is a problem in transferring large data(mote than 1GB) to sshd from recent OpenSSH(3.6.1 or later). FIXED. For security concerns, those sshd will re-key periodically and jsch had failed to handle it. - bugfix: 'exec', 'shell' and 'sftp' channels will fail if the acceptable packet size by remote sshd is not so large. FIXED. - bugfix: there are problems in 'InputStream ChannelSftp.get(String)' and 'OutputStream put(String)'. FIXED. - feature: added boolean flag 'dontclose' to * setInputStream(), * setOutputStream() and * setExtOutputStream() methods of Channel class. - feature: added 'com.jcraft.jsch.ChannelSubsystem' - feature: allowed to control the compression level in the packet compression. Refer to 'examples/Compression.java'. - change: modified 'com/jcraft/jsch/jce/KeyPairGenRSA.java' to be complied on JDK 1.2. - change: 'examples/ScpTo.java' and 'examples/ScpFrom.java' will use 'long' type for the file size instead of 'int'. - change: 'Identity.getSignature' method will not expect 'session'. - change: while waiting for socket connection establishment, Thread.join will be used instead of Thread.sleep. Changes since version 0.1.20: - known issue: there are problems in 'InputStream ChannelSftp.get(String)' and 'OutputStream put(String)'. They will be re-implemented in the next release. - bugfix: EOF packets should not be sent twice. This bug had crashed the session on every channel close. FIXED. - bugfix: at the fail on opening connection to remote sshd, a misleading exception "invalid server's version string" had been thrown. FIXED. - bugfix: fixed a bug in hadling the size of remote channel window. - bugfix: channels should not be closed even if EOF is received. FIXED. - bugfix: fixed bugs in file name globbing on sftp. - change: to transfer packets efficiently, the size of internal buffer for each channel has been increased. - change: ChannelSftp.ls will return a vector of com.jcraft.jsch.ChannelSftp.LsEntry. Sorry for inconveniences. - feature: added ForwardedTCPIPDaemon. Refer to 'examples/Daemon.java', which demonstrates to provide network services like inetd. - feature: ChannelExec.setPty() method to request for assigning pseudo tty. - feature: added ciphers "aes128-cbc", "aes192-cbc" and "aes256-cbc". Refer to 'examples/AES.java'. - feature: local port-forwarding settings can be dynamically deleted by the bound address. - feature: added 'Channel.isClosed()'. Channel.getExitStatus() should be invoked after Channel.isClosed()==true. Changes since version 0.1.19: - ClassCastException while calling ChannelExec.finalize() method. FIXED. Thanks to wswiatek at ais dot pl. Changes since version 0.1.18: - fixed problems related to thread-safety. Thanks to Eric Meek at cs dot utk dot edu. - At the lost of the network connectivity to the remote SSHD, clients connected to the local port were never made aware of the disconnection. FIXED. - fixed confusions in handling EOFs from local input stream and the input stream for remote process. - 'com.jcraft.jsch.jce.AES128CBC' is added, but it is not be functional in this release. It will work in the next release. - Some sshd(Foxit-WAC-Serve) waits for SSH_MSG_NEWKEYS request before sending it. FIXED. - fixed a problem in connecting to Cisco Devices. Thanks to Jason Jeffords at comcast dot net. - changed the method 'add' of 'HostKeyRepository' interface. - 'UIKeyborarInteracetive' will ignore empty prompt by sshd. - added 'sendIgnore()' method to 'Session' class. - added '-p' for scp command in 'examples/ScpTo.java' to preserve modification times, access times, and modes from the original file. Changes since version 0.1.17: - added 'com.jcraft.jsch.HostKeyRepository' interface. It will allow you to handle host keys in your own repository (for example, RDB) instead of using 'known_hosts' file. - added methods to get the finger-print of host keys. refer to 'examples/KnownHosts.java'. - improved 'known_hosts' file handling. - comment lines will be kept. - SSH1 host keys will be kept. - each hostname can have multiple host keys. - fixed a crash bug in processing private keys which have too long key-bits. Changes since version 0.1.16: - 'com.jcraft.jsch.jce.DHG1' and 'com.jcraft.jsch.jce.DHGEX' are moved to 'com.jcraft.jsch' package. - added APIs to handle hostkeys included in 'known_hosts', JSch.getHostKeys(), JSch.removeHostKey() - allowing to set timeout value in opening sockets, Session.connect(int timeout) Changes since version 0.1.15: - adding support of setting mtime for remote files on sftp channel. - setKnownHosts method of JSch class will accept InputStream. - implementation of Basic password authentication for HTTP proxy. - fixed a bug in checking which ssh protocol version remote sshd supports - SSH_MSG_CHANNEL_OPEN_FAILURE will be handled correctly. - methods in SftpATTRS class has been public. - working around SIGBLOB bug hidden in older sshd. Changes since version 0.1.14: - fixed a crash bug in accepting keep-alive messages. - the parent directory of 'known_hosts' file will be created if it does not exist. - the Subsystem channel support was removed. Changes since version 0.1.13: - added 'setClientVersion' method to Session class. - fixed hung-up problem on SftpChannel in connecting to the sshd, which does not support sftp. - fixed OutOfMemory exception problem in decrypting a private key with bad passphrase. - fixed hung-up problem in communicating with the sshd, whose window size is small. - RuntimeExceptions will be thrown from jsch APIs. - SSH_MSG_CHANNEL_SUCCESS and SSH_MSG_CHANNEL_FAILURE requests have been supported. Changes since version 0.1.12: - added the partial authentication support. - allowing to change the passphrase of a private key file instead of creating a new private key. - added 'examples/ChangePassphrase.java' - the interface 'UIKeyboardInteractive' has been modified. Changes since version 0.1.11: - RSA keypair generation. - added the method 'getFingerPrint' to KeyPair class, which will return the finger print of the public key. - fixed a bug in generating non-ciphered private key. Changes since version 0.1.10: - fixed a bug in the password authentication, sneaked in 0.1.9. By this bug, the password authentication had failed every time. Changes since version 0.1.9: - username and password can be in UTF-8 encoding. - DSA keypair generation. - added 'examples/KeyGen.java', which demonstrates the DSA keypair generation. Changes since version 0.1.8: - fixed crash problems on the local port forwarding. - fixed crash problems on the remote port forwarding. - added setErrStream() and getErrStream() to ChannelExec. - added keyboard-interactive authentication support. - modified TripleDESCBC to support IBM's JDK 1.4.1. - added 'examples/UserAuthKI.java', which demonstrates keyboard-interactive authentication. Changes since version 0.1.7: - added APIs for sftp resume downloads and uploads. The author greatly appreciates elpernotador(webmaster at unlix dot com dot ar), who motivated him to hack this functionality. - 'examples/Sftp.java' demonstrates sftp resume functionality. Please refer to "put-resume", "put-append", "get-resume" and "get-append" command. - added the support of 'window-change' request. - fixed a freeze bug in 'Inputstream get(String src)' method of 'ChannelSftp' class. Changes since version 0.1.6: - added 'int getExitStatus()' method to 'Channel' class. - fixed crash bugs in closing channels for port forwarding. - fixed glitches in managing forwarded ports. Changes since version 0.1.5: - fixed crash bugs in port forwarding. - modified to use "ssh-rsa" for key-exchanging by the default. - the port forwarding setting can be canceled dynamically. - fixed a freeze bug in getting an empty file on sftp channel. Changes since version 0.1.4: - fixed a bug in managing local window size. The local window should be consumed by CHANNEL_EXTENDED_DATA packet. - checking the availability of the ssh session in opening channels. In some case, ssh session had been freezed. - java.io.File.separator will be refereed in generating local pathname on sftp channel. - absolute local pathname will be handled correctly on sftp channel. Changes since version 0.1.3: - fixed a serious bug, which had leaked resources related to ChannelExec. - added the older SFTP protocol(version 0, 1, 2) support. - fixed a problem in the authentication step for FSecure's sshd. - fixed a bug, which had broken Diffie-Hellman key exchange in some case. - implemented the file name globbing for local files on sftp session. - fixed a bug in the file name globbing. - added an interface 'SftpProgressMonitor'. - modified 'examples/Sftp.java' to demonstrate displaying progress-bar in transferring files. Changes since version 0.1.2: - modified 'build.xml' to allow Ant users to compile jsch with debug support (i.e. line-number tables) by overriding the property javac.debug on the command line. - added a property 'StrictHostKeyChecking'. - added 'UserAuthNone' class to request a list of authentication methods on remote sshd. - channels will be managed in each sessions. - added 'ChannelSubsystem', which allows users to use their own implementations for subsystems. - added 'isEOF()' method to 'Channel' class. - supported key pair files in DOS file format. Changes since version 0.1.1: - added the file name globbing support on sftp session. - fixed a bug in the public key authentication. When there was not a public key in ~/.ssh/, that problem occurred. - improved the 'setTimeout' method. - fixed a typo in 'LICENSE.txt' Changes since version 0.1.0: - added 'rekey' method to 'Session' class for key re-exchanging. - added 'rekey' and 'compression' command to 'examples/Sftp.java'. - added new 'get' and 'put' methods to 'ChannelSftp'. Those methods will operate I/O streams. - methods in 'ChannelSftp' will throw 'SftpException' - 'ChannelSftp.Ssh_exp_name' is added for the output of 'ls'. Thanks to Graeme Vetterlein. - added 'setTimeout' and 'getTimeout' methods to 'Session' class. - guess will be done in the algorithm negotiation step. - FSecure's DSA private key has been supported partially. - hostkeys will be saved into 'known_hosts' file. - fixed a bug in 'Util.toBase64' method. - 'Identity' will reject unrecognized keys. - 'build.xml' will check if jzlib is available or not. Thanks to Stefan Bodewig. - added javadoc target in 'build.xml'. Thanks to Robert Anderson. Changes since version 0.0.13: - fixed a bug in connecting to Fsecure's sshd on Windows. - the license is changed to BSD style. Changes since version 0.0.12: - fixed a bug in verifying DAS signatures. - added 'SftpATTR' class, which allow you to get attributes of remote files on sftp channel, and 'stat', 'lstat' method are added to 'ChannelSftp' class. - added 'getInputStream' and 'getOutputStream' methods Channel class, which return passive I/O streams. - 'setIdentity' method is deleted from 'Session' class and 'addIdentity' method is added to 'JSch' class - 'setUserName' method is deleted from 'Session' class and 'getSession' method of 'JSch' class is changed. - 'isConnected' method is added to 'Session' class. - 'UserInfo' interface is changed. Changes since version 0.0.11: - taking care of remote window size. - adding 'disconnect' method to 'Channel' and 'Session' classes. - signal sending support. - 'mkdir' command for sftp. - 'fromBase64' method has been moved to Util class and 'toBase64' method has also been added to that class. - 'KnownHosts' class for checking host-key in 'known_host' file. - 'examples/KnownHosts.java' has been added. - 'setUserName' and 'setPassword' methods have been added to Session class. - 'UserInfo' interface has been changed. - The implementation of compression has moved to 'com.jcraft.jsch.jcraft' package. - fixed a bug in handling 'SSH_MSG_CHANNEL_REQUET' request. - fixed a bug in sending multiple requests on a single session. Changes since version 0.0.10: - Diffie-Hellman key exchange 'diffie-hellman-group1-sha1' is supported. Refer to 'src/com/jcraft/jsch/jce/DHG1.java'. Thanks to Mitsugu Kitano, whose feedback was very helpful. - By the default, 'diffie-hellman-group1-sha1' will be used in the key exchange step. - The file attribute on 'SSH File Transfer Protocol' is supported. Now, we can say JSch supports 'SSH File Transfer Protocol'. - 'examples/Sftp.java' is updated. 'chgrp','chown','chmod' commands are supported. Changes since version 0.0.9: - SSH File Transfer Protocol is supported partially. - 'examples/Sftp.java' is added. This example is a tiny sftp command and supports 'cd','put','get','rm',etc. - 'close' method is added to Channel interface. - build.xml for examples is added. Thanks to Ronald Broberg. Changes since version 0.0.8: - the tunneling through a SOCKS5 proxy is supported. - 'examples/ScpFrom.java' is added. - 'com.jcraft.jsch.UserInfo' interface is modified. Changes since version 0.0.7: - Packet comression is supported. - 'examples/Compression.java' is added. - JZlib is included. Changes since version 0.0.6: - RSA host key is supported. - RSA public key authentication is supported. Changes since version 0.0.5: - DSA public key authentication is supported. - examples/UserAuthPubKey.java is added. - examples/ScpTo.java is added. Changes since version 0.0.4: - 3des-cbc is supported. - hmac-sha1 is supported. - hmac-md5-96 is supported. - hmac-sha1-96 is supported. Changes since version 0.0.3: - port forwarding, similar to the -L option of SSH. - examples/PortForwardingL.java is added. - examples/StreamForwarding.java is added. - examples/Exec.java is renamed as examples/Shell.java - stream forwarding is added. - ChannelSftp class is added for implementing filexfer. - interfaces for jsch users are changed. Changes since version 0.0.2: - remote exec is supported. - examples/Exec.java is added. - build.xml and some scripts for Ant are added. (lbruand) - Const class is added. (lbruand) Changes since version 0.0.1: - the tunneling via HTTP proxy is supported. - port forwarding like option -R of ssh command. the given port on the remote host will be forwarded to the given host and port on the local side. jsch-0.1.53/lib/0000755000000000000000000000000012534212177011777 5ustar rootrootjsch-0.1.53/build.sh0000644000000000000000000000053210463620553012664 0ustar rootroot#!/bin/sh echo echo "JSch Build System" echo "-----------------" export OLD_ANT_HOME=$ANT_HOME ANT_HOME=./tools export OLD_CLASSPATH=$CLASSPATH export CLASSPATH chmod u+x ${ANT_HOME}/bin/antRun chmod u+x ${ANT_HOME}/bin/ant export PROPOSAL="" ${ANT_HOME}/bin/ant -emacs $@ export CLASSPATH=$OLD_CLASSPATH export ANT_HOME=$OLD_ANT_HOME jsch-0.1.53/tools/0000755000000000000000000000000011671025743012373 5ustar rootrootjsch-0.1.53/tools/lib/0000755000000000000000000000000011671025743013141 5ustar rootrootjsch-0.1.53/tools/bin/0000755000000000000000000000000011671025743013143 5ustar rootrootjsch-0.1.53/tools/bin/runant.pl0000644000000000000000000000723007662347650015022 0ustar rootroot#!/usr/bin/perl ####################################################################### # # runant.pl # # wrapper script for invoking ant in a platform with Perl installed # this may include cgi-bin invocation, which is considered somewhat daft. # (slo: that should be a separate file which can be derived from this # and returns the XML formatted output) # # the code is not totally portable due to classpath and directory splitting # issues. oops. (NB, use File::Spec::Functions will help and the code is # structured for the catfile() call, but because of perl version funnies # the code is not included. # # created: 2000-8-24 # last modified: 2000-8-24 # author: Steve Loughran steve_l@sourceforge.net ####################################################################### # # Assumptions: # # - the "java" executable/script is on the command path # - ANT_HOME has been set # - target platform uses ":" as classpath separator or perl indicates it is dos/win32 # - target platform uses "/" as directory separator. #be fussy about variables use strict; #platform specifics (disabled) #use File::Spec::Functions; #turn warnings on during dev; generates a few spurious uninitialised var access warnings #use warnings; #and set $debug to 1 to turn on trace info my $debug=0; ####################################################################### # # check to make sure environment is setup # my $HOME = $ENV{ANT_HOME}; if ($HOME eq "") { die "\n\nANT_HOME *MUST* be set!\n\n"; } my $JAVACMD = $ENV{JAVACMD}; $JAVACMD = "java" if $JAVACMD eq ""; #ISSUE: what java wants to split up classpath varies from platform to platform #and perl is not too hot at hinting which box it is on. #here I assume ":" 'cept on win32 and dos. Add extra tests here as needed. my $s=":"; if(($^O eq "MSWin32") || ($^O eq "dos")) { $s=";"; } #build up standard classpath my $localpath=$ENV{CLASSPATH}; if ($localpath eq "") { print "warning: no initial classpath\n" if ($debug); $localpath=""; } #add jar files. I am sure there is a perl one liner to do this. my $jarpattern="$HOME/lib/*.jar"; my @jarfiles =glob($jarpattern); print "jarfiles=@jarfiles\n" if ($debug); my $jar; foreach $jar (@jarfiles ) { $localpath.="$s$jar"; } #if Java home is defined, look for tools.jar & classes.zip and add to classpath my $JAVA_HOME = $ENV{JAVA_HOME}; if ($JAVA_HOME ne "") { my $tools="$JAVA_HOME/lib/tools.jar"; if (-e "$tools") { $localpath .= "$s$tools"; } my $classes="$JAVA_HOME/lib/classes.zip"; if (-e $classes) { $localpath .= "$s$classes"; } } else { print "\n\nWarning: JAVA_HOME environment variable is not set.\n". "If the build fails because sun.* classes could not be found\n". "you will need to set the JAVA_HOME environment variable\n". "to the installation directory of java\n"; } #jikes my @ANT_OPTS=split $ENV{ANT_OPTS}; if($ENV{JIKESPATH} ne "") { push @ANT_OPTS, "-Djikes.class.path=$ENV{JIKESPATH}"; } #construct arguments to java my @ARGS; push @ARGS, "-classpath", "$localpath", "-Dant.home=$HOME"; push @ARGS, @ANT_OPTS; push @ARGS, "org.apache.tools.ant.Main"; push @ARGS, @ARGV; print "\n $JAVACMD @ARGS\n\n" if ($debug); my $returnValue = system $JAVACMD, @ARGS; if ($returnValue eq 0) { exit 0; } else { # only 0 and 1 are widely recognized as exit values # so change the exit value to 1 exit 1; } jsch-0.1.53/tools/bin/antRun.bat0000644000000000000000000000043107662347650015111 0ustar rootroot@echo off rem Change drive and directory to %1 (Win9X only for NT/2K use "cd /d") cd %1 %1\ set ANT_RUN_CMD=%2 shift shift set PARAMS= :loop if ""%1 == "" goto runCommand set PARAMS=%PARAMS% %1 shift goto loop :runCommand rem echo %ANT_RUN_CMD% %PARAMS% %ANT_RUN_CMD% %PARAMS% jsch-0.1.53/tools/bin/lcp.bat0000644000000000000000000000031307662347650014417 0ustar rootrootset _CLASSPATHCOMPONENT=%1 :argCheck if %2a==a goto gotAllArgs shift set _CLASSPATHCOMPONENT=%_CLASSPATHCOMPONENT% %1 goto argCheck :gotAllArgs set LOCALCLASSPATH=%_CLASSPATHCOMPONENT%;%LOCALCLASSPATH% jsch-0.1.53/tools/bin/runant.py0000644000000000000000000000522107662347650015035 0ustar rootroot#!/usr/bin/python """ runant.py This script is a translation of the runant.pl written by Steve Loughran. It runs ant with/out arguments, it should be quite portable (thanks to the python os library) This script has been tested with Python2.0/Win2K created: 2001-04-11 author: Pierre Dittgen pierre.dittgen@criltelecom.com Assumptions: - the "java" executable/script is on the command path - ANT_HOME has been set """ import os, os.path, string, sys # Change it to 1 to get extra debug information debug = 0 ####################################################################### # # check to make sure environment is setup # if not os.environ.has_key('ANT_HOME'): print '\n\nANT_HOME *MUST* be set!\n\n' sys.exit(1) else: ANT_HOME = os.environ['ANT_HOME'] if not os.environ.has_key('JAVACMD'): JAVACMD = 'java' else: JAVACMD = os.environ['JAVACMD'] # Sets the separator char for CLASSPATH SEPARATOR = ':' if os.name == 'dos' or os.name == 'nt': SEPARATOR = ';' # Build up standard classpath localpath = '' if os.environ.has_key('CLASSPATH'): localpath = os.environ['CLASSPATH'] else: if debug: print 'Warning: no initial classpath\n' # Add jar files LIBDIR = os.path.join(ANT_HOME, 'lib') jarfiles = [] for file in os.listdir(LIBDIR): if file[-4:] == '.jar': jarfiles.append(os.path.join(LIBDIR,file)) if debug: print 'Jar files:' for jar in jarfiles: print jar localpath = localpath + SEPARATOR + string.join(jarfiles, SEPARATOR) # If JAVA_HOME is defined, look for tools.jar & classes.zip # and add to classpath if os.environ.has_key('JAVA_HOME') and os.environ['JAVA_HOME'] != '': JAVA_HOME = os.environ['JAVA_HOME'] TOOLS = os.path.join(JAVA_HOME, os.path.join('lib', 'tools.jar')) if os.path.exists(TOOLS): localpath = localpath + SEPARATOR + TOOLS CLASSES = os.path.join(JAVA_HOME, os.path.join('lib', 'classes.zip')) if os.path.exists(CLASSES): localpath = localpath + SEPARATOR + CLASSES else: print '\n\nWarning: JAVA_HOME environment variable is not set.\n', \ 'If the build fails because sun.* classes could not be found\n', \ 'you will need to set the JAVA_HOME environment variable\n', \ 'to the installation directory of java\n' # Jikes ANT_OPTS = [] if os.environ.has_key('ANT_OPTS'): ANT_OPTS = string.split(os.environ['ANT_OPTS']) if os.environ.has_key('JIKESPATH'): ANT_OPTS.append('-Djikes.class.path=' + os.environ['JIKESPATH']) # Builds the commandline cmdline = '%s -classpath %s -Dant.home=%s %s org.apache.tools.ant.Main %s' \ % (JAVACMD, localpath, ANT_HOME, string.join(ANT_OPTS,' '), \ string.join(sys.argv[1:], ' ')) if debug: print '\n%s\n\n' % (cmdline) # Run the biniou! os.system(cmdline) jsch-0.1.53/tools/bin/antRun0000644000000000000000000000011507662347650014343 0ustar rootroot#! /bin/sh # Args: DIR command cd "$1" CMD="$2" shift shift exec $CMD "$@" jsch-0.1.53/tools/bin/ant.bat0000644000000000000000000000560207662347650014431 0ustar rootroot@echo off if exist "%HOME%\antrc_pre.bat" call "%HOME%\antrc_pre.bat" if not "%OS%"=="Windows_NT" goto win9xStart :winNTStart @setlocal rem %~dp0 is name of current script under NT set DEFAULT_ANT_HOME=%~dp0 rem : operator works similar to make : operator set DEFAULT_ANT_HOME=%DEFAULT_ANT_HOME%\.. if "%ANT_HOME%"=="" set ANT_HOME=%DEFAULT_ANT_HOME% set DEFAULT_ANT_HOME= rem Need to check if we are using the 4NT shell... if "%eval[2+2]" == "4" goto setup4NT rem On NT/2K grab all arguments at once set ANT_CMD_LINE_ARGS=%* goto doneStart :setup4NT set ANT_CMD_LINE_ARGS=%$ goto doneStart :win9xStart rem Slurp the command line arguments. This loop allows for an unlimited number of rem agruments (up to the command line limit, anyway). set ANT_CMD_LINE_ARGS= :setupArgs if %1a==a goto doneStart set ANT_CMD_LINE_ARGS=%ANT_CMD_LINE_ARGS% %1 shift goto setupArgs :doneStart rem This label provides a place for the argument list loop to break out rem and for NT handling to skip to. rem find ANT_HOME if not "%ANT_HOME%"=="" goto checkJava rem check for ant in Program Files on system drive if not exist "%SystemDrive%\Program Files\ant" goto checkSystemDrive set ANT_HOME=%SystemDrive%\Program Files\ant goto checkJava :checkSystemDrive rem check for ant in root directory of system drive if not exist %SystemDrive%\ant\nul goto checkCDrive set ANT_HOME=%SystemDrive%\ant goto checkJava :checkCDrive rem check for ant in C:\ant for Win9X users if not exist C:\ant\nul goto noAntHome set ANT_HOME=C:\ant goto checkJava :noAntHome echo ANT_HOME is not set and ant could not be located. Please set ANT_HOME. goto end :checkJava set _JAVACMD=%JAVACMD% set LOCALCLASSPATH=%CLASSPATH% for %%i in ("%ANT_HOME%\lib\*.jar") do call "%ANT_HOME%\bin\lcp.bat" %%i if "%JAVA_HOME%" == "" goto noJavaHome if "%_JAVACMD%" == "" set _JAVACMD=%JAVA_HOME%\bin\java if exist "%JAVA_HOME%\lib\tools.jar" call "%ANT_HOME%\bin\lcp.bat" %JAVA_HOME%\lib\tools.jar if exist "%JAVA_HOME%\lib\classes.zip" call "%ANT_HOME%\bin\lcp.bat" %JAVA_HOME%\lib\classes.zip goto checkJikes :noJavaHome if "%_JAVACMD%" == "" set _JAVACMD=java echo. echo Warning: JAVA_HOME environment variable is not set. echo If build fails because sun.* classes could not be found echo you will need to set the JAVA_HOME environment variable echo to the installation directory of java. echo. :checkJikes if not "%JIKESPATH%" == "" goto runAntWithJikes :runAnt "%_JAVACMD%" -classpath "%LOCALCLASSPATH%" -Dant.home="%ANT_HOME%" %ANT_OPTS% org.apache.tools.ant.Main %ANT_CMD_LINE_ARGS% goto end :runAntWithJikes "%_JAVACMD%" -classpath "%LOCALCLASSPATH%" -Dant.home="%ANT_HOME%" -Djikes.class.path="%JIKESPATH%" %ANT_OPTS% org.apache.tools.ant.Main %ANT_CMD_LINE_ARGS% :end set LOCALCLASSPATH= set _JAVACMD= set ANT_CMD_LINE_ARGS= if not "%OS%"=="Windows_NT" goto mainEnd :winNTend @endlocal :mainEnd if exist "%HOME%\antrc_post.bat" call "%HOME%\antrc_post.bat" jsch-0.1.53/tools/bin/ant0000644000000000000000000000632007662347650013662 0ustar rootroot#! /bin/sh if [ -f $HOME/.antrc ] ; then . $HOME/.antrc fi # OS specific support. $var _must_ be set to either true or false. cygwin=false; darwin=false; case "`uname`" in CYGWIN*) cygwin=true ;; Darwin*) darwin=true ;; esac if [ -z "$ANT_HOME" ] ; then # try to find ANT if [ -d /opt/ant ] ; then ANT_HOME=/opt/ant fi if [ -d ${HOME}/opt/ant ] ; then ANT_HOME=${HOME}/opt/ant fi ## resolve links - $0 may be a link to ant's home PRG=$0 progname=`basename $0` while [ -h "$PRG" ] ; do ls=`ls -ld "$PRG"` link=`expr "$ls" : '.*-> \(.*\)$'` if expr "$link" : '.*/.*' > /dev/null; then PRG="$link" else PRG="`dirname $PRG`/$link" fi done ANT_HOME=`dirname "$PRG"`/.. fi # For Cygwin, ensure paths are in UNIX format before anything is touched if $cygwin ; then [ -n "$ANT_HOME" ] && ANT_HOME=`cygpath --unix "$ANT_HOME"` [ -n "$JAVA_HOME" ] && JAVA_HOME=`cygpath --unix "$JAVA_HOME"` [ -n "$CLASSPATH" ] && CLASSPATH=`cygpath --path --unix "$CLASSPATH"` fi if [ -z "$JAVACMD" ] ; then if [ -n "$JAVA_HOME" ] ; then if [ -x "$JAVA_HOME/jre/sh/java" ] ; then # IBM's JDK on AIX uses strange locations for the executables JAVACMD=$JAVA_HOME/jre/sh/java else JAVACMD=$JAVA_HOME/bin/java fi else JAVACMD=java fi fi if [ ! -x "$JAVACMD" ] ; then echo "Error: JAVA_HOME is not defined correctly." echo " We cannot execute $JAVACMD" exit fi if [ -n "$CLASSPATH" ] ; then LOCALCLASSPATH=$CLASSPATH fi # add in the dependency .jar files DIRLIBS=${ANT_HOME}/lib/*.jar for i in ${DIRLIBS} do # if the directory is empty, then it will return the input string # this is stupid, so case for it if [ "$i" != "${DIRLIBS}" ] ; then if [ -z "$LOCALCLASSPATH" ] ; then LOCALCLASSPATH=$i else LOCALCLASSPATH="$i":$LOCALCLASSPATH fi fi done if [ -n "$JAVA_HOME" ] ; then if [ -f "$JAVA_HOME/lib/tools.jar" ] ; then LOCALCLASSPATH=$LOCALCLASSPATH:$JAVA_HOME/lib/tools.jar fi if [ -f "$JAVA_HOME/lib/classes.zip" ] ; then LOCALCLASSPATH=$LOCALCLASSPATH:$JAVA_HOME/lib/classes.zip fi # OSX hack to make Ant work with jikes if $darwin ; then OSXHACK="/System/Library/Frameworks/JavaVM.framework/Versions/CurrentJDK/Classes" if [ -d ${OSXHACK} ] ; then for i in ${OSXHACK}/*.jar do JIKESPATH=$JIKESPATH:$i done fi fi else echo "Warning: JAVA_HOME environment variable is not set." echo " If build fails because sun.* classes could not be found" echo " you will need to set the JAVA_HOME environment variable" echo " to the installation directory of java." fi # supply JIKESPATH to Ant as jikes.class.path if [ -n "$JIKESPATH" ] ; then if [ -n "$ANT_OPTS" ] ; then ANT_OPTS="$ANT_OPTS -Djikes.class.path=$JIKESPATH" else ANT_OPTS=-Djikes.class.path=$JIKESPATH fi fi # For Cygwin, switch paths to Windows format before running java if $cygwin; then ANT_HOME=`cygpath --path --windows "$ANT_HOME"` JAVA_HOME=`cygpath --path --windows "$JAVA_HOME"` LOCALCLASSPATH=`cygpath --path --windows "$LOCALCLASSPATH"` fi $JAVACMD -classpath "$LOCALCLASSPATH" -Dant.home="${ANT_HOME}" $ANT_OPTS org.apache.tools.ant.Main "$@" jsch-0.1.53/examples/0000755000000000000000000000000012533602353013045 5ustar rootrootjsch-0.1.53/examples/AES.java0000644000000000000000000001072711743464515014337 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /** * This program will demonstrate how to use "aes128-cbc". * */ import com.jcraft.jsch.*; import java.awt.*; import javax.swing.*; public class AES{ public static void main(String[] arg){ try{ JSch jsch=new JSch(); //jsch.setKnownHosts("/home/foo/.ssh/known_hosts"); String host=null; if(arg.length>0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); //session.setPassword("your password"); // username and password will be given via UserInfo interface. UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.setConfig("cipher.s2c", "aes128-cbc,3des-cbc,blowfish-cbc"); session.setConfig("cipher.c2s", "aes128-cbc,3des-cbc,blowfish-cbc"); session.setConfig("CheckCiphers", "aes128-cbc"); session.connect(); Channel channel=session.openChannel("shell"); channel.setInputStream(System.in); channel.setOutputStream(System.out); channel.connect(); } catch(Exception e){ System.out.println(e); } } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); // username and passphrase will be given via UserInfo interface. UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.connect(); Channel channel=session.openChannel("shell"); channel.setInputStream(System.in); channel.setOutputStream(System.out); channel.connect(); } catch(Exception e){ System.out.println(e); } } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return null; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passphrase; JTextField passphraseField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return passphrase; } public boolean promptPassphrase(String message){ Object[] ob={passphraseField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passphrase=passphraseField.getText(); return true; } else{ return false; } } public boolean promptPassword(String message){ return true; } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); // username and password will be given via UserInfo interface. UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.connect(); String foo=JOptionPane.showInputDialog("Enter host and port", "host:port"); host=foo.substring(0, foo.indexOf(':')); port=Integer.parseInt(foo.substring(foo.indexOf(':')+1)); System.out.println("System.{in,out} will be forwarded to "+ host+":"+port+"."); Channel channel = session.getStreamForwarder(host, port); // InputStream in = channel.getInputStream(); // OutpuStream out = channel.getOutputStream(); channel.setInputStream(System.in); channel.setOutputStream(System.out); channel.connect(1000); } catch(Exception e){ System.out.println(e); } } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); String config = "Port 22\n"+ "\n"+ "Host foo\n"+ " User "+user+"\n"+ " Hostname "+host+"\n"+ "Host *\n"+ " ConnectTime 30000\n"+ " PreferredAuthentications keyboard-interactive,password,publickey\n"+ " #ForwardAgent yes\n"+ " #StrictHostKeyChecking no\n"+ " #IdentityFile ~/.ssh/id_rsa\n"+ " #UserKnownHostsFile ~/.ssh/known_hosts"; System.out.println("Generated configurations:"); System.out.println(config); ConfigRepository configRepository = com.jcraft.jsch.OpenSSHConfig.parse(config); //com.jcraft.jsch.OpenSSHConfig.parseFile("~/.ssh/config"); jsch.setConfigRepository(configRepository); // "foo" is from "Host foo" in the above config. Session session=jsch.getSession("foo"); String passwd = JOptionPane.showInputDialog("Enter password"); session.setPassword(passwd); UserInfo ui = new MyUserInfo(){ public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } public boolean promptYesNo(String message){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, message, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } // If password is not given before the invocation of Session#connect(), // implement also following methods, // * UserInfo#getPassword(), // * UserInfo#promptPassword(String message) and // * UIKeyboardInteractive#promptKeyboardInteractive() }; session.setUserInfo(ui); session.connect(); // making a connection with timeout as defined above. Channel channel=session.openChannel("shell"); channel.setInputStream(System.in); /* // a hack for MS-DOS prompt on Windows. channel.setInputStream(new FilterInputStream(System.in){ public int read(byte[] b, int off, int len)throws IOException{ return in.read(b, off, (len>1024?1024:len)); } }); */ channel.setOutputStream(System.out); /* // Choose the pty-type "vt102". ((ChannelShell)channel).setPtyType("vt102"); */ /* // Set environment variable "LANG" as "ja_JP.eucJP". ((ChannelShell)channel).setEnv("LANG", "ja_JP.eucJP"); */ //channel.connect(); channel.connect(3*1000); } catch(Exception e){ System.out.println(e); } } public static abstract class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return null; } public boolean promptYesNo(String str){ return false; } public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return false; } public boolean promptPassword(String message){ return false; } public void showMessage(String message){ } public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ return null; } } } jsch-0.1.53/examples/ScpFrom.java0000644000000000000000000001527011743464243015274 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /** * This program will demonstrate the file transfer from remote to local * $ CLASSPATH=.:../build javac ScpFrom.java * $ CLASSPATH=.:../build java ScpFrom user@remotehost:file1 file2 * You will be asked passwd. * If everything works fine, a file 'file1' on 'remotehost' will copied to * local 'file1'. * */ import com.jcraft.jsch.*; import java.awt.*; import javax.swing.*; import java.io.*; public class ScpFrom{ public static void main(String[] arg){ if(arg.length!=2){ System.err.println("usage: java ScpFrom user@remotehost:file1 file2"); System.exit(-1); } FileOutputStream fos=null; try{ String user=arg[0].substring(0, arg[0].indexOf('@')); arg[0]=arg[0].substring(arg[0].indexOf('@')+1); String host=arg[0].substring(0, arg[0].indexOf(':')); String rfile=arg[0].substring(arg[0].indexOf(':')+1); String lfile=arg[1]; String prefix=null; if(new File(lfile).isDirectory()){ prefix=lfile+File.separator; } JSch jsch=new JSch(); Session session=jsch.getSession(user, host, 22); // username and password will be given via UserInfo interface. UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.connect(); // exec 'scp -f rfile' remotely String command="scp -f "+rfile; Channel channel=session.openChannel("exec"); ((ChannelExec)channel).setCommand(command); // get I/O streams for remote scp OutputStream out=channel.getOutputStream(); InputStream in=channel.getInputStream(); channel.connect(); byte[] buf=new byte[1024]; // send '\0' buf[0]=0; out.write(buf, 0, 1); out.flush(); while(true){ int c=checkAck(in); if(c!='C'){ break; } // read '0644 ' in.read(buf, 0, 5); long filesize=0L; while(true){ if(in.read(buf, 0, 1)<0){ // error break; } if(buf[0]==' ')break; filesize=filesize*10L+(long)(buf[0]-'0'); } String file=null; for(int i=0;;i++){ in.read(buf, i, 1); if(buf[i]==(byte)0x0a){ file=new String(buf, 0, i); break; } } //System.out.println("filesize="+filesize+", file="+file); // send '\0' buf[0]=0; out.write(buf, 0, 1); out.flush(); // read a content of lfile fos=new FileOutputStream(prefix==null ? lfile : prefix+file); int foo; while(true){ if(buf.length0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.connect(); String subsystem=JOptionPane.showInputDialog("Enter subsystem name", ""); Channel channel=session.openChannel("subsystem"); ((ChannelSubsystem)channel).setSubsystem(subsystem); ((ChannelSubsystem)channel).setPty(true); channel.setInputStream(System.in); ((ChannelSubsystem)channel).setErrStream(System.err); channel.setOutputStream(System.out); channel.connect(); /* channel.setInputStream(System.in); ((ChannelSubsystem)channel).setErrStream(System.err); InputStream in = channel.getInputStream(); channel.connect(); byte[] tmp=new byte[1024]; while(true){ while(in.available()>0){ int i=in.read(tmp, 0, 1024); if(i<0)break; System.out.print(new String(tmp, 0, i)); } if(channel.isClosed()){ System.out.println("exit-status: "+channel.getExitStatus()); break; } try{Thread.sleep(1000);}catch(Exception ee){} } channel.disconnect(); session.disconnect(); */ } catch(Exception e){ System.out.println(e); } } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); /* String xhost="127.0.0.1"; int xport=0; String display=JOptionPane.showInputDialog("Enter display name", xhost+":"+xport); xhost=display.substring(0, display.indexOf(':')); xport=Integer.parseInt(display.substring(display.indexOf(':')+1)); session.setX11Host(xhost); session.setX11Port(xport+6000); */ // username and password will be given via UserInfo interface. UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.connect(); String command=JOptionPane.showInputDialog("Enter command", "set|grep SSH"); Channel channel=session.openChannel("exec"); ((ChannelExec)channel).setCommand(command); // X Forwarding // channel.setXForwarding(true); //channel.setInputStream(System.in); channel.setInputStream(null); //channel.setOutputStream(System.out); //FileOutputStream fos=new FileOutputStream("/tmp/stderr"); //((ChannelExec)channel).setErrStream(fos); ((ChannelExec)channel).setErrStream(System.err); InputStream in=channel.getInputStream(); channel.connect(); byte[] tmp=new byte[1024]; while(true){ while(in.available()>0){ int i=in.read(tmp, 0, 1024); if(i<0)break; System.out.print(new String(tmp, 0, i)); } if(channel.isClosed()){ if(in.available()>0) continue; System.out.println("exit-status: "+channel.getExitStatus()); break; } try{Thread.sleep(1000);}catch(Exception ee){} } channel.disconnect(); session.disconnect(); } catch(Exception e){ System.out.println(e); } } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0){ command+=lfile.substring(lfile.lastIndexOf('/')+1); } else{ command+=lfile; } command+="\n"; out.write(command.getBytes()); out.flush(); if(checkAck(in)!=0){ System.exit(0); } // send a content of lfile fis=new FileInputStream(lfile); byte[] buf=new byte[1024]; while(true){ int len=fis.read(buf, 0, buf.length); if(len<=0) break; out.write(buf, 0, len); //out.flush(); } fis.close(); fis=null; // send '\0' buf[0]=0; out.write(buf, 0, 1); out.flush(); if(checkAck(in)!=0){ System.exit(0); } out.close(); channel.disconnect(); session.disconnect(); System.exit(0); } catch(Exception e){ System.out.println(e); try{if(fis!=null)fis.close();}catch(Exception ee){} } } static int checkAck(InputStream in) throws IOException{ int b=in.read(); // b may be 0 for success, // 1 for error, // 2 for fatal error, // -1 if(b==0) return b; if(b==-1) return b; if(b==1 || b==2){ StringBuffer sb=new StringBuffer(); int c; do { c=in.read(); sb.append((char)c); } while(c!='\n'); if(b==1){ // error System.out.print(sb.toString()); } if(b==2){ // fatal error System.out.print(sb.toString()); } } return b; } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); // username and password will be given via UserInfo interface. UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); /* // In adding to known_hosts file, host names will be hashed. session.setConfig("HashKnownHosts", "yes"); */ session.connect(); { HostKey hk=session.getHostKey(); System.out.println("HostKey: "+ hk.getHost()+" "+ hk.getType()+" "+ hk.getFingerPrint(jsch)); } Channel channel=session.openChannel("shell"); channel.setInputStream(System.in); channel.setOutputStream(System.out); channel.connect(); } catch(Exception e){ System.out.println(e); } } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); String foo=JOptionPane.showInputDialog("Enter -L port:host:hostport", "port:host:hostport"); lport=Integer.parseInt(foo.substring(0, foo.indexOf(':'))); foo=foo.substring(foo.indexOf(':')+1); rhost=foo.substring(0, foo.indexOf(':')); rport=Integer.parseInt(foo.substring(foo.indexOf(':')+1)); // username and password will be given via UserInfo interface. UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.connect(); //Channel channel=session.openChannel("shell"); //channel.connect(); int assinged_port=session.setPortForwardingL(lport, rhost, rport); System.out.println("localhost:"+assinged_port+" -> "+rhost+":"+rport); } catch(Exception e){ System.out.println(e); } } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); // username and password will be given via UserInfo interface. UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.setConfig("compression.s2c", "zlib@openssh.com,zlib,none"); session.setConfig("compression.c2s", "zlib@openssh.com,zlib,none"); session.setConfig("compression_level", "9"); session.connect(); Channel channel=session.openChannel("shell"); channel.setInputStream(System.in); channel.setOutputStream(System.out); channel.connect(); } catch(Exception e){ System.out.println(e); } } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i'. * 'help' command will show available command. * In current implementation, the destination path for 'get' and 'put' * commands must be a file, not a directory. * */ import com.jcraft.jsch.*; import java.awt.*; import javax.swing.*; public class Sftp{ public static void main(String[] arg){ try{ JSch jsch=new JSch(); String host=null; if(arg.length>0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); int port=22; Session session=jsch.getSession(user, host, port); // username and password will be given via UserInfo interface. UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.connect(); Channel channel=session.openChannel("sftp"); channel.connect(); ChannelSftp c=(ChannelSftp)channel; java.io.InputStream in=System.in; java.io.PrintStream out=System.out; java.util.Vector cmds=new java.util.Vector(); byte[] buf=new byte[1024]; int i; String str; int level=0; while(true){ out.print("sftp> "); cmds.removeAllElements(); i=in.read(buf, 0, 1024); if(i<=0)break; i--; if(i>0 && buf[i-1]==0x0d)i--; //str=new String(buf, 0, i); //System.out.println("|"+str+"|"); int s=0; for(int ii=0; ii0){ cmds.addElement(new String(buf, s, ii-s)); } while(ii'7'){foo=-1; break;} foo<<=3; foo|=(k-'0'); } if(foo==-1)continue; } else{ try{foo=Integer.parseInt((String)cmds.elementAt(1));} catch(Exception e){continue;} } try{ if(cmd.equals("chgrp")){ c.chgrp(foo, path); } else if(cmd.equals("chown")){ c.chown(foo, path); } else if(cmd.equals("chmod")){ c.chmod(foo, path); } } catch(SftpException e){ System.out.println(e.toString()); } continue; } if(cmd.equals("pwd") || cmd.equals("lpwd")){ str=(cmd.equals("pwd")?"Remote":"Local"); str+=" working directory: "; if(cmd.equals("pwd")) str+=c.pwd(); else str+=c.lpwd(); out.println(str); continue; } if(cmd.equals("ls") || cmd.equals("dir")){ String path="."; if(cmds.size()==2) path=(String)cmds.elementAt(1); try{ java.util.Vector vv=c.ls(path); if(vv!=null){ for(int ii=0; ii2) continue; String p1 = cmds.size()==1 ? ".": (String)cmds.elementAt(1); SftpStatVFS stat = c.statVFS(p1); long size = stat.getSize(); long used = stat.getUsed(); long avail = stat.getAvailForNonRoot(); long root_avail = stat.getAvail(); long capacity = stat.getCapacity(); System.out.println("Size: "+size); System.out.println("Used: "+used); System.out.println("Avail: "+avail); System.out.println("(root): "+root_avail); System.out.println("%Capacity: "+capacity); continue; } if(cmd.equals("stat") || cmd.equals("lstat")){ if(cmds.size()!=2) continue; String p1=(String)cmds.elementAt(1); SftpATTRS attrs=null; try{ if(cmd.equals("stat")) attrs=c.stat(p1); else attrs=c.lstat(p1); } catch(SftpException e){ System.out.println(e.toString()); } if(attrs!=null){ out.println(attrs); } else{ } continue; } if(cmd.equals("readlink")){ if(cmds.size()!=2) continue; String p1=(String)cmds.elementAt(1); String filename=null; try{ filename=c.readlink(p1); out.println(filename); } catch(SftpException e){ System.out.println(e.toString()); } continue; } if(cmd.equals("realpath")){ if(cmds.size()!=2) continue; String p1=(String)cmds.elementAt(1); String filename=null; try{ filename=c.realpath(p1); out.println(filename); } catch(SftpException e){ System.out.println(e.toString()); } continue; } if(cmd.equals("version")){ out.println("SFTP protocol version "+c.version()); continue; } if(cmd.equals("help") || cmd.equals("?")){ out.println(help); continue; } out.println("unimplemented command: "+cmd); } session.disconnect(); } catch(Exception e){ System.out.println(e); } System.exit(0); } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i=this.count*100/max){ return true; } percent=this.count*100/max; monitor.setNote("Completed "+this.count+"("+percent+"%) out of "+max+"."); monitor.setProgress((int)this.count); return !(monitor.isCanceled()); } public void end(){ monitor.close(); } } private static String help = " Available commands:\n"+ " * means unimplemented command.\n"+ "cd path Change remote directory to 'path'\n"+ "lcd path Change local directory to 'path'\n"+ "chgrp grp path Change group of file 'path' to 'grp'\n"+ "chmod mode path Change permissions of file 'path' to 'mode'\n"+ "chown own path Change owner of file 'path' to 'own'\n"+ "df [path] Display statistics for current directory or\n"+ " filesystem containing 'path'\n"+ "help Display this help text\n"+ "get remote-path [local-path] Download file\n"+ "get-resume remote-path [local-path] Resume to download file.\n"+ "get-append remote-path [local-path] Append remote file to local file\n"+ "hardlink oldpath newpath Hardlink remote file\n"+ "*lls [ls-options [path]] Display local directory listing\n"+ "ln oldpath newpath Symlink remote file\n"+ "*lmkdir path Create local directory\n"+ "lpwd Print local working directory\n"+ "ls [path] Display remote directory listing\n"+ "*lumask umask Set local umask to 'umask'\n"+ "mkdir path Create remote directory\n"+ "put local-path [remote-path] Upload file\n"+ "put-resume local-path [remote-path] Resume to upload file\n"+ "put-append local-path [remote-path] Append local file to remote file.\n"+ "pwd Display remote working directory\n"+ "stat path Display info about path\n"+ "exit Quit sftp\n"+ "quit Quit sftp\n"+ "rename oldpath newpath Rename remote file\n"+ "rmdir path Remove remote directory\n"+ "rm path Delete remote file\n"+ "symlink oldpath newpath Symlink remote file\n"+ "readlink path Check the target of a symbolic link\n"+ "realpath path Canonicalize the path\n"+ "rekey Key re-exchanging\n"+ "compression level Packet compression will be enabled\n"+ "version Show SFTP version\n"+ "? Synonym for help"; } jsch-0.1.53/examples/Shell.java0000644000000000000000000001014612142615675014770 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /** * This program enables you to connect to sshd server and get the shell prompt. * $ CLASSPATH=.:../build javac Shell.java * $ CLASSPATH=.:../build java Shell * You will be asked username, hostname and passwd. * If everything works fine, you will get the shell prompt. Output may * be ugly because of lacks of terminal-emulation, but you can issue commands. * */ import com.jcraft.jsch.*; import java.awt.*; import javax.swing.*; public class Shell{ public static void main(String[] arg){ try{ JSch jsch=new JSch(); //jsch.setKnownHosts("/home/foo/.ssh/known_hosts"); String host=null; if(arg.length>0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); String passwd = JOptionPane.showInputDialog("Enter password"); session.setPassword(passwd); UserInfo ui = new MyUserInfo(){ public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } public boolean promptYesNo(String message){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, message, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } // If password is not given before the invocation of Session#connect(), // implement also following methods, // * UserInfo#getPassword(), // * UserInfo#promptPassword(String message) and // * UIKeyboardInteractive#promptKeyboardInteractive() }; session.setUserInfo(ui); // It must not be recommended, but if you want to skip host-key check, // invoke following, // session.setConfig("StrictHostKeyChecking", "no"); //session.connect(); session.connect(30000); // making a connection with timeout. Channel channel=session.openChannel("shell"); // Enable agent-forwarding. //((ChannelShell)channel).setAgentForwarding(true); channel.setInputStream(System.in); /* // a hack for MS-DOS prompt on Windows. channel.setInputStream(new FilterInputStream(System.in){ public int read(byte[] b, int off, int len)throws IOException{ return in.read(b, off, (len>1024?1024:len)); } }); */ channel.setOutputStream(System.out); /* // Choose the pty-type "vt102". ((ChannelShell)channel).setPtyType("vt102"); */ /* // Set environment variable "LANG" as "ja_JP.eucJP". ((ChannelShell)channel).setEnv("LANG", "ja_JP.eucJP"); */ //channel.connect(); channel.connect(3*1000); } catch(Exception e){ System.out.println(e); } } public static abstract class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return null; } public boolean promptYesNo(String str){ return false; } public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return false; } public boolean promptPassword(String message){ return false; } public void showMessage(String message){ } public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ return null; } } } jsch-0.1.53/examples/README0000644000000000000000000001657712142650274013746 0ustar rootroot README of example directory ==================================================================== Last modified: Wed Oct 16 13:53:12 UTC 2002 This directory contains some examples, which demonstrate how to use JSch - Shell.java This program enables you to connect to sshd server and get the shell prompt. $ CLASSPATH=.:../build javac Shell.java $ CLASSPATH=.:../build java Shell You will be asked username, hostname and passwd. If everything works fine, you will get the shell prompt. Output will be ugly because of lacks of terminal-emulation, but you can issue commands. - X11Forwarding.java This program will demonstrate X11 forwarding. $ CLASSPATH=.:../build javac X11Forwarding.java $ CLASSPATH=.:../build java X11Forwarding You will be asked username, hostname, displayname and passwd. If your X server does not run at 127.0.0.1, please enter correct displayname. If everything works fine, you will get the shell prompt. Try X applications; for example, xlogo. - Exec.java This program will demonstrate remote exec. $ CLASSPATH=.:../build javac Exec.java $ CLASSPATH=.:../build java Exec You will be asked username, hostname, displayname, passwd and command. If everything works fine, given command will be invoked on the remote side and outputs will be printed out. - ViaHTTP.java This program will demonstrate the ssh session via HTTP proxy. $ CLASSPATH=.:../build javac ViaHTTP.java $ CLASSPATH=.:../build java ViaHTTP You will be asked username, hostname, proxy-server and passwd. If everything works fine, you will get the shell prompt. - ViaSOCKS.java This program will demonstrate the ssh session via SOCKS proxy. $ CLASSPATH=.:../build javac ViaSOCKS.java $ CLASSPATH=.:../build java ViaSOCKS You will be asked username, hostname, proxy-server and passwd. If everything works fine, you will get the shell prompt. - PortForwardingR.java This program will demonstrate the port forwarding like option -R of ssh command; the given port on the remote host will be forwarded to the given host and port on the local side. $ CLASSPATH=.:../build javac PortForwardingR.java $ CLASSPATH=.:../build java PortForwardingR You will be asked username, hostname, port:host:hostport and passwd. If everything works fine, you will get the shell prompt. Try the port on remote host. - PortForwardingL.java This program will demonstrate the port forwarding like option -L of ssh command; the given port on the local host will be forwarded to the given remote host and port on the remote side. $ CLASSPATH=.:../build javac PortForwardingL.java $ CLASSPATH=.:../build java PortForwardingL You will be asked username, hostname, port:host:hostport and passwd. If everything works fine, you will get the shell prompt. Try the port on localhost. - StreamForwarding.java This program will demonstrate the stream forwarding. The given Java I/O streams will be forwared to the given remote host and port on the remote side. It is simmilar to the -L option of ssh command, but you don't have to assign and open a local tcp port. $ CLASSPATH=.:../build javac StreamForwarding.java $ CLASSPATH=.:../build java StreamForwarding You will be asked username, hostname, host:hostport and passwd. If everything works fine, System.in and System.out streams will be forwared to remote port and you can send messages from command line. - UserAuthPubKey.java This program will demonstrate the user authentification by public key. $ CLASSPATH=.:../build javac UserAuthPubKey.java $ CLASSPATH=.:../build java UserAuthPubKey You will be asked username, hostname, privatekey(id_dsa) and passphrase. If everything works fine, you will get the shell prompt - Compression.java This program will demonstrate the packet compression. $ CLASSPATH=.:../build javac Compression.java $ CLASSPATH=.:../build java Compression You will be asked username, hostname and passwd. If everything works fine, you will get the shell prompt. In this program, all data from sshd server to jsch will be compressed. - ScpTo.java This program will demonstrate the file transfer from local to remote. $ CLASSPATH=.:../build javac ScpTo.java $ CLASSPATH=.:../build java ScpTo file1 user@remotehost:file2 You will be asked passwd. If everything works fine, a local file 'file1' will copied to 'file2' on 'remotehost'. - ScpFrom.java This program will demonstrate the file transfer from remote to local $ CLASSPATH=.:../build javac ScpFrom.java $ CLASSPATH=.:../build java ScpFrom user@remotehost:file1 file2 You will be asked passwd. If everything works fine, a file 'file1' on 'remotehost' will copied to local 'file1'. - Sftp.java This program will demonstrate the sftp protocol support. $ CLASSPATH=.:../build javac Sftp.java $ CLASSPATH=.:../build java Sftp You will be asked username, host and passwd. If everything works fine, you will get a prompt 'sftp>'. 'help' command will show available command. In current implementation, the destination path for 'get' and 'put' commands must be a file, not a directory. - KnownHosts.java This program will demonstrate the 'known_hosts' file handling. $ CLASSPATH=.:../build javac KnownHosts.java $ CLASSPATH=.:../build java KnownHosts You will be asked username, hostname, a path for 'known_hosts' and passwd. If everything works fine, you will get the shell prompt. In current implementation, jsch only reads 'known_hosts' for checking and does not modify it. - UserAuthKI.java This program will demonstrate the keyboard-interactive authentication. $ CLASSPATH=.:../build javac UserAuthKI.java $ CLASSPATH=.:../build java UserAuthKI If the remote sshd supports keyboard-interactive authentication, you will be prompted. - KeyGen.java This progam will demonstrate the DSA keypair generation. $ CLASSPATH=.:../build javac KeyGen.java $ CLASSPATH=.:../build java KeyGen rsa output_keyfile comment or $ CLASSPATH=.:../build java KeyGen dsa output_keyfile comment You will be asked a passphrase for output_keyfile. If everything works fine, you will get the DSA or RSA keypair, output_keyfile and output_keyfile+".pub". The private key and public key are in the OpenSSH format. - ChangePassphrase.java This program will demonstrate to change the passphrase for a private key file instead of creating a new private key. $ CLASSPATH=.:../build javac ChangePassphrase.java $ CLASSPATH=.:../build java ChangePassphrase private-key A passphrase will be prompted if the given private-key has been encrypted. After successfully loading the content of the private-key, the new passphrase will be prompted and the given private-key will be re-encrypted with that new passphrase. - AES.java This program will demonstrate how to use "aes128-cbc". - Daemon.java This program will demonstrate how to provide a network service like inetd by using remote port-forwarding functionality. - Logger.java This program will demonstrate how to enable logging mechanism and get logging messages. - Subsystem.java This program will demonstrate how to use the Subsystem channel. - Sudo.java This program will demonstrate how to exec 'sudo' on the remote. - ScpToNoneCipher.java This program will demonstrate how to enable none cipher. - JumpHosts.java This program will demonstrate SSH through jump hosts. - OpenSSHConfig.java This program will demonstrate how OpenSSH's config is supported. jsch-0.1.53/examples/X11Forwarding.java0000644000000000000000000001150311743463542016313 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /** * This program will demonstrate X11 forwarding. * $ CLASSPATH=.:../build javac X11Forwarding.java * $ CLASSPATH=.:../build java X11Forwarding * You will be asked username, hostname, displayname and passwd. * If your X server does not run at 127.0.0.1, please enter correct * displayname. If everything works fine, you will get the shell prompt. * Try X applications; for example, xlogo. * */ import com.jcraft.jsch.*; import java.awt.*; import javax.swing.*; public class X11Forwarding{ public static void main(String[] arg){ String xhost="127.0.0.1"; int xport=0; try{ JSch jsch=new JSch(); String host=null; if(arg.length>0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); String display=JOptionPane.showInputDialog("Please enter display name", xhost+":"+xport); xhost=display.substring(0, display.indexOf(':')); xport=Integer.parseInt(display.substring(display.indexOf(':')+1)); session.setX11Host(xhost); session.setX11Port(xport+6000); // username and password will be given via UserInfo interface. UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.connect(); Channel channel=session.openChannel("shell"); channel.setXForwarding(true); channel.setInputStream(System.in); channel.setOutputStream(System.out); channel.connect(); } catch(Exception e){ System.out.println(e); } } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); String proxy=JOptionPane.showInputDialog("Enter proxy server", "hostname:port"); proxy_host=proxy.substring(0, proxy.indexOf(':')); proxy_port=Integer.parseInt(proxy.substring(proxy.indexOf(':')+1)); session.setProxy(new ProxyHTTP(proxy_host, proxy_port)); // username and password will be given via UserInfo interface. UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.connect(); Channel channel=session.openChannel("shell"); channel.setInputStream(System.in); channel.setOutputStream(System.out); channel.connect(); } catch(Exception e){ System.out.println(e); } } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); String foo=JOptionPane.showInputDialog("Enter -R port:host:hostport", "port:host:hostport"); rport=Integer.parseInt(foo.substring(0, foo.indexOf(':'))); foo=foo.substring(foo.indexOf(':')+1); lhost=foo.substring(0, foo.indexOf(':')); lport=Integer.parseInt(foo.substring(foo.indexOf(':')+1)); // username and password will be given via UserInfo interface. UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.connect(); // Channel channel=session.openChannel("shell"); // channel.connect(); session.setPortForwardingR(rport, lhost, lport); System.out.println(host+":"+rport+" -> "+lhost+":"+lport); } catch(Exception e){ System.out.println(e); } } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); String proxy=JOptionPane.showInputDialog("Enter proxy server", "hostname:port"); proxy_host=proxy.substring(0, proxy.indexOf(':')); proxy_port=Integer.parseInt(proxy.substring(proxy.indexOf(':')+1)); session.setProxy(new ProxySOCKS5(proxy_host, proxy_port)); // username and password will be given via UserInfo interface. UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.connect(); Channel channel=session.openChannel("shell"); channel.setInputStream(System.in); channel.setOutputStream(System.out); channel.connect(); } catch(Exception e){ System.out.println(e); } } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); String foo=JOptionPane.showInputDialog("Enter remote port number", "8888"); rport=Integer.parseInt(foo); // username and password will be given via UserInfo interface. UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.connect(); //session.setPortForwardingR(rport, Parrot.class.getName()); session.setPortForwardingR(rport, "Daemon$Parrot"); System.out.println(host+":"+rport+" <--> "+"Parrot"); } catch(Exception e){ System.out.println(e); } } public static class Parrot implements ForwardedTCPIPDaemon{ ChannelForwardedTCPIP channel; Object[] arg; InputStream in; OutputStream out; public void setChannel(ChannelForwardedTCPIP c, InputStream in, OutputStream out){ this.channel=c; this.in=in; this.out=out; } public void setArg(Object[] arg){this.arg=arg;} public void run(){ try{ byte[] buf=new byte[1024]; System.out.println("remote port: "+channel.getRemotePort()); System.out.println("remote host: "+channel.getSession().getHost()); while(true){ int i=in.read(buf, 0, buf.length); if(i<=0)break; out.write(buf, 0, i); out.flush(); if(buf[0]=='.')break; } } catch(JSchException e){ System.out.println("session is down."); } catch(IOException e){ } } } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result=JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); // username and password will be given via UserInfo interface. UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.connect(); Channel channel=session.openChannel("shell"); channel.setInputStream(System.in); channel.setOutputStream(System.out); channel.connect(); } catch(Exception e){ System.out.println(e); } } public static class MyLogger implements com.jcraft.jsch.Logger { static java.util.Hashtable name=new java.util.Hashtable(); static{ name.put(new Integer(DEBUG), "DEBUG: "); name.put(new Integer(INFO), "INFO: "); name.put(new Integer(WARN), "WARN: "); name.put(new Integer(ERROR), "ERROR: "); name.put(new Integer(FATAL), "FATAL: "); } public boolean isEnabled(int level){ return true; } public void log(int level, String message){ System.err.print(name.get(new Integer(level))); System.err.println(message); } } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result=JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.connect(); String command=JOptionPane.showInputDialog("Enter command, execed with sudo", "printenv SUDO_USER"); String sudo_pass=null; { JTextField passwordField=(JTextField)new JPasswordField(8); Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, "Enter password for sudo", JOptionPane.OK_CANCEL_OPTION); if(result!=JOptionPane.OK_OPTION){ System.exit(-1); } sudo_pass=passwordField.getText(); } Channel channel=session.openChannel("exec"); // man sudo // -S The -S (stdin) option causes sudo to read the password from the // standard input instead of the terminal device. // -p The -p (prompt) option allows you to override the default // password prompt and use a custom one. ((ChannelExec)channel).setCommand("sudo -S -p '' "+command); InputStream in=channel.getInputStream(); OutputStream out=channel.getOutputStream(); ((ChannelExec)channel).setErrStream(System.err); channel.connect(); out.write((sudo_pass+"\n").getBytes()); out.flush(); byte[] tmp=new byte[1024]; while(true){ while(in.available()>0){ int i=in.read(tmp, 0, 1024); if(i<0)break; System.out.print(new String(tmp, 0, i)); } if(channel.isClosed()){ System.out.println("exit-status: "+channel.getExitStatus()); break; } try{Thread.sleep(1000);}catch(Exception ee){} } channel.disconnect(); session.disconnect(); } catch(Exception e){ System.out.println(e); } } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0){ command+=lfile.substring(lfile.lastIndexOf('/')+1); } else{ command+=lfile; } command+="\n"; out.write(command.getBytes()); out.flush(); if(checkAck(in)!=0){ System.exit(0); } // send a content of lfile fis=new FileInputStream(lfile); byte[] buf=new byte[1024]; while(true){ int len=fis.read(buf, 0, buf.length); if(len<=0) break; out.write(buf, 0, len); out.flush(); } fis.close(); fis=null; // send '\0' buf[0]=0; out.write(buf, 0, 1); out.flush(); if(checkAck(in)!=0){ System.exit(0); } session.disconnect(); System.exit(0); } catch(Exception e){ System.out.println(e); try{if(fis!=null)fis.close();}catch(Exception ee){} } } static int checkAck(InputStream in) throws IOException{ int b=in.read(); // b may be 0 for success, // 1 for error, // 2 for fatal error, // -1 if(b==0) return b; if(b==-1) return b; if(b==1 || b==2){ StringBuffer sb=new StringBuffer(); int c; do { c=in.read(); sb.append((char)c); } while(c!='\n'); if(b==1){ // error System.out.print(sb.toString()); } if(b==2){ // fatal error System.out.print(sb.toString()); } } return b; } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return true; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0){ host=arg[0]; } else{ host=JOptionPane.showInputDialog("Enter username@hostname", System.getProperty("user.name")+ "@localhost"); } String user=host.substring(0, host.indexOf('@')); host=host.substring(host.indexOf('@')+1); Session session=jsch.getSession(user, host, 22); // username and passphrase will be given via UserInfo interface. UserInfo ui=new MyUserInfo(); session.setUserInfo(ui); session.connect(); Channel channel=session.openChannel("shell"); channel.setInputStream(System.in); channel.setOutputStream(System.out); channel.connect(); } catch(Exception e){ System.out.println(e); } } public static class MyUserInfo implements UserInfo, UIKeyboardInteractive{ public String getPassword(){ return passwd; } public boolean promptYesNo(String str){ Object[] options={ "yes", "no" }; int foo=JOptionPane.showOptionDialog(null, str, "Warning", JOptionPane.DEFAULT_OPTION, JOptionPane.WARNING_MESSAGE, null, options, options[0]); return foo==0; } String passwd; JTextField passwordField=(JTextField)new JPasswordField(20); public String getPassphrase(){ return null; } public boolean promptPassphrase(String message){ return false; } public boolean promptPassword(String message){ Object[] ob={passwordField}; int result= JOptionPane.showConfirmDialog(null, ob, message, JOptionPane.OK_CANCEL_OPTION); if(result==JOptionPane.OK_OPTION){ passwd=passwordField.getText(); return true; } else{ return false; } } public void showMessage(String message){ JOptionPane.showMessageDialog(null, message); } final GridBagConstraints gbc = new GridBagConstraints(0,0,1,1,1,1, GridBagConstraints.NORTHWEST, GridBagConstraints.NONE, new Insets(0,0,0,0),0,0); private Container panel; public String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo){ /* //System.out.println("promptKeyboardInteractive"); System.out.println("destination: "+destination); System.out.println("name: "+name); System.out.println("instruction: "+instruction); System.out.println("prompt.length: "+prompt.length); System.out.println("prompt: "+prompt[0]); */ panel = new JPanel(); panel.setLayout(new GridBagLayout()); gbc.weightx = 1.0; gbc.gridwidth = GridBagConstraints.REMAINDER; gbc.gridx = 0; panel.add(new JLabel(instruction), gbc); gbc.gridy++; gbc.gridwidth = GridBagConstraints.RELATIVE; JTextField[] texts=new JTextField[prompt.length]; for(int i=0; i0) notifyAll(); } int getRecipient(){ return recipient; } void init() throws JSchException { } public void connect() throws JSchException{ connect(0); } public void connect(int connectTimeout) throws JSchException{ this.connectTimeout=connectTimeout; try{ sendChannelOpen(); start(); } catch(Exception e){ connected=false; disconnect(); if(e instanceof JSchException) throw (JSchException)e; throw new JSchException(e.toString(), e); } } public void setXForwarding(boolean foo){ } public void start() throws JSchException{} public boolean isEOF() {return eof_remote;} void getData(Buffer buf){ setRecipient(buf.getInt()); setRemoteWindowSize(buf.getUInt()); setRemotePacketSize(buf.getInt()); } public void setInputStream(InputStream in){ io.setInputStream(in, false); } public void setInputStream(InputStream in, boolean dontclose){ io.setInputStream(in, dontclose); } public void setOutputStream(OutputStream out){ io.setOutputStream(out, false); } public void setOutputStream(OutputStream out, boolean dontclose){ io.setOutputStream(out, dontclose); } public void setExtOutputStream(OutputStream out){ io.setExtOutputStream(out, false); } public void setExtOutputStream(OutputStream out, boolean dontclose){ io.setExtOutputStream(out, dontclose); } public InputStream getInputStream() throws IOException { int max_input_buffer_size = 32*1024; try { max_input_buffer_size = Integer.parseInt(getSession().getConfig("max_input_buffer_size")); } catch(Exception e){} PipedInputStream in = new MyPipedInputStream( 32*1024, // this value should be customizable. max_input_buffer_size ); boolean resizable = 32*10240){ int _l=l; if(l>_bufl-(14+dataLen)-Session.buffer_margin){ _l=_bufl-(14+dataLen)-Session.buffer_margin; } if(_l<=0){ flush(); continue; } System.arraycopy(buf, s, _buf, 14+dataLen, _l); dataLen+=_l; s+=_l; l-=_l; } } public void flush() throws java.io.IOException{ if(closed){ throw new java.io.IOException("Already closed"); } if(dataLen==0) return; packet.reset(); buffer.putByte((byte)Session.SSH_MSG_CHANNEL_DATA); buffer.putInt(recipient); buffer.putInt(dataLen); buffer.skip(dataLen); try{ int foo=dataLen; dataLen=0; synchronized(channel){ if(!channel.close) getSession().write(packet, channel, foo); } } catch(Exception e){ close(); throw new java.io.IOException(e.toString()); } } public void close() throws java.io.IOException{ if(packet==null){ try{ init(); } catch(java.io.IOException e){ // close should be finished silently. return; } } if(closed){ return; } if(dataLen>0){ flush(); } channel.eof(); closed=true; } }; return out; } class MyPipedInputStream extends PipedInputStream{ private int BUFFER_SIZE = 1024; private int max_buffer_size = BUFFER_SIZE; MyPipedInputStream() throws IOException{ super(); } MyPipedInputStream(int size) throws IOException{ super(); buffer=new byte[size]; BUFFER_SIZE = size; max_buffer_size = size; } MyPipedInputStream(int size, int max_buffer_size) throws IOException{ this(size); this.max_buffer_size = max_buffer_size; } MyPipedInputStream(PipedOutputStream out) throws IOException{ super(out); } MyPipedInputStream(PipedOutputStream out, int size) throws IOException{ super(out); buffer=new byte[size]; BUFFER_SIZE=size; } /* * TODO: We should have our own Piped[I/O]Stream implementation. * Before accepting data, JDK's PipedInputStream will check the existence of * reader thread, and if it is not alive, the stream will be closed. * That behavior may cause the problem if multiple threads make access to it. */ public synchronized void updateReadSide() throws IOException { if(available() != 0){ // not empty return; } in = 0; out = 0; buffer[in++] = 0; read(); } private int freeSpace(){ int size = 0; if(out < in) { size = buffer.length-in; } else if(in < out){ if(in == -1) size = buffer.length; else size = out - in; } return size; } synchronized void checkSpace(int len) throws IOException { int size = freeSpace(); if(size max_buffer_size){ foo = max_buffer_size; } if((foo - datasize) < len) return; byte[] tmp = new byte[foo]; if(out < in) { System.arraycopy(buffer, 0, tmp, 0, buffer.length); } else if(in < out){ if(in == -1) { } else { System.arraycopy(buffer, 0, tmp, 0, in); System.arraycopy(buffer, out, tmp, tmp.length-(buffer.length-out), (buffer.length-out)); out = tmp.length-(buffer.length-out); } } else if(in == out){ System.arraycopy(buffer, 0, tmp, 0, buffer.length); in=buffer.length; } buffer=tmp; } else if(buffer.length == size && size > BUFFER_SIZE) { int i = size/2; if(i0) notifyAll(); } void setRemotePacketSize(int foo){ this.rmpsize=foo; } public void run(){ } void write(byte[] foo) throws IOException { write(foo, 0, foo.length); } void write(byte[] foo, int s, int l) throws IOException { try{ io.put(foo, s, l); }catch(NullPointerException e){} } void write_ext(byte[] foo, int s, int l) throws IOException { try{ io.put_ext(foo, s, l); }catch(NullPointerException e){} } void eof_remote(){ eof_remote=true; try{ io.out_close(); } catch(NullPointerException e){} } void eof(){ if(eof_local)return; eof_local=true; int i = getRecipient(); if(i == -1) return; try{ Buffer buf=new Buffer(100); Packet packet=new Packet(buf); packet.reset(); buf.putByte((byte)Session.SSH_MSG_CHANNEL_EOF); buf.putInt(i); synchronized(this){ if(!close) getSession().write(packet); } } catch(Exception e){ //System.err.println("Channel.eof"); //e.printStackTrace(); } /* if(!isConnected()){ disconnect(); } */ } /* http://www1.ietf.org/internet-drafts/draft-ietf-secsh-connect-24.txt 5.3 Closing a Channel When a party will no longer send more data to a channel, it SHOULD send SSH_MSG_CHANNEL_EOF. byte SSH_MSG_CHANNEL_EOF uint32 recipient_channel No explicit response is sent to this message. However, the application may send EOF to whatever is at the other end of the channel. Note that the channel remains open after this message, and more data may still be sent in the other direction. This message does not consume window space and can be sent even if no window space is available. When either party wishes to terminate the channel, it sends SSH_MSG_CHANNEL_CLOSE. Upon receiving this message, a party MUST send back a SSH_MSG_CHANNEL_CLOSE unless it has already sent this message for the channel. The channel is considered closed for a party when it has both sent and received SSH_MSG_CHANNEL_CLOSE, and the party may then reuse the channel number. A party MAY send SSH_MSG_CHANNEL_CLOSE without having sent or received SSH_MSG_CHANNEL_EOF. byte SSH_MSG_CHANNEL_CLOSE uint32 recipient_channel This message does not consume window space and can be sent even if no window space is available. It is recommended that any data sent before this message is delivered to the actual destination, if possible. */ void close(){ if(close)return; close=true; eof_local=eof_remote=true; int i = getRecipient(); if(i == -1) return; try{ Buffer buf=new Buffer(100); Packet packet=new Packet(buf); packet.reset(); buf.putByte((byte)Session.SSH_MSG_CHANNEL_CLOSE); buf.putInt(i); synchronized(this){ getSession().write(packet); } } catch(Exception e){ //e.printStackTrace(); } } public boolean isClosed(){ return close; } static void disconnect(Session session){ Channel[] channels=null; int count=0; synchronized(pool){ channels=new Channel[pool.size()]; for(int i=0; i0){ if(timeout>0L){ if((System.currentTimeMillis()-start)>timeout){ retry=0; continue; } } try{ long t = timeout==0L ? 10L : timeout; this.notifyme=1; wait(t); } catch(java.lang.InterruptedException e){ } finally{ this.notifyme=0; } retry--; } } if(!_session.isConnected()){ throw new JSchException("session is down"); } if(this.getRecipient()==-1){ // timeout throw new JSchException("channel is not opened."); } if(this.open_confirmation==false){ // SSH_MSG_CHANNEL_OPEN_FAILURE throw new JSchException("channel is not opened."); } connected=true; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/UserAuthPublicKey.java0000644000000000000000000002003012500205561023041 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; import java.util.Vector; class UserAuthPublicKey extends UserAuth{ public boolean start(Session session) throws Exception{ super.start(session); Vector identities=session.getIdentityRepository().getIdentities(); byte[] passphrase=null; byte[] _username=null; int command; synchronized(identities){ if(identities.size()<=0){ return false; } _username=Util.str2byte(username); for(int i=0; i= session.max_auth_tries){ return false; } Identity identity=(Identity)(identities.elementAt(i)); byte[] pubkeyblob=identity.getPublicKeyBlob(); if(pubkeyblob!=null){ // send // byte SSH_MSG_USERAUTH_REQUEST(50) // string user name // string service name ("ssh-connection") // string "publickey" // boolen FALSE // string public key algorithm name // string public key blob packet.reset(); buf.putByte((byte)SSH_MSG_USERAUTH_REQUEST); buf.putString(_username); buf.putString(Util.str2byte("ssh-connection")); buf.putString(Util.str2byte("publickey")); buf.putByte((byte)0); buf.putString(Util.str2byte(identity.getAlgName())); buf.putString(pubkeyblob); session.write(packet); loop1: while(true){ buf=session.read(buf); command=buf.getCommand()&0xff; if(command==SSH_MSG_USERAUTH_PK_OK){ break; } else if(command==SSH_MSG_USERAUTH_FAILURE){ break; } else if(command==SSH_MSG_USERAUTH_BANNER){ buf.getInt(); buf.getByte(); buf.getByte(); byte[] _message=buf.getString(); byte[] lang=buf.getString(); String message=Util.byte2str(_message); if(userinfo!=null){ userinfo.showMessage(message); } continue loop1; } else{ //System.err.println("USERAUTH fail ("+command+")"); //throw new JSchException("USERAUTH fail ("+command+")"); break; } } if(command!=SSH_MSG_USERAUTH_PK_OK){ continue; } } //System.err.println("UserAuthPublicKey: identity.isEncrypted()="+identity.isEncrypted()); int count=5; while(true){ if((identity.isEncrypted() && passphrase==null)){ if(userinfo==null) throw new JSchException("USERAUTH fail"); if(identity.isEncrypted() && !userinfo.promptPassphrase("Passphrase for "+identity.getName())){ throw new JSchAuthCancelException("publickey"); //throw new JSchException("USERAUTH cancel"); //break; } String _passphrase=userinfo.getPassphrase(); if(_passphrase!=null){ passphrase=Util.str2byte(_passphrase); } } if(!identity.isEncrypted() || passphrase!=null){ if(identity.setPassphrase(passphrase)){ if(passphrase!=null && (session.getIdentityRepository() instanceof IdentityRepository.Wrapper)){ ((IdentityRepository.Wrapper)session.getIdentityRepository()).check(); } break; } } Util.bzero(passphrase); passphrase=null; count--; if(count==0)break; } Util.bzero(passphrase); passphrase=null; //System.err.println("UserAuthPublicKey: identity.isEncrypted()="+identity.isEncrypted()); if(identity.isEncrypted()) continue; if(pubkeyblob==null) pubkeyblob=identity.getPublicKeyBlob(); //System.err.println("UserAuthPublicKey: pubkeyblob="+pubkeyblob); if(pubkeyblob==null) continue; // send // byte SSH_MSG_USERAUTH_REQUEST(50) // string user name // string service name ("ssh-connection") // string "publickey" // boolen TRUE // string public key algorithm name // string public key blob // string signature packet.reset(); buf.putByte((byte)SSH_MSG_USERAUTH_REQUEST); buf.putString(_username); buf.putString(Util.str2byte("ssh-connection")); buf.putString(Util.str2byte("publickey")); buf.putByte((byte)1); buf.putString(Util.str2byte(identity.getAlgName())); buf.putString(pubkeyblob); // byte[] tmp=new byte[buf.index-5]; // System.arraycopy(buf.buffer, 5, tmp, 0, tmp.length); // buf.putString(signature); byte[] sid=session.getSessionId(); int sidlen=sid.length; byte[] tmp=new byte[4+sidlen+buf.index-5]; tmp[0]=(byte)(sidlen>>>24); tmp[1]=(byte)(sidlen>>>16); tmp[2]=(byte)(sidlen>>>8); tmp[3]=(byte)(sidlen); System.arraycopy(sid, 0, tmp, 4, sidlen); System.arraycopy(buf.buffer, 5, tmp, 4+sidlen, buf.index-5); byte[] signature=identity.getSignature(tmp); if(signature==null){ // for example, too long key length. break; } buf.putString(signature); session.write(packet); loop2: while(true){ buf=session.read(buf); command=buf.getCommand()&0xff; if(command==SSH_MSG_USERAUTH_SUCCESS){ return true; } else if(command==SSH_MSG_USERAUTH_BANNER){ buf.getInt(); buf.getByte(); buf.getByte(); byte[] _message=buf.getString(); byte[] lang=buf.getString(); String message=Util.byte2str(_message); if(userinfo!=null){ userinfo.showMessage(message); } continue loop2; } else if(command==SSH_MSG_USERAUTH_FAILURE){ buf.getInt(); buf.getByte(); buf.getByte(); byte[] foo=buf.getString(); int partial_success=buf.getByte(); //System.err.println(new String(foo)+ // " partial_success:"+(partial_success!=0)); if(partial_success!=0){ throw new JSchPartialAuthException(Util.byte2str(foo)); } session.auth_failures++; break; } //System.err.println("USERAUTH fail ("+command+")"); //throw new JSchException("USERAUTH fail ("+command+")"); break; } } } return false; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/IdentityFile.java0000644000000000000000000001002412500205107022060 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; import java.io.*; class IdentityFile implements Identity{ private JSch jsch; private KeyPair kpair; private String identity; static IdentityFile newInstance(String prvfile, String pubfile, JSch jsch) throws JSchException{ KeyPair kpair = KeyPair.load(jsch, prvfile, pubfile); return new IdentityFile(jsch, prvfile, kpair); } static IdentityFile newInstance(String name, byte[] prvkey, byte[] pubkey, JSch jsch) throws JSchException{ KeyPair kpair = KeyPair.load(jsch, prvkey, pubkey); return new IdentityFile(jsch, name, kpair); } private IdentityFile(JSch jsch, String name, KeyPair kpair) throws JSchException{ this.jsch = jsch; this.identity = name; this.kpair = kpair; } /** * Decrypts this identity with the specified pass-phrase. * @param passphrase the pass-phrase for this identity. * @return true if the decryption is succeeded * or this identity is not cyphered. */ public boolean setPassphrase(byte[] passphrase) throws JSchException{ return kpair.decrypt(passphrase); } /** * Returns the public-key blob. * @return the public-key blob */ public byte[] getPublicKeyBlob(){ return kpair.getPublicKeyBlob(); } /** * Signs on data with this identity, and returns the result. * @param data data to be signed * @return the signature */ public byte[] getSignature(byte[] data){ return kpair.getSignature(data); } /** * @deprecated This method should not be invoked. * @see #setPassphrase(byte[] passphrase) */ public boolean decrypt(){ throw new RuntimeException("not implemented"); } /** * Returns the name of the key algorithm. * @return "ssh-rsa" or "ssh-dss" */ public String getAlgName(){ return new String(kpair.getKeyTypeName()); } /** * Returns the name of this identity. * It will be useful to identify this object in the {@link IdentityRepository}. */ public String getName(){ return identity; } /** * Returns true if this identity is cyphered. * @return true if this identity is cyphered. */ public boolean isEncrypted(){ return kpair.isEncrypted(); } /** * Disposes internally allocated data, like byte array for the private key. */ public void clear(){ kpair.dispose(); kpair = null; } /** * Returns an instance of {@link KeyPair} used in this {@link Identity}. * @return an instance of {@link KeyPair} used in this {@link Identity}. */ public KeyPair getKeyPair(){ return kpair; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/UserAuthKeyboardInteractive.java0000644000000000000000000001461112500205541025116 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; class UserAuthKeyboardInteractive extends UserAuth{ public boolean start(Session session) throws Exception{ super.start(session); if(userinfo!=null && !(userinfo instanceof UIKeyboardInteractive)){ return false; } String dest=username+"@"+session.host; if(session.port!=22){ dest+=(":"+session.port); } byte[] password=session.password; boolean cancel=false; byte[] _username=null; _username=Util.str2byte(username); while(true){ if(session.auth_failures >= session.max_auth_tries){ return false; } // send // byte SSH_MSG_USERAUTH_REQUEST(50) // string user name (ISO-10646 UTF-8, as defined in [RFC-2279]) // string service name (US-ASCII) "ssh-userauth" ? "ssh-connection" // string "keyboard-interactive" (US-ASCII) // string language tag (as defined in [RFC-3066]) // string submethods (ISO-10646 UTF-8) packet.reset(); buf.putByte((byte)SSH_MSG_USERAUTH_REQUEST); buf.putString(_username); buf.putString(Util.str2byte("ssh-connection")); //buf.putString("ssh-userauth".getBytes()); buf.putString(Util.str2byte("keyboard-interactive")); buf.putString(Util.empty); buf.putString(Util.empty); session.write(packet); boolean firsttime=true; loop: while(true){ buf=session.read(buf); int command=buf.getCommand()&0xff; if(command==SSH_MSG_USERAUTH_SUCCESS){ return true; } if(command==SSH_MSG_USERAUTH_BANNER){ buf.getInt(); buf.getByte(); buf.getByte(); byte[] _message=buf.getString(); byte[] lang=buf.getString(); String message=Util.byte2str(_message); if(userinfo!=null){ userinfo.showMessage(message); } continue loop; } if(command==SSH_MSG_USERAUTH_FAILURE){ buf.getInt(); buf.getByte(); buf.getByte(); byte[] foo=buf.getString(); int partial_success=buf.getByte(); // System.err.println(new String(foo)+ // " partial_success:"+(partial_success!=0)); if(partial_success!=0){ throw new JSchPartialAuthException(Util.byte2str(foo)); } if(firsttime){ return false; //throw new JSchException("USERAUTH KI is not supported"); //cancel=true; // ?? } session.auth_failures++; break; } if(command==SSH_MSG_USERAUTH_INFO_REQUEST){ firsttime=false; buf.getInt(); buf.getByte(); buf.getByte(); String name=Util.byte2str(buf.getString()); String instruction=Util.byte2str(buf.getString()); String languate_tag=Util.byte2str(buf.getString()); int num=buf.getInt(); String[] prompt=new String[num]; boolean[] echo=new boolean[num]; for(int i=0; i= 0){ response=new byte[1][]; response[0]=password; password=null; } else if(num>0 ||(name.length()>0 || instruction.length()>0) ){ if(userinfo!=null){ UIKeyboardInteractive kbi=(UIKeyboardInteractive)userinfo; String[] _response=kbi.promptKeyboardInteractive(dest, name, instruction, prompt, echo); if(_response!=null){ response=new byte[_response.length][]; for(int i=0; i<_response.length; i++){ response[i]=Util.str2byte(_response[i]); } } } } // byte SSH_MSG_USERAUTH_INFO_RESPONSE(61) // int num-responses // string response[1] (ISO-10646 UTF-8) // ... // string response[num-responses] (ISO-10646 UTF-8) packet.reset(); buf.putByte((byte)SSH_MSG_USERAUTH_INFO_RESPONSE); if(num>0 && (response==null || // cancel num!=response.length)){ if(response==null){ // working around the bug in OpenSSH ;-< buf.putInt(num); for(int i=0; i>>4)&0x0f))); out.write(b2a((byte)(iv[i]&0x0f))); } out.write(cr); out.write(cr); } int i=0; while(i0){ len>>>=8; i++; } return i; } int writeLength(byte[] data, int index, int len){ int i=countLength(len)-1; if(i==0){ data[index++]=(byte)len; return index; } data[index++]=(byte)(0x80|i); int j=index+i; while(i>0){ data[index+i-1]=(byte)(len&0xff); len>>>=8; i--; } return j; } private Random genRandom(){ if(random==null){ try{ Class c=Class.forName(jsch.getConfig("random")); random=(Random)(c.newInstance()); } catch(Exception e){ System.err.println("connect: random "+e); } } return random; } private HASH genHash(){ try{ Class c=Class.forName(jsch.getConfig("md5")); hash=(HASH)(c.newInstance()); hash.init(); } catch(Exception e){ } return hash; } private Cipher genCipher(){ try{ Class c; c=Class.forName(jsch.getConfig("3des-cbc")); cipher=(Cipher)(c.newInstance()); } catch(Exception e){ } return cipher; } /* hash is MD5 h(0) <- hash(passphrase, iv); h(n) <- hash(h(n-1), passphrase, iv); key <- (h(0),...,h(n))[0,..,key.length]; */ synchronized byte[] genKey(byte[] passphrase, byte[] iv){ if(cipher==null) cipher=genCipher(); if(hash==null) hash=genHash(); byte[] key=new byte[cipher.getBlockSize()]; int hsize=hash.getBlockSize(); byte[] hn=new byte[key.length/hsize*hsize+ (key.length%hsize==0?0:hsize)]; try{ byte[] tmp=null; if(vendor==VENDOR_OPENSSH){ for(int index=0; index+hsize<=hn.length;){ if(tmp!=null){ hash.update(tmp, 0, tmp.length); } hash.update(passphrase, 0, passphrase.length); hash.update(iv, 0, iv.length > 8 ? 8: iv.length); tmp=hash.digest(); System.arraycopy(tmp, 0, hn, index, tmp.length); index+=tmp.length; } System.arraycopy(hn, 0, key, 0, key.length); } else if(vendor==VENDOR_FSECURE){ for(int index=0; index+hsize<=hn.length;){ if(tmp!=null){ hash.update(tmp, 0, tmp.length); } hash.update(passphrase, 0, passphrase.length); tmp=hash.digest(); System.arraycopy(tmp, 0, hn, index, tmp.length); index+=tmp.length; } System.arraycopy(hn, 0, key, 0, key.length); } else if(vendor==VENDOR_PUTTY){ Class c=Class.forName((String)jsch.getConfig("sha-1")); HASH sha1=(HASH)(c.newInstance()); tmp = new byte[4]; key = new byte[20*2]; for(int i = 0; i < 2; i++){ sha1.init(); tmp[3]=(byte)i; sha1.update(tmp, 0, tmp.length); sha1.update(passphrase, 0, passphrase.length); System.arraycopy(sha1.digest(), 0, key, i*20, 20); } } } catch(Exception e){ System.err.println(e); } return key; } /** * @deprecated use #writePrivateKey(java.io.OutputStream out, byte[] passphrase) */ public void setPassphrase(String passphrase){ if(passphrase==null || passphrase.length()==0){ setPassphrase((byte[])null); } else{ setPassphrase(Util.str2byte(passphrase)); } } /** * @deprecated use #writePrivateKey(String name, byte[] passphrase) */ public void setPassphrase(byte[] passphrase){ if(passphrase!=null && passphrase.length==0) passphrase=null; this.passphrase=passphrase; } protected boolean encrypted=false; protected byte[] data=null; private byte[] iv=null; private byte[] publickeyblob=null; public boolean isEncrypted(){ return encrypted; } public boolean decrypt(String _passphrase){ if(_passphrase==null || _passphrase.length()==0){ return !encrypted; } return decrypt(Util.str2byte(_passphrase)); } public boolean decrypt(byte[] _passphrase){ if(!encrypted){ return true; } if(_passphrase==null){ return !encrypted; } byte[] bar=new byte[_passphrase.length]; System.arraycopy(_passphrase, 0, bar, 0, bar.length); _passphrase=bar; byte[] foo=decrypt(data, _passphrase, iv); Util.bzero(_passphrase); if(parse(foo)){ encrypted=false; } return !encrypted; } public static KeyPair load(JSch jsch, String prvkey) throws JSchException{ String pubkey=prvkey+".pub"; if(!new File(pubkey).exists()){ pubkey=null; } return load(jsch, prvkey, pubkey); } public static KeyPair load(JSch jsch, String prvfile, String pubfile) throws JSchException{ byte[] prvkey=null; byte[] pubkey=null; try{ prvkey = Util.fromFile(prvfile); } catch(IOException e){ throw new JSchException(e.toString(), (Throwable)e); } String _pubfile=pubfile; if(pubfile==null){ _pubfile=prvfile+".pub"; } try{ pubkey = Util.fromFile(_pubfile); } catch(IOException e){ if(pubfile!=null){ throw new JSchException(e.toString(), (Throwable)e); } } try { return load(jsch, prvkey, pubkey); } finally { Util.bzero(prvkey); } } public static KeyPair load(JSch jsch, byte[] prvkey, byte[] pubkey) throws JSchException{ byte[] iv=new byte[8]; // 8 boolean encrypted=true; byte[] data=null; byte[] publickeyblob=null; int type=ERROR; int vendor=VENDOR_OPENSSH; String publicKeyComment = ""; Cipher cipher=null; // prvkey from "ssh-add" command on the remote. if(pubkey==null && prvkey!=null && (prvkey.length>11 && prvkey[0]==0 && prvkey[1]==0 && prvkey[2]==0 && (prvkey[3]==7 || prvkey[3]==19))){ Buffer buf=new Buffer(prvkey); buf.skip(prvkey.length); // for using Buffer#available() String _type = new String(buf.getString()); // ssh-rsa or ssh-dss buf.rewind(); KeyPair kpair=null; if(_type.equals("ssh-rsa")){ kpair=KeyPairRSA.fromSSHAgent(jsch, buf); } else if(_type.equals("ssh-dss")){ kpair=KeyPairDSA.fromSSHAgent(jsch, buf); } else if(_type.equals("ecdsa-sha2-nistp256") || _type.equals("ecdsa-sha2-nistp384") || _type.equals("ecdsa-sha2-nistp512")){ kpair=KeyPairECDSA.fromSSHAgent(jsch, buf); } else{ throw new JSchException("privatekey: invalid key "+new String(prvkey, 4, 7)); } return kpair; } try{ byte[] buf=prvkey; if(buf!=null){ KeyPair ppk = loadPPK(jsch, buf); if(ppk !=null) return ppk; } int len = (buf!=null ? buf.length : 0); int i=0; // skip garbage lines. while(i= len) throw new JSchException("invalid privatekey: "+prvkey); if(buf[i]=='D'&& buf[i+1]=='S'&& buf[i+2]=='A'){ type=DSA; } else if(buf[i]=='R'&& buf[i+1]=='S'&& buf[i+2]=='A'){ type=RSA; } else if(buf[i]=='E'&& buf[i+1]=='C'){ type=ECDSA; } else if(buf[i]=='S'&& buf[i+1]=='S'&& buf[i+2]=='H'){ // FSecure type=UNKNOWN; vendor=VENDOR_FSECURE; } else if(i+6 < len && buf[i]=='P' && buf[i+1]=='R' && buf[i+2]=='I' && buf[i+3]=='V' && buf[i+4]=='A' && buf[i+5]=='T' && buf[i+6]=='E'){ type=UNKNOWN; vendor=VENDOR_PKCS8; encrypted=false; i+=3; } else if(i+8 < len && buf[i]=='E' && buf[i+1]=='N' && buf[i+2]=='C' && buf[i+3]=='R' && buf[i+4]=='Y' && buf[i+5]=='P' && buf[i+6]=='T' && buf[i+7]=='E' && buf[i+8]=='D'){ type=UNKNOWN; vendor=VENDOR_PKCS8; i+=5; } else{ throw new JSchException("invalid privatekey: "+prvkey); } i+=3; continue; } if(buf[i]=='A'&& i+7 0) data=Util.fromBase64(_buf, start, i-start); Util.bzero(_buf); } if(data!=null && data.length>4 && // FSecure data[0]==(byte)0x3f && data[1]==(byte)0x6f && data[2]==(byte)0xf9 && data[3]==(byte)0xeb){ Buffer _buf=new Buffer(data); _buf.getInt(); // 0x3f6ff9be _buf.getInt(); byte[]_type=_buf.getString(); //System.err.println("type: "+new String(_type)); String _cipher=Util.byte2str(_buf.getString()); //System.err.println("cipher: "+_cipher); if(_cipher.equals("3des-cbc")){ _buf.getInt(); byte[] foo=new byte[data.length-_buf.getOffSet()]; _buf.getByte(foo); data=foo; encrypted=true; throw new JSchException("unknown privatekey format: "+prvkey); } else if(_cipher.equals("none")){ _buf.getInt(); _buf.getInt(); encrypted=false; byte[] foo=new byte[data.length-_buf.getOffSet()]; _buf.getByte(foo); data=foo; } } if(pubkey!=null){ try{ buf=pubkey; len=buf.length; if(buf.length>4 && // FSecure's public key buf[0]=='-' && buf[1]=='-' && buf[2]=='-' && buf[3]=='-'){ boolean valid=true; i=0; do{i++;}while(buf.length>i && buf[i]!=0x0a); if(buf.length<=i) {valid=false;} while(valid){ if(buf[i]==0x0a){ boolean inheader=false; for(int j=i+1; j7){ if(buf[4]=='d'){ type=DSA; } else if(buf[4]=='r'){ type=RSA; } } i=0; while(i0 && buf[i-1]==0x0d) i--; if(start7){ type=ECDSA; } i=0; while(i0 && buf[i-1]==0x0d) i--; if(start0){ while(buf.length > i){ if(buf[i++] == 0x0d){ if(data == null){ data = new byte[i - index - 1]; System.arraycopy(buf, index, data, 0, i - index - 1); } else { byte[] tmp = new byte[data.length + i - index - 1]; System.arraycopy(data, 0, tmp, 0, data.length); System.arraycopy(buf, index, tmp, data.length, i - index -1); for(int j = 0; j < data.length; j++) data[j] = 0; // clear data = tmp; } break; } } if(buf[i]==0x0a) i++; index=i; } if(data != null) buffer.index = index; return data; } private static boolean parseHeader(Buffer buffer, java.util.Hashtable v){ byte[] buf = buffer.buffer; int index = buffer.index; String key = null; String value = null; for(int i = index; i < buf.length; i++){ if(buf[i] == 0x0d){ break; } if(buf[i] == ':'){ key = new String(buf, index, i - index); i++; if(i < buf.length && buf[i] == ' '){ i++; } index = i; break; } } if(key == null) return false; for(int i = index; i < buf.length; i++){ if(buf[i] == 0x0d){ value = new String(buf, index, i - index); i++; if(i < buf.length && buf[i] == 0x0a){ i++; } index = i; break; } } if(value != null){ v.put(key, value); buffer.index = index; } return (key != null && value != null); } void copy(KeyPair kpair){ this.publickeyblob=kpair.publickeyblob; this.vendor=kpair.vendor; this.publicKeyComment=kpair.publicKeyComment; this.cipher=kpair.cipher; } class ASN1Exception extends Exception { } class ASN1 { byte[] buf; int start; int length; ASN1(byte[] buf) throws ASN1Exception { this(buf, 0, buf.length); } ASN1(byte[] buf, int start, int length) throws ASN1Exception { this.buf = buf; this.start = start; this.length = length; if(start+length>buf.length) throw new ASN1Exception(); } int getType() { return buf[start]&0xff; } boolean isSEQUENCE() { return getType()==(0x30&0xff); } boolean isINTEGER() { return getType()==(0x02&0xff); } boolean isOBJECT() { return getType()==(0x06&0xff); } boolean isOCTETSTRING() { return getType()==(0x04&0xff); } private int getLength(int[] indexp) { int index=indexp[0]; int length=buf[index++]&0xff; if((length&0x80)!=0) { int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(buf[index++]&0xff); } } indexp[0]=index; return length; } byte[] getContent() { int[] indexp=new int[1]; indexp[0]=start+1; int length = getLength(indexp); int index=indexp[0]; byte[] tmp = new byte[length]; System.arraycopy(buf, index, tmp, 0, tmp.length); return tmp; } ASN1[] getContents() throws ASN1Exception { int typ = buf[start]; int[] indexp=new int[1]; indexp[0]=start+1; int length = getLength(indexp); if(typ == 0x05){ return new ASN1[0]; } int index=indexp[0]; java.util.Vector values = new java.util.Vector(); while(length>0) { index++; length--; int tmp=index; indexp[0]=index; int l=getLength(indexp); index=indexp[0]; length-=(index-tmp); values.addElement(new ASN1(buf, tmp-1, 1+(index-tmp)+l)); index+=l; length-=l; } ASN1[] result = new ASN1[values.size()]; for(int i = 0; i 0){ socket.setSoTimeout(timeout); } socket.setTcpNoDelay(true); byte[] buf=new byte[1024]; int index=0; /* +----+----------+----------+ |VER | NMETHODS | METHODS | +----+----------+----------+ | 1 | 1 | 1 to 255 | +----+----------+----------+ The VER field is set to X'05' for this version of the protocol. The NMETHODS field contains the number of method identifier octets that appear in the METHODS field. The values currently defined for METHOD are: o X'00' NO AUTHENTICATION REQUIRED o X'01' GSSAPI o X'02' USERNAME/PASSWORD o X'03' to X'7F' IANA ASSIGNED o X'80' to X'FE' RESERVED FOR PRIVATE METHODS o X'FF' NO ACCEPTABLE METHODS */ buf[index++]=5; buf[index++]=2; buf[index++]=0; // NO AUTHENTICATION REQUIRED buf[index++]=2; // USERNAME/PASSWORD out.write(buf, 0, index); /* The server selects from one of the methods given in METHODS, and sends a METHOD selection message: +----+--------+ |VER | METHOD | +----+--------+ | 1 | 1 | +----+--------+ */ //in.read(buf, 0, 2); fill(in, buf, 2); boolean check=false; switch((buf[1])&0xff){ case 0: // NO AUTHENTICATION REQUIRED check=true; break; case 2: // USERNAME/PASSWORD if(user==null || passwd==null)break; /* Once the SOCKS V5 server has started, and the client has selected the Username/Password Authentication protocol, the Username/Password subnegotiation begins. This begins with the client producing a Username/Password request: +----+------+----------+------+----------+ |VER | ULEN | UNAME | PLEN | PASSWD | +----+------+----------+------+----------+ | 1 | 1 | 1 to 255 | 1 | 1 to 255 | +----+------+----------+------+----------+ The VER field contains the current version of the subnegotiation, which is X'01'. The ULEN field contains the length of the UNAME field that follows. The UNAME field contains the username as known to the source operating system. The PLEN field contains the length of the PASSWD field that follows. The PASSWD field contains the password association with the given UNAME. */ index=0; buf[index++]=1; buf[index++]=(byte)(user.length()); System.arraycopy(Util.str2byte(user), 0, buf, index, user.length()); index+=user.length(); buf[index++]=(byte)(passwd.length()); System.arraycopy(Util.str2byte(passwd), 0, buf, index, passwd.length()); index+=passwd.length(); out.write(buf, 0, index); /* The server verifies the supplied UNAME and PASSWD, and sends the following response: +----+--------+ |VER | STATUS | +----+--------+ | 1 | 1 | +----+--------+ A STATUS field of X'00' indicates success. If the server returns a `failure' (STATUS value other than X'00') status, it MUST close the connection. */ //in.read(buf, 0, 2); fill(in, buf, 2); if(buf[1]==0) check=true; break; default: } if(!check){ try{ socket.close(); } catch(Exception eee){ } throw new JSchException("fail in SOCKS5 proxy"); } /* The SOCKS request is formed as follows: +----+-----+-------+------+----------+----------+ |VER | CMD | RSV | ATYP | DST.ADDR | DST.PORT | +----+-----+-------+------+----------+----------+ | 1 | 1 | X'00' | 1 | Variable | 2 | +----+-----+-------+------+----------+----------+ Where: o VER protocol version: X'05' o CMD o CONNECT X'01' o BIND X'02' o UDP ASSOCIATE X'03' o RSV RESERVED o ATYP address type of following address o IP V4 address: X'01' o DOMAINNAME: X'03' o IP V6 address: X'04' o DST.ADDR desired destination address o DST.PORT desired destination port in network octet order */ index=0; buf[index++]=5; buf[index++]=1; // CONNECT buf[index++]=0; byte[] hostb=Util.str2byte(host); int len=hostb.length; buf[index++]=3; // DOMAINNAME buf[index++]=(byte)(len); System.arraycopy(hostb, 0, buf, index, len); index+=len; buf[index++]=(byte)(port>>>8); buf[index++]=(byte)(port&0xff); out.write(buf, 0, index); /* The SOCKS request information is sent by the client as soon as it has established a connection to the SOCKS server, and completed the authentication negotiations. The server evaluates the request, and returns a reply formed as follows: +----+-----+-------+------+----------+----------+ |VER | REP | RSV | ATYP | BND.ADDR | BND.PORT | +----+-----+-------+------+----------+----------+ | 1 | 1 | X'00' | 1 | Variable | 2 | +----+-----+-------+------+----------+----------+ Where: o VER protocol version: X'05' o REP Reply field: o X'00' succeeded o X'01' general SOCKS server failure o X'02' connection not allowed by ruleset o X'03' Network unreachable o X'04' Host unreachable o X'05' Connection refused o X'06' TTL expired o X'07' Command not supported o X'08' Address type not supported o X'09' to X'FF' unassigned o RSV RESERVED o ATYP address type of following address o IP V4 address: X'01' o DOMAINNAME: X'03' o IP V6 address: X'04' o BND.ADDR server bound address o BND.PORT server bound port in network octet order */ //in.read(buf, 0, 4); fill(in, buf, 4); if(buf[1]!=0){ try{ socket.close(); } catch(Exception eee){ } throw new JSchException("ProxySOCKS5: server returns "+buf[1]); } switch(buf[3]&0xff){ case 1: //in.read(buf, 0, 6); fill(in, buf, 6); break; case 3: //in.read(buf, 0, 1); fill(in, buf, 1); //in.read(buf, 0, buf[0]+2); fill(in, buf, (buf[0]&0xff)+2); break; case 4: //in.read(buf, 0, 18); fill(in, buf, 18); break; default: } } catch(RuntimeException e){ throw e; } catch(Exception e){ try{ if(socket!=null)socket.close(); } catch(Exception eee){ } String message="ProxySOCKS5: "+e.toString(); if(e instanceof Throwable) throw new JSchException(message, (Throwable)e); throw new JSchException(message); } } public InputStream getInputStream(){ return in; } public OutputStream getOutputStream(){ return out; } public Socket getSocket(){ return socket; } public void close(){ try{ if(in!=null)in.close(); if(out!=null)out.close(); if(socket!=null)socket.close(); } catch(Exception e){ } in=null; out=null; socket=null; } public static int getDefaultPort(){ return DEFAULTPORT; } private void fill(InputStream in, byte[] buf, int len) throws JSchException, IOException{ int s=0; while(s>>4)&0xf]; bar[2*i+1]=table[(foo[i])&0xf]; } faked_cookie_hex_pool.put(session, bar); foo=bar; } return foo; } } static void removeFakedCookie(Session session){ synchronized(faked_cookie_hex_pool){ faked_cookie_hex_pool.remove(session); faked_cookie_pool.remove(session); } } ChannelX11(){ super(); setLocalWindowSizeMax(LOCAL_WINDOW_SIZE_MAX); setLocalWindowSize(LOCAL_WINDOW_SIZE_MAX); setLocalPacketSize(LOCAL_MAXIMUM_PACKET_SIZE); type=Util.str2byte("x11"); connected=true; /* try{ socket=Util.createSocket(host, port, TIMEOUT); socket.setTcpNoDelay(true); io=new IO(); io.setInputStream(socket.getInputStream()); io.setOutputStream(socket.getOutputStream()); } catch(Exception e){ //System.err.println(e); } */ } public void run(){ try{ socket=Util.createSocket(host, port, TIMEOUT); socket.setTcpNoDelay(true); io=new IO(); io.setInputStream(socket.getInputStream()); io.setOutputStream(socket.getOutputStream()); sendOpenConfirmation(); } catch(Exception e){ sendOpenFailure(SSH_OPEN_ADMINISTRATIVELY_PROHIBITED); close=true; disconnect(); return; } thread=Thread.currentThread(); Buffer buf=new Buffer(rmpsize); Packet packet=new Packet(buf); int i=0; try{ while(thread!=null && io!=null && io.in!=null){ i=io.in.read(buf.buffer, 14, buf.buffer.length-14-Session.buffer_margin); if(i<=0){ eof(); break; } if(close)break; packet.reset(); buf.putByte((byte)Session.SSH_MSG_CHANNEL_DATA); buf.putInt(recipient); buf.putInt(i); buf.skip(i); getSession().write(packet, this, i); } } catch(Exception e){ //System.err.println(e); } disconnect(); } private byte[] cache=new byte[0]; private byte[] addCache(byte[] foo, int s, int l){ byte[] bar=new byte[cache.length+l]; System.arraycopy(foo, s, bar, cache.length, l); if(cache.length>0) System.arraycopy(cache, 0, bar, 0, cache.length); cache=bar; return cache; } void write(byte[] foo, int s, int l) throws java.io.IOException { //if(eof_local)return; if(init){ Session _session=null; try{ _session=getSession(); } catch(JSchException e){ throw new java.io.IOException(e.toString()); } foo=addCache(foo, s, l); s=0; l=foo.length; if(l<9) return; int plen=(foo[s+6]&0xff)*256+(foo[s+7]&0xff); int dlen=(foo[s+8]&0xff)*256+(foo[s+9]&0xff); if((foo[s]&0xff)==0x42){ } else if((foo[s]&0xff)==0x6c){ plen=((plen>>>8)&0xff)|((plen<<8)&0xff00); dlen=((dlen>>>8)&0xff)|((dlen<<8)&0xff00); } else{ // ?? } if(l<12+plen+((-plen)&3)+dlen) return; byte[] bar=new byte[dlen]; System.arraycopy(foo, s+12+plen+((-plen)&3), bar, 0, dlen); byte[] faked_cookie=null; synchronized(faked_cookie_pool){ faked_cookie=(byte[])faked_cookie_pool.get(_session); } /* System.err.print("faked_cookie: "); for(int i=0; i *
  • Host
  • *
  • User
  • *
  • Hostname
  • *
  • Port
  • *
  • PreferredAuthentications
  • *
  • IdentityFile
  • *
  • NumberOfPasswordPrompts
  • *
  • ConnectTimeout
  • *
  • HostKeyAlias
  • *
  • UserKnownHostsFile
  • *
  • KexAlgorithms
  • *
  • HostKeyAlgorithms
  • *
  • Ciphers
  • *
  • Macs
  • *
  • Compression
  • *
  • CompressionLevel
  • *
  • ForwardAgent
  • *
  • RequestTTY
  • *
  • ServerAliveInterval
  • *
  • LocalForward
  • *
  • RemoteForward
  • *
  • ClearAllForwardings
  • * * * @see ConfigRepository */ public class OpenSSHConfig implements ConfigRepository { /** * Parses the given string, and returns an instance of ConfigRepository. * * @param conf string, which includes OpenSSH's config * @return an instanceof OpenSSHConfig */ public static OpenSSHConfig parse(String conf) throws IOException { Reader r = new StringReader(conf); try { return new OpenSSHConfig(r); } finally { r.close(); } } /** * Parses the given file, and returns an instance of ConfigRepository. * * @param file OpenSSH's config file * @return an instanceof OpenSSHConfig */ public static OpenSSHConfig parseFile(String file) throws IOException { Reader r = new FileReader(Util.checkTilde(file)); try { return new OpenSSHConfig(r); } finally { r.close(); } } OpenSSHConfig(Reader r) throws IOException { _parse(r); } private final Hashtable config = new Hashtable(); private final Vector hosts = new Vector(); private void _parse(Reader r) throws IOException { BufferedReader br = new BufferedReader(r); String host = ""; Vector/**/ kv = new Vector(); String l = null; while((l = br.readLine()) != null){ l = l.trim(); if(l.length() == 0 || l.startsWith("#")) continue; String[] key_value = l.split("[= \t]", 2); for(int i = 0; i < key_value.length; i++) key_value[i] = key_value[i].trim(); if(key_value.length <= 1) continue; if(key_value[0].equals("Host")){ config.put(host, kv); hosts.addElement(host); host = key_value[1]; kv = new Vector(); } else { kv.addElement(key_value); } } config.put(host, kv); hosts.addElement(host); } public Config getConfig(String host) { return new MyConfig(host); } private static final Hashtable keymap = new Hashtable(); static { keymap.put("kex", "KexAlgorithms"); keymap.put("server_host_key", "HostKeyAlgorithms"); keymap.put("cipher.c2s", "Ciphers"); keymap.put("cipher.s2c", "Ciphers"); keymap.put("mac.c2s", "Macs"); keymap.put("mac.s2c", "Macs"); keymap.put("compression.s2c", "Compression"); keymap.put("compression.c2s", "Compression"); keymap.put("compression_level", "CompressionLevel"); keymap.put("MaxAuthTries", "NumberOfPasswordPrompts"); } class MyConfig implements Config { private String host; private Vector _configs = new Vector(); MyConfig(String host){ this.host = host; _configs.addElement(config.get("")); byte[] _host = Util.str2byte(host); if(hosts.size() > 1){ for(int i = 1; i < hosts.size(); i++){ String patterns[] = ((String)hosts.elementAt(i)).split("[ \t]"); for(int j = 0; j < patterns.length; j++){ boolean negate = false; String foo = patterns[j].trim(); if(foo.startsWith("!")){ negate = true; foo = foo.substring(1).trim(); } if(Util.glob(Util.str2byte(foo), _host)){ if(!negate){ _configs.addElement(config.get((String)hosts.elementAt(i))); } } else if(negate){ _configs.addElement(config.get((String)hosts.elementAt(i))); } } } } } private String find(String key) { if(keymap.get(key)!=null) { key = (String)keymap.get(key); } key = key.toUpperCase(); String value = null; for(int i = 0; i < _configs.size(); i++) { Vector v = (Vector)_configs.elementAt(i); for(int j = 0; j < v.size(); j++) { String[] kv = (String[])v.elementAt(j); if(kv[0].toUpperCase().equals(key)) { value = kv[1]; break; } } if(value != null) break; } return value; } private String[] multiFind(String key) { key = key.toUpperCase(); Vector value = new Vector(); for(int i = 0; i < _configs.size(); i++) { Vector v = (Vector)_configs.elementAt(i); for(int j = 0; j < v.size(); j++) { String[] kv = (String[])v.elementAt(j); if(kv[0].toUpperCase().equals(key)) { String foo = kv[1]; if(foo != null) { value.remove(foo); value.addElement(foo); } } } } String[] result = new String[value.size()]; value.toArray(result); return result; } public String getHostname(){ return find("Hostname"); } public String getUser(){ return find("User"); } public int getPort(){ String foo = find("Port"); int port = -1; try { port = Integer.parseInt(foo); } catch(NumberFormatException e){ // wrong format } return port; } public String getValue(String key){ if(key.equals("compression.s2c") || key.equals("compression.c2s")) { String foo = find(key); if(foo == null || foo.equals("no")) return "none,zlib@openssh.com,zlib"; return "zlib@openssh.com,zlib,none"; } return find(key); } public String[] getValues(String key){ return multiFind(key); } } } jsch-0.1.53/src/main/java/com/jcraft/jsch/RequestWindowChange.java0000644000000000000000000000515712500205415023432 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; class RequestWindowChange extends Request{ int width_columns=80; int height_rows=24; int width_pixels=640; int height_pixels=480; void setSize(int col, int row, int wp, int hp){ this.width_columns=col; this.height_rows=row; this.width_pixels=wp; this.height_pixels=hp; } public void request(Session session, Channel channel) throws Exception{ super.request(session, channel); Buffer buf=new Buffer(); Packet packet=new Packet(buf); //byte SSH_MSG_CHANNEL_REQUEST //uint32 recipient_channel //string "window-change" //boolean FALSE //uint32 terminal width, columns //uint32 terminal height, rows //uint32 terminal width, pixels //uint32 terminal height, pixels packet.reset(); buf.putByte((byte) Session.SSH_MSG_CHANNEL_REQUEST); buf.putInt(channel.getRecipient()); buf.putString(Util.str2byte("window-change")); buf.putByte((byte)(waitForReply() ? 1 : 0)); buf.putInt(width_columns); buf.putInt(height_rows); buf.putInt(width_pixels); buf.putInt(height_pixels); write(packet); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/ChannelShell.java0000644000000000000000000000462412500204726022046 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; import java.util.*; public class ChannelShell extends ChannelSession{ ChannelShell(){ super(); pty=true; } public void start() throws JSchException{ Session _session=getSession(); try{ sendRequests(); Request request=new RequestShell(); request.request(_session, this); } catch(Exception e){ if(e instanceof JSchException) throw (JSchException)e; if(e instanceof Throwable) throw new JSchException("ChannelShell", (Throwable)e); throw new JSchException("ChannelShell"); } if(io.in!=null){ thread=new Thread(this); thread.setName("Shell for "+_session.host); if(_session.daemon_thread){ thread.setDaemon(_session.daemon_thread); } thread.start(); } } void init() throws JSchException { io.setInputStream(getSession().in); io.setOutputStream(getSession().out); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/Request.java0000644000000000000000000000501012500205336021122 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; abstract class Request{ private boolean reply=false; private Session session=null; private Channel channel=null; void request(Session session, Channel channel) throws Exception{ this.session=session; this.channel=channel; if(channel.connectTimeout>0){ setReply(true); } } boolean waitForReply(){ return reply; } void setReply(boolean reply){ this.reply=reply; } void write(Packet packet) throws Exception{ if(reply){ channel.reply=-1; } session.write(packet); if(reply){ long start=System.currentTimeMillis(); long timeout=channel.connectTimeout; while(channel.isConnected() && channel.reply==-1){ try{Thread.sleep(10);} catch(Exception ee){ } if(timeout>0L && (System.currentTimeMillis()-start)>timeout){ channel.reply=0; throw new JSchException("channel request: timeout"); } } if(channel.reply==0){ throw new JSchException("failed to send channel request"); } } } } jsch-0.1.53/src/main/java/com/jcraft/jsch/SftpProgressMonitor.java0000644000000000000000000000340512500205454023512 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public interface SftpProgressMonitor{ public static final int PUT=0; public static final int GET=1; public static final long UNKNOWN_SIZE = -1L; void init(int op, String src, String dest, long max); boolean count(long count); void end(); } jsch-0.1.53/src/main/java/com/jcraft/jsch/SignatureECDSA.java0000644000000000000000000000323612477533123022216 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public interface SignatureECDSA extends Signature { void setPubKey(byte[] r, byte[] s) throws Exception; void setPrvKey(byte[] s) throws Exception; } jsch-0.1.53/src/main/java/com/jcraft/jsch/UserAuthPassword.java0000644000000000000000000001411012500205553022757 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; class UserAuthPassword extends UserAuth{ private final int SSH_MSG_USERAUTH_PASSWD_CHANGEREQ=60; public boolean start(Session session) throws Exception{ super.start(session); byte[] password=session.password; String dest=username+"@"+session.host; if(session.port!=22){ dest+=(":"+session.port); } try{ while(true){ if(session.auth_failures >= session.max_auth_tries){ return false; } if(password==null){ if(userinfo==null){ //throw new JSchException("USERAUTH fail"); return false; } if(!userinfo.promptPassword("Password for "+dest)){ throw new JSchAuthCancelException("password"); //break; } String _password=userinfo.getPassword(); if(_password==null){ throw new JSchAuthCancelException("password"); //break; } password=Util.str2byte(_password); } byte[] _username=null; _username=Util.str2byte(username); // send // byte SSH_MSG_USERAUTH_REQUEST(50) // string user name // string service name ("ssh-connection") // string "password" // boolen FALSE // string plaintext password (ISO-10646 UTF-8) packet.reset(); buf.putByte((byte)SSH_MSG_USERAUTH_REQUEST); buf.putString(_username); buf.putString(Util.str2byte("ssh-connection")); buf.putString(Util.str2byte("password")); buf.putByte((byte)0); buf.putString(password); session.write(packet); loop: while(true){ buf=session.read(buf); int command=buf.getCommand()&0xff; if(command==SSH_MSG_USERAUTH_SUCCESS){ return true; } if(command==SSH_MSG_USERAUTH_BANNER){ buf.getInt(); buf.getByte(); buf.getByte(); byte[] _message=buf.getString(); byte[] lang=buf.getString(); String message=Util.byte2str(_message); if(userinfo!=null){ userinfo.showMessage(message); } continue loop; } if(command==SSH_MSG_USERAUTH_PASSWD_CHANGEREQ){ buf.getInt(); buf.getByte(); buf.getByte(); byte[] instruction=buf.getString(); byte[] tag=buf.getString(); if(userinfo==null || !(userinfo instanceof UIKeyboardInteractive)){ if(userinfo!=null){ userinfo.showMessage("Password must be changed."); } return false; } UIKeyboardInteractive kbi=(UIKeyboardInteractive)userinfo; String[] response; String name="Password Change Required"; String[] prompt={"New Password: "}; boolean[] echo={false}; response=kbi.promptKeyboardInteractive(dest, name, Util.byte2str(instruction), prompt, echo); if(response==null){ throw new JSchAuthCancelException("password"); } byte[] newpassword=Util.str2byte(response[0]); // send // byte SSH_MSG_USERAUTH_REQUEST(50) // string user name // string service name ("ssh-connection") // string "password" // boolen TRUE // string plaintext old password (ISO-10646 UTF-8) // string plaintext new password (ISO-10646 UTF-8) packet.reset(); buf.putByte((byte)SSH_MSG_USERAUTH_REQUEST); buf.putString(_username); buf.putString(Util.str2byte("ssh-connection")); buf.putString(Util.str2byte("password")); buf.putByte((byte)1); buf.putString(password); buf.putString(newpassword); Util.bzero(newpassword); response=null; session.write(packet); continue loop; } if(command==SSH_MSG_USERAUTH_FAILURE){ buf.getInt(); buf.getByte(); buf.getByte(); byte[] foo=buf.getString(); int partial_success=buf.getByte(); //System.err.println(new String(foo)+ // " partial_success:"+(partial_success!=0)); if(partial_success!=0){ throw new JSchPartialAuthException(Util.byte2str(foo)); } session.auth_failures++; break; } else{ //System.err.println("USERAUTH fail ("+buf.getCommand()+")"); // throw new JSchException("USERAUTH fail ("+buf.getCommand()+")"); return false; } } if(password!=null){ Util.bzero(password); password=null; } } } finally{ if(password!=null){ Util.bzero(password); password=null; } } //throw new JSchException("USERAUTH fail"); //return false; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/RequestAgentForwarding.java0000644000000000000000000000432612500205344024134 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2006-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; class RequestAgentForwarding extends Request{ public void request(Session session, Channel channel) throws Exception{ super.request(session, channel); setReply(false); Buffer buf=new Buffer(); Packet packet=new Packet(buf); // byte SSH_MSG_CHANNEL_REQUEST(98) // uint32 recipient channel // string request type // "auth-agent-req@openssh.com" // boolean want reply // 0 packet.reset(); buf.putByte((byte) Session.SSH_MSG_CHANNEL_REQUEST); buf.putInt(channel.getRecipient()); buf.putString(Util.str2byte("auth-agent-req@openssh.com")); buf.putByte((byte)(waitForReply() ? 1 : 0)); write(packet); session.agent_forwarding=true; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/UserAuthGSSAPIWithMIC.java0000644000000000000000000001550512500205530023334 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2006-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT(INCLUDING NEGLIGENCE OR OTHERWISE)ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public class UserAuthGSSAPIWithMIC extends UserAuth { private static final int SSH_MSG_USERAUTH_GSSAPI_RESPONSE= 60; private static final int SSH_MSG_USERAUTH_GSSAPI_TOKEN= 61; private static final int SSH_MSG_USERAUTH_GSSAPI_EXCHANGE_COMPLETE=63; private static final int SSH_MSG_USERAUTH_GSSAPI_ERROR= 64; private static final int SSH_MSG_USERAUTH_GSSAPI_ERRTOK= 65; private static final int SSH_MSG_USERAUTH_GSSAPI_MIC= 66; private static final byte[][] supported_oid={ // OID 1.2.840.113554.1.2.2 in DER {(byte)0x6,(byte)0x9,(byte)0x2a,(byte)0x86,(byte)0x48, (byte)0x86,(byte)0xf7,(byte)0x12,(byte)0x1,(byte)0x2, (byte)0x2} }; private static final String[] supported_method={ "gssapi-with-mic.krb5" }; public boolean start(Session session)throws Exception{ super.start(session); byte[] _username=Util.str2byte(username); packet.reset(); // byte SSH_MSG_USERAUTH_REQUEST(50) // string user name(in ISO-10646 UTF-8 encoding) // string service name(in US-ASCII) // string "gssapi"(US-ASCII) // uint32 n, the number of OIDs client supports // string[n] mechanism OIDS buf.putByte((byte)SSH_MSG_USERAUTH_REQUEST); buf.putString(_username); buf.putString(Util.str2byte("ssh-connection")); buf.putString(Util.str2byte("gssapi-with-mic")); buf.putInt(supported_oid.length); for(int i=0; i0){ socket.setSoTimeout(timeout); } socket.setTcpNoDelay(true); io.setInputStream(in); io.setOutputStream(out); } else{ synchronized(proxy){ proxy.connect(socket_factory, host, port, connectTimeout); io.setInputStream(proxy.getInputStream()); io.setOutputStream(proxy.getOutputStream()); socket=proxy.getSocket(); } } if(connectTimeout>0 && socket!=null){ socket.setSoTimeout(connectTimeout); } isConnected=true; if(JSch.getLogger().isEnabled(Logger.INFO)){ JSch.getLogger().log(Logger.INFO, "Connection established"); } jsch.addSession(this); { // Some Cisco devices will miss to read '\n' if it is sent separately. byte[] foo=new byte[V_C.length+1]; System.arraycopy(V_C, 0, foo, 0, V_C.length); foo[foo.length-1]=(byte)'\n'; io.put(foo, 0, foo.length); } while(true){ i=0; j=0; while(i0 && buf.buffer[i-1]==13){ // 0x0d i--; } } if(i<=3 || ((i!=buf.buffer.length) && (buf.buffer[0]!='S'||buf.buffer[1]!='S'|| buf.buffer[2]!='H'||buf.buffer[3]!='-'))){ // It must not start with 'SSH-' //System.err.println(new String(buf.buffer, 0, i); continue; } if(i==buf.buffer.length || i<7 || // SSH-1.99 or SSH-2.0 (buf.buffer[4]=='1' && buf.buffer[6]!='9') // SSH-1.5 ){ throw new JSchException("invalid server's version string"); } break; } V_S=new byte[i]; System.arraycopy(buf.buffer, 0, V_S, 0, i); //System.err.println("V_S: ("+i+") ["+new String(V_S)+"]"); if(JSch.getLogger().isEnabled(Logger.INFO)){ JSch.getLogger().log(Logger.INFO, "Remote version string: "+Util.byte2str(V_S)); JSch.getLogger().log(Logger.INFO, "Local version string: "+Util.byte2str(V_C)); } send_kexinit(); buf=read(buf); if(buf.getCommand()!=SSH_MSG_KEXINIT){ in_kex=false; throw new JSchException("invalid protocol: "+buf.getCommand()); } if(JSch.getLogger().isEnabled(Logger.INFO)){ JSch.getLogger().log(Logger.INFO, "SSH_MSG_KEXINIT received"); } KeyExchange kex=receive_kexinit(buf); while(true){ buf=read(buf); if(kex.getState()==buf.getCommand()){ kex_start_time=System.currentTimeMillis(); boolean result=kex.next(buf); if(!result){ //System.err.println("verify: "+result); in_kex=false; throw new JSchException("verify: "+result); } } else{ in_kex=false; throw new JSchException("invalid protocol(kex): "+buf.getCommand()); } if(kex.getState()==KeyExchange.STATE_END){ break; } } try{ checkHost(host, port, kex); } catch(JSchException ee){ in_kex=false; throw ee; } send_newkeys(); // receive SSH_MSG_NEWKEYS(21) buf=read(buf); //System.err.println("read: 21 ? "+buf.getCommand()); if(buf.getCommand()==SSH_MSG_NEWKEYS){ if(JSch.getLogger().isEnabled(Logger.INFO)){ JSch.getLogger().log(Logger.INFO, "SSH_MSG_NEWKEYS received"); } receive_newkeys(buf, kex); } else{ in_kex=false; throw new JSchException("invalid protocol(newkyes): "+buf.getCommand()); } try{ String s = getConfig("MaxAuthTries"); if(s!=null){ max_auth_tries = Integer.parseInt(s); } } catch(NumberFormatException e){ throw new JSchException("MaxAuthTries: "+getConfig("MaxAuthTries"), e); } boolean auth=false; boolean auth_cancel=false; UserAuth ua=null; try{ Class c=Class.forName(getConfig("userauth.none")); ua=(UserAuth)(c.newInstance()); } catch(Exception e){ throw new JSchException(e.toString(), e); } auth=ua.start(this); String cmethods=getConfig("PreferredAuthentications"); String[] cmethoda=Util.split(cmethods, ","); String smethods=null; if(!auth){ smethods=((UserAuthNone)ua).getMethods(); if(smethods!=null){ smethods=smethods.toLowerCase(); } else{ // methods: publickey,password,keyboard-interactive //smethods="publickey,password,keyboard-interactive"; smethods=cmethods; } } String[] smethoda=Util.split(smethods, ","); int methodi=0; loop: while(true){ while(!auth && cmethoda!=null && methodi= max_auth_tries){ if(JSch.getLogger().isEnabled(Logger.INFO)){ JSch.getLogger().log(Logger.INFO, "Login trials exceeds "+max_auth_tries); } } if(auth_cancel) throw new JSchException("Auth cancel"); throw new JSchException("Auth fail"); } if(socket!=null && (connectTimeout>0 || timeout>0)){ socket.setSoTimeout(timeout); } isAuthed=true; synchronized(lock){ if(isConnected){ connectThread=new Thread(this); connectThread.setName("Connect thread "+host+" session"); if(daemon_thread){ connectThread.setDaemon(daemon_thread); } connectThread.start(); requestPortForwarding(); } else{ // The session has been already down and // we don't have to start new thread. } } } catch(Exception e) { in_kex=false; try{ if(isConnected){ String message = e.toString(); packet.reset(); buf.checkFreeSize(1+4*3+message.length()+2+buffer_margin); buf.putByte((byte)SSH_MSG_DISCONNECT); buf.putInt(3); buf.putString(Util.str2byte(message)); buf.putString(Util.str2byte("en")); write(packet); } } catch(Exception ee){} try{ disconnect(); } catch(Exception ee){ } isConnected=false; //e.printStackTrace(); if(e instanceof RuntimeException) throw (RuntimeException)e; if(e instanceof JSchException) throw (JSchException)e; throw new JSchException("Session.connect: "+e); } finally{ Util.bzero(this.password); this.password=null; } } private KeyExchange receive_kexinit(Buffer buf) throws Exception { int j=buf.getInt(); if(j!=buf.getLength()){ // packet was compressed and buf.getByte(); // j is the size of deflated packet. I_S=new byte[buf.index-5]; } else{ I_S=new byte[j-1-buf.getByte()]; } System.arraycopy(buf.buffer, buf.s, I_S, 0, I_S.length); if(!in_kex){ // We are in rekeying activated by the remote! send_kexinit(); } guess=KeyExchange.guess(I_S, I_C); if(guess==null){ throw new JSchException("Algorithm negotiation fail"); } if(!isAuthed && (guess[KeyExchange.PROPOSAL_ENC_ALGS_CTOS].equals("none") || (guess[KeyExchange.PROPOSAL_ENC_ALGS_STOC].equals("none")))){ throw new JSchException("NONE Cipher should not be chosen before authentification is successed."); } KeyExchange kex=null; try{ Class c=Class.forName(getConfig(guess[KeyExchange.PROPOSAL_KEX_ALGS])); kex=(KeyExchange)(c.newInstance()); } catch(Exception e){ throw new JSchException(e.toString(), e); } kex.init(this, V_S, V_C, I_S, I_C); return kex; } private volatile boolean in_kex=false; public void rekey() throws Exception { send_kexinit(); } private void send_kexinit() throws Exception { if(in_kex) return; String cipherc2s=getConfig("cipher.c2s"); String ciphers2c=getConfig("cipher.s2c"); String[] not_available_ciphers=checkCiphers(getConfig("CheckCiphers")); if(not_available_ciphers!=null && not_available_ciphers.length>0){ cipherc2s=Util.diffString(cipherc2s, not_available_ciphers); ciphers2c=Util.diffString(ciphers2c, not_available_ciphers); if(cipherc2s==null || ciphers2c==null){ throw new JSchException("There are not any available ciphers."); } } String kex=getConfig("kex"); String[] not_available_kexes=checkKexes(getConfig("CheckKexes")); if(not_available_kexes!=null && not_available_kexes.length>0){ kex=Util.diffString(kex, not_available_kexes); if(kex==null){ throw new JSchException("There are not any available kexes."); } } String server_host_key = getConfig("server_host_key"); String[] not_available_shks = checkSignatures(getConfig("CheckSignatures")); if(not_available_shks!=null && not_available_shks.length>0){ server_host_key=Util.diffString(server_host_key, not_available_shks); if(server_host_key==null){ throw new JSchException("There are not any available sig algorithm."); } } in_kex=true; kex_start_time=System.currentTimeMillis(); // byte SSH_MSG_KEXINIT(20) // byte[16] cookie (random bytes) // string kex_algorithms // string server_host_key_algorithms // string encryption_algorithms_client_to_server // string encryption_algorithms_server_to_client // string mac_algorithms_client_to_server // string mac_algorithms_server_to_client // string compression_algorithms_client_to_server // string compression_algorithms_server_to_client // string languages_client_to_server // string languages_server_to_client Buffer buf = new Buffer(); // send_kexinit may be invoked Packet packet = new Packet(buf); // by user thread. packet.reset(); buf.putByte((byte) SSH_MSG_KEXINIT); synchronized(random){ random.fill(buf.buffer, buf.index, 16); buf.skip(16); } buf.putString(Util.str2byte(kex)); buf.putString(Util.str2byte(server_host_key)); buf.putString(Util.str2byte(cipherc2s)); buf.putString(Util.str2byte(ciphers2c)); buf.putString(Util.str2byte(getConfig("mac.c2s"))); buf.putString(Util.str2byte(getConfig("mac.s2c"))); buf.putString(Util.str2byte(getConfig("compression.c2s"))); buf.putString(Util.str2byte(getConfig("compression.s2c"))); buf.putString(Util.str2byte(getConfig("lang.c2s"))); buf.putString(Util.str2byte(getConfig("lang.s2c"))); buf.putByte((byte)0); buf.putInt(0); buf.setOffSet(5); I_C=new byte[buf.getLength()]; buf.getByte(I_C); write(packet); if(JSch.getLogger().isEnabled(Logger.INFO)){ JSch.getLogger().log(Logger.INFO, "SSH_MSG_KEXINIT sent"); } } private void send_newkeys() throws Exception { // send SSH_MSG_NEWKEYS(21) packet.reset(); buf.putByte((byte)SSH_MSG_NEWKEYS); write(packet); if(JSch.getLogger().isEnabled(Logger.INFO)){ JSch.getLogger().log(Logger.INFO, "SSH_MSG_NEWKEYS sent"); } } private void checkHost(String chost, int port, KeyExchange kex) throws JSchException { String shkc=getConfig("StrictHostKeyChecking"); if(hostKeyAlias!=null){ chost=hostKeyAlias; } //System.err.println("shkc: "+shkc); byte[] K_S=kex.getHostKey(); String key_type=kex.getKeyType(); String key_fprint=kex.getFingerPrint(); if(hostKeyAlias==null && port!=22){ chost=("["+chost+"]:"+port); } HostKeyRepository hkr=getHostKeyRepository(); String hkh=getConfig("HashKnownHosts"); if(hkh.equals("yes") && (hkr instanceof KnownHosts)){ hostkey=((KnownHosts)hkr).createHashedHostKey(chost, K_S); } else{ hostkey=new HostKey(chost, K_S); } int i=0; synchronized(hkr){ i=hkr.check(chost, K_S); } boolean insert=false; if((shkc.equals("ask") || shkc.equals("yes")) && i==HostKeyRepository.CHANGED){ String file=null; synchronized(hkr){ file=hkr.getKnownHostsRepositoryID(); } if(file==null){file="known_hosts";} boolean b=false; if(userinfo!=null){ String message= "WARNING: REMOTE HOST IDENTIFICATION HAS CHANGED!\n"+ "IT IS POSSIBLE THAT SOMEONE IS DOING SOMETHING NASTY!\n"+ "Someone could be eavesdropping on you right now (man-in-the-middle attack)!\n"+ "It is also possible that the "+key_type+" host key has just been changed.\n"+ "The fingerprint for the "+key_type+" key sent by the remote host "+chost+" is\n"+ key_fprint+".\n"+ "Please contact your system administrator.\n"+ "Add correct host key in "+file+" to get rid of this message."; if(shkc.equals("ask")){ b=userinfo.promptYesNo(message+ "\nDo you want to delete the old key and insert the new key?"); } else{ // shkc.equals("yes") userinfo.showMessage(message); } } if(!b){ throw new JSchException("HostKey has been changed: "+chost); } synchronized(hkr){ hkr.remove(chost, kex.getKeyAlgorithName(), null); insert=true; } } if((shkc.equals("ask") || shkc.equals("yes")) && (i!=HostKeyRepository.OK) && !insert){ if(shkc.equals("yes")){ throw new JSchException("reject HostKey: "+host); } //System.err.println("finger-print: "+key_fprint); if(userinfo!=null){ boolean foo=userinfo.promptYesNo( "The authenticity of host '"+host+"' can't be established.\n"+ key_type+" key fingerprint is "+key_fprint+".\n"+ "Are you sure you want to continue connecting?" ); if(!foo){ throw new JSchException("reject HostKey: "+host); } insert=true; } else{ if(i==HostKeyRepository.NOT_INCLUDED) throw new JSchException("UnknownHostKey: "+host+". "+key_type+" key fingerprint is "+key_fprint); else throw new JSchException("HostKey has been changed: "+host); } } if(shkc.equals("no") && HostKeyRepository.NOT_INCLUDED==i){ insert=true; } if(i==HostKeyRepository.OK){ HostKey[] keys = hkr.getHostKey(chost, kex.getKeyAlgorithName()); String _key= Util.byte2str(Util.toBase64(K_S, 0, K_S.length)); for(int j=0; j< keys.length; j++){ if(keys[i].getKey().equals(_key) && keys[j].getMarker().equals("@revoked")){ if(userinfo!=null){ userinfo.showMessage( "The "+ key_type +" host key for "+ host +" is marked as revoked.\n"+ "This could mean that a stolen key is being used to "+ "impersonate this host."); } if(JSch.getLogger().isEnabled(Logger.INFO)){ JSch.getLogger().log(Logger.INFO, "Host '"+host+"' has provided revoked key."); } throw new JSchException("revoked HostKey: "+host); } } } if(i==HostKeyRepository.OK && JSch.getLogger().isEnabled(Logger.INFO)){ JSch.getLogger().log(Logger.INFO, "Host '"+host+"' is known and matches the "+key_type+" host key"); } if(insert && JSch.getLogger().isEnabled(Logger.WARN)){ JSch.getLogger().log(Logger.WARN, "Permanently added '"+host+"' ("+key_type+") to the list of known hosts."); } if(insert){ synchronized(hkr){ hkr.add(hostkey, userinfo); } } } //public void start(){ (new Thread(this)).start(); } public Channel openChannel(String type) throws JSchException{ if(!isConnected){ throw new JSchException("session is down"); } try{ Channel channel=Channel.getChannel(type); addChannel(channel); channel.init(); if(channel instanceof ChannelSession){ applyConfigChannel((ChannelSession)channel); } return channel; } catch(Exception e){ //e.printStackTrace(); } return null; } // encode will bin invoked in write with synchronization. public void encode(Packet packet) throws Exception{ //System.err.println("encode: "+packet.buffer.getCommand()); //System.err.println(" "+packet.buffer.index); //if(packet.buffer.getCommand()==96){ //Thread.dumpStack(); //} if(deflater!=null){ compress_len[0]=packet.buffer.index; packet.buffer.buffer=deflater.compress(packet.buffer.buffer, 5, compress_len); packet.buffer.index=compress_len[0]; } if(c2scipher!=null){ //packet.padding(c2scipher.getIVSize()); packet.padding(c2scipher_size); int pad=packet.buffer.buffer[4]; synchronized(random){ random.fill(packet.buffer.buffer, packet.buffer.index-pad, pad); } } else{ packet.padding(8); } if(c2smac!=null){ c2smac.update(seqo); c2smac.update(packet.buffer.buffer, 0, packet.buffer.index); c2smac.doFinal(packet.buffer.buffer, packet.buffer.index); } if(c2scipher!=null){ byte[] buf=packet.buffer.buffer; c2scipher.update(buf, 0, packet.buffer.index, buf, 0); } if(c2smac!=null){ packet.buffer.skip(c2smac.getBlockSize()); } } int[] uncompress_len=new int[1]; int[] compress_len=new int[1]; private int s2ccipher_size=8; private int c2scipher_size=8; public Buffer read(Buffer buf) throws Exception{ int j=0; while(true){ buf.reset(); io.getByte(buf.buffer, buf.index, s2ccipher_size); buf.index+=s2ccipher_size; if(s2ccipher!=null){ s2ccipher.update(buf.buffer, 0, s2ccipher_size, buf.buffer, 0); } j=((buf.buffer[0]<<24)&0xff000000)| ((buf.buffer[1]<<16)&0x00ff0000)| ((buf.buffer[2]<< 8)&0x0000ff00)| ((buf.buffer[3] )&0x000000ff); // RFC 4253 6.1. Maximum Packet Length if(j<5 || j>PACKET_MAX_SIZE){ start_discard(buf, s2ccipher, s2cmac, j, PACKET_MAX_SIZE); } int need = j+4-s2ccipher_size; //if(need<0){ // throw new IOException("invalid data"); //} if((buf.index+need)>buf.buffer.length){ byte[] foo=new byte[buf.index+need]; System.arraycopy(buf.buffer, 0, foo, 0, buf.index); buf.buffer=foo; } if((need%s2ccipher_size)!=0){ String message="Bad packet length "+need; if(JSch.getLogger().isEnabled(Logger.FATAL)){ JSch.getLogger().log(Logger.FATAL, message); } start_discard(buf, s2ccipher, s2cmac, j, PACKET_MAX_SIZE-s2ccipher_size); } if(need>0){ io.getByte(buf.buffer, buf.index, need); buf.index+=(need); if(s2ccipher!=null){ s2ccipher.update(buf.buffer, s2ccipher_size, need, buf.buffer, s2ccipher_size); } } if(s2cmac!=null){ s2cmac.update(seqi); s2cmac.update(buf.buffer, 0, buf.index); s2cmac.doFinal(s2cmac_result1, 0); io.getByte(s2cmac_result2, 0, s2cmac_result2.length); if(!java.util.Arrays.equals(s2cmac_result1, s2cmac_result2)){ if(need > PACKET_MAX_SIZE){ throw new IOException("MAC Error"); } start_discard(buf, s2ccipher, s2cmac, j, PACKET_MAX_SIZE-need); continue; } } seqi++; if(inflater!=null){ //inflater.uncompress(buf); int pad=buf.buffer[4]; uncompress_len[0]=buf.index-5-pad; byte[] foo=inflater.uncompress(buf.buffer, 5, uncompress_len); if(foo!=null){ buf.buffer=foo; buf.index=5+uncompress_len[0]; } else{ System.err.println("fail in inflater"); break; } } int type=buf.getCommand()&0xff; //System.err.println("read: "+type); if(type==SSH_MSG_DISCONNECT){ buf.rewind(); buf.getInt();buf.getShort(); int reason_code=buf.getInt(); byte[] description=buf.getString(); byte[] language_tag=buf.getString(); throw new JSchException("SSH_MSG_DISCONNECT: "+ reason_code+ " "+Util.byte2str(description)+ " "+Util.byte2str(language_tag)); //break; } else if(type==SSH_MSG_IGNORE){ } else if(type==SSH_MSG_UNIMPLEMENTED){ buf.rewind(); buf.getInt();buf.getShort(); int reason_id=buf.getInt(); if(JSch.getLogger().isEnabled(Logger.INFO)){ JSch.getLogger().log(Logger.INFO, "Received SSH_MSG_UNIMPLEMENTED for "+reason_id); } } else if(type==SSH_MSG_DEBUG){ buf.rewind(); buf.getInt();buf.getShort(); /* byte always_display=(byte)buf.getByte(); byte[] message=buf.getString(); byte[] language_tag=buf.getString(); System.err.println("SSH_MSG_DEBUG:"+ " "+Util.byte2str(message)+ " "+Util.byte2str(language_tag)); */ } else if(type==SSH_MSG_CHANNEL_WINDOW_ADJUST){ buf.rewind(); buf.getInt();buf.getShort(); Channel c=Channel.getChannel(buf.getInt(), this); if(c==null){ } else{ c.addRemoteWindowSize(buf.getUInt()); } } else if(type==UserAuth.SSH_MSG_USERAUTH_SUCCESS){ isAuthed=true; if(inflater==null && deflater==null){ String method; method=guess[KeyExchange.PROPOSAL_COMP_ALGS_CTOS]; initDeflater(method); method=guess[KeyExchange.PROPOSAL_COMP_ALGS_STOC]; initInflater(method); } break; } else{ break; } } buf.rewind(); return buf; } private void start_discard(Buffer buf, Cipher cipher, MAC mac, int packet_length, int discard) throws JSchException, IOException{ MAC discard_mac = null; if(!cipher.isCBC()){ throw new JSchException("Packet corrupt"); } if(packet_length!=PACKET_MAX_SIZE && mac != null){ discard_mac = mac; } discard -= buf.index; while(discard>0){ buf.reset(); int len = discard>buf.buffer.length ? buf.buffer.length : discard; io.getByte(buf.buffer, 0, len); if(discard_mac!=null){ discard_mac.update(buf.buffer, 0, len); } discard -= len; } if(discard_mac!=null){ discard_mac.doFinal(buf.buffer, 0); } throw new JSchException("Packet corrupt"); } byte[] getSessionId(){ return session_id; } private void receive_newkeys(Buffer buf, KeyExchange kex) throws Exception { updateKeys(kex); in_kex=false; } private void updateKeys(KeyExchange kex) throws Exception{ byte[] K=kex.getK(); byte[] H=kex.getH(); HASH hash=kex.getHash(); if(session_id==null){ session_id=new byte[H.length]; System.arraycopy(H, 0, session_id, 0, H.length); } /* Initial IV client to server: HASH (K || H || "A" || session_id) Initial IV server to client: HASH (K || H || "B" || session_id) Encryption key client to server: HASH (K || H || "C" || session_id) Encryption key server to client: HASH (K || H || "D" || session_id) Integrity key client to server: HASH (K || H || "E" || session_id) Integrity key server to client: HASH (K || H || "F" || session_id) */ buf.reset(); buf.putMPInt(K); buf.putByte(H); buf.putByte((byte)0x41); buf.putByte(session_id); hash.update(buf.buffer, 0, buf.index); IVc2s=hash.digest(); int j=buf.index-session_id.length-1; buf.buffer[j]++; hash.update(buf.buffer, 0, buf.index); IVs2c=hash.digest(); buf.buffer[j]++; hash.update(buf.buffer, 0, buf.index); Ec2s=hash.digest(); buf.buffer[j]++; hash.update(buf.buffer, 0, buf.index); Es2c=hash.digest(); buf.buffer[j]++; hash.update(buf.buffer, 0, buf.index); MACc2s=hash.digest(); buf.buffer[j]++; hash.update(buf.buffer, 0, buf.index); MACs2c=hash.digest(); try{ Class c; String method; method=guess[KeyExchange.PROPOSAL_ENC_ALGS_STOC]; c=Class.forName(getConfig(method)); s2ccipher=(Cipher)(c.newInstance()); while(s2ccipher.getBlockSize()>Es2c.length){ buf.reset(); buf.putMPInt(K); buf.putByte(H); buf.putByte(Es2c); hash.update(buf.buffer, 0, buf.index); byte[] foo=hash.digest(); byte[] bar=new byte[Es2c.length+foo.length]; System.arraycopy(Es2c, 0, bar, 0, Es2c.length); System.arraycopy(foo, 0, bar, Es2c.length, foo.length); Es2c=bar; } s2ccipher.init(Cipher.DECRYPT_MODE, Es2c, IVs2c); s2ccipher_size=s2ccipher.getIVSize(); method=guess[KeyExchange.PROPOSAL_MAC_ALGS_STOC]; c=Class.forName(getConfig(method)); s2cmac=(MAC)(c.newInstance()); MACs2c = expandKey(buf, K, H, MACs2c, hash, s2cmac.getBlockSize()); s2cmac.init(MACs2c); //mac_buf=new byte[s2cmac.getBlockSize()]; s2cmac_result1=new byte[s2cmac.getBlockSize()]; s2cmac_result2=new byte[s2cmac.getBlockSize()]; method=guess[KeyExchange.PROPOSAL_ENC_ALGS_CTOS]; c=Class.forName(getConfig(method)); c2scipher=(Cipher)(c.newInstance()); while(c2scipher.getBlockSize()>Ec2s.length){ buf.reset(); buf.putMPInt(K); buf.putByte(H); buf.putByte(Ec2s); hash.update(buf.buffer, 0, buf.index); byte[] foo=hash.digest(); byte[] bar=new byte[Ec2s.length+foo.length]; System.arraycopy(Ec2s, 0, bar, 0, Ec2s.length); System.arraycopy(foo, 0, bar, Ec2s.length, foo.length); Ec2s=bar; } c2scipher.init(Cipher.ENCRYPT_MODE, Ec2s, IVc2s); c2scipher_size=c2scipher.getIVSize(); method=guess[KeyExchange.PROPOSAL_MAC_ALGS_CTOS]; c=Class.forName(getConfig(method)); c2smac=(MAC)(c.newInstance()); MACc2s = expandKey(buf, K, H, MACc2s, hash, c2smac.getBlockSize()); c2smac.init(MACc2s); method=guess[KeyExchange.PROPOSAL_COMP_ALGS_CTOS]; initDeflater(method); method=guess[KeyExchange.PROPOSAL_COMP_ALGS_STOC]; initInflater(method); } catch(Exception e){ if(e instanceof JSchException) throw e; throw new JSchException(e.toString(), e); //System.err.println("updatekeys: "+e); } } /* * RFC 4253 7.2. Output from Key Exchange * If the key length needed is longer than the output of the HASH, the * key is extended by computing HASH of the concatenation of K and H and * the entire key so far, and appending the resulting bytes (as many as * HASH generates) to the key. This process is repeated until enough * key material is available; the key is taken from the beginning of * this value. In other words: * K1 = HASH(K || H || X || session_id) (X is e.g., "A") * K2 = HASH(K || H || K1) * K3 = HASH(K || H || K1 || K2) * ... * key = K1 || K2 || K3 || ... */ private byte[] expandKey(Buffer buf, byte[] K, byte[] H, byte[] key, HASH hash, int required_length) throws Exception { byte[] result = key; int size = hash.getBlockSize(); while(result.length < required_length){ buf.reset(); buf.putMPInt(K); buf.putByte(H); buf.putByte(result); hash.update(buf.buffer, 0, buf.index); byte[] tmp = new byte[result.length+size]; System.arraycopy(result, 0, tmp, 0, result.length); System.arraycopy(hash.digest(), 0, tmp, result.length, size); Util.bzero(result); result = tmp; } return result; } /*public*/ /*synchronized*/ void write(Packet packet, Channel c, int length) throws Exception{ long t = getTimeout(); while(true){ if(in_kex){ if(t>0L && (System.currentTimeMillis()-kex_start_time)>t){ throw new JSchException("timeout in wating for rekeying process."); } try{Thread.sleep(10);} catch(java.lang.InterruptedException e){}; continue; } synchronized(c){ if(c.rwsize=length){ c.rwsize-=length; break; } } if(c.close || !c.isConnected()){ throw new IOException("channel is broken"); } boolean sendit=false; int s=0; byte command=0; int recipient=-1; synchronized(c){ if(c.rwsize>0){ long len=c.rwsize; if(len>length){ len=length; } if(len!=length){ s=packet.shift((int)len, (c2scipher!=null ? c2scipher_size : 8), (c2smac!=null ? c2smac.getBlockSize() : 0)); } command=packet.buffer.getCommand(); recipient=c.getRecipient(); length-=len; c.rwsize-=len; sendit=true; } } if(sendit){ _write(packet); if(length==0){ return; } packet.unshift(command, recipient, s, length); } synchronized(c){ if(in_kex){ continue; } if(c.rwsize>=length){ c.rwsize-=length; break; } //try{ //System.out.println("1wait: "+c.rwsize); // c.notifyme++; // c.wait(100); //} //catch(java.lang.InterruptedException e){ //} //finally{ // c.notifyme--; //} } } _write(packet); } public void write(Packet packet) throws Exception{ // System.err.println("in_kex="+in_kex+" "+(packet.buffer.getCommand())); long t = getTimeout(); while(in_kex){ if(t>0L && (System.currentTimeMillis()-kex_start_time)>t){ throw new JSchException("timeout in wating for rekeying process."); } byte command=packet.buffer.getCommand(); //System.err.println("command: "+command); if(command==SSH_MSG_KEXINIT || command==SSH_MSG_NEWKEYS || command==SSH_MSG_KEXDH_INIT || command==SSH_MSG_KEXDH_REPLY || command==SSH_MSG_KEX_DH_GEX_GROUP || command==SSH_MSG_KEX_DH_GEX_INIT || command==SSH_MSG_KEX_DH_GEX_REPLY || command==SSH_MSG_KEX_DH_GEX_REQUEST || command==SSH_MSG_DISCONNECT){ break; } try{Thread.sleep(10);} catch(java.lang.InterruptedException e){}; } _write(packet); } private void _write(Packet packet) throws Exception{ synchronized(lock){ encode(packet); if(io!=null){ io.put(packet); seqo++; } } } Runnable thread; public void run(){ thread=this; byte[] foo; Buffer buf=new Buffer(); Packet packet=new Packet(buf); int i=0; Channel channel; int[] start=new int[1]; int[] length=new int[1]; KeyExchange kex=null; int stimeout=0; try{ while(isConnected && thread!=null){ try{ buf=read(buf); stimeout=0; } catch(InterruptedIOException/*SocketTimeoutException*/ ee){ if(!in_kex && stimeoutlport is 0, the tcp port will be allocated. * @param lport local port for local port forwarding * @param host host address for local port forwarding * @param rport remote port number for local port forwarding * @return an allocated local TCP port number * @see #setPortForwardingL(String bind_address, int lport, String host, int rport, ServerSocketFactory ssf, int connectTimeout) */ public int setPortForwardingL(int lport, String host, int rport) throws JSchException{ return setPortForwardingL("127.0.0.1", lport, host, rport); } /** * Registers the local port forwarding. If bind_address is an empty string * or '*', the port should be available from all interfaces. * If bind_address is "localhost" or * null, the listening port will be bound for local use only. * If lport is 0, the tcp port will be allocated. * @param bind_address bind address for local port forwarding * @param lport local port for local port forwarding * @param host host address for local port forwarding * @param rport remote port number for local port forwarding * @return an allocated local TCP port number * @see #setPortForwardingL(String bind_address, int lport, String host, int rport, ServerSocketFactory ssf, int connectTimeout) */ public int setPortForwardingL(String bind_address, int lport, String host, int rport) throws JSchException{ return setPortForwardingL(bind_address, lport, host, rport, null); } /** * Registers the local port forwarding. * If bind_address is an empty string or "*", * the port should be available from all interfaces. * If bind_address is "localhost" or * null, the listening port will be bound for local use only. * If lport is 0, the tcp port will be allocated. * @param bind_address bind address for local port forwarding * @param lport local port for local port forwarding * @param host host address for local port forwarding * @param rport remote port number for local port forwarding * @param ssf socket factory * @return an allocated local TCP port number * @see #setPortForwardingL(String bind_address, int lport, String host, int rport, ServerSocketFactory ssf, int connectTimeout) */ public int setPortForwardingL(String bind_address, int lport, String host, int rport, ServerSocketFactory ssf) throws JSchException{ return setPortForwardingL(bind_address, lport, host, rport, ssf, 0); } /** * Registers the local port forwarding. * If bind_address is an empty string * or "*", the port should be available from all interfaces. * If bind_address is "localhost" or * null, the listening port will be bound for local use only. * If lport is 0, the tcp port will be allocated. * @param bind_address bind address for local port forwarding * @param lport local port for local port forwarding * @param host host address for local port forwarding * @param rport remote port number for local port forwarding * @param ssf socket factory * @param connectTimeout timeout for establishing port connection * @return an allocated local TCP port number */ public int setPortForwardingL(String bind_address, int lport, String host, int rport, ServerSocketFactory ssf, int connectTimeout) throws JSchException{ PortWatcher pw=PortWatcher.addPort(this, bind_address, lport, host, rport, ssf); pw.setConnectTimeout(connectTimeout); Thread tmp=new Thread(pw); tmp.setName("PortWatcher Thread for "+host); if(daemon_thread){ tmp.setDaemon(daemon_thread); } tmp.start(); return pw.lport; } /** * Cancels the local port forwarding assigned * at local TCP port lport on loopback interface. * * @param lport local TCP port */ public void delPortForwardingL(int lport) throws JSchException{ delPortForwardingL("127.0.0.1", lport); } /** * Cancels the local port forwarding assigned * at local TCP port lport on bind_address interface. * * @param bind_address bind_address of network interfaces * @param lport local TCP port */ public void delPortForwardingL(String bind_address, int lport) throws JSchException{ PortWatcher.delPort(this, bind_address, lport); } /** * Lists the registered local port forwarding. * * @return a list of "lport:host:hostport" */ public String[] getPortForwardingL() throws JSchException{ return PortWatcher.getPortForwarding(this); } /** * Registers the remote port forwarding for the loopback interface * of the remote. * * @param rport remote port * @param host host address * @param lport local port * @see #setPortForwardingR(String bind_address, int rport, String host, int lport, SocketFactory sf) */ public void setPortForwardingR(int rport, String host, int lport) throws JSchException{ setPortForwardingR(null, rport, host, lport, (SocketFactory)null); } /** * Registers the remote port forwarding. * If bind_address is an empty string or "*", * the port should be available from all interfaces. * If bind_address is "localhost" or is not given, * the listening port will be bound for local use only. * Note that if GatewayPorts is "no" on the * remote, "localhost" is always used as a bind_address. * * @param bind_address bind address * @param rport remote port * @param host host address * @param lport local port * @see #setPortForwardingR(String bind_address, int rport, String host, int lport, SocketFactory sf) */ public void setPortForwardingR(String bind_address, int rport, String host, int lport) throws JSchException{ setPortForwardingR(bind_address, rport, host, lport, (SocketFactory)null); } /** * Registers the remote port forwarding for the loopback interface * of the remote. * * @param rport remote port * @param host host address * @param lport local port * @param sf socket factory * @see #setPortForwardingR(String bind_address, int rport, String host, int lport, SocketFactory sf) */ public void setPortForwardingR(int rport, String host, int lport, SocketFactory sf) throws JSchException{ setPortForwardingR(null, rport, host, lport, sf); } // TODO: This method should return the integer value as the assigned port. /** * Registers the remote port forwarding. * If bind_address is an empty string or "*", * the port should be available from all interfaces. * If bind_address is "localhost" or is not given, * the listening port will be bound for local use only. * Note that if GatewayPorts is "no" on the * remote, "localhost" is always used as a bind_address. * If rport is 0, the TCP port will be allocated on the remote. * * @param bind_address bind address * @param rport remote port * @param host host address * @param lport local port * @param sf socket factory */ public void setPortForwardingR(String bind_address, int rport, String host, int lport, SocketFactory sf) throws JSchException{ int allocated=_setPortForwardingR(bind_address, rport); ChannelForwardedTCPIP.addPort(this, bind_address, rport, allocated, host, lport, sf); } /** * Registers the remote port forwarding for the loopback interface * of the remote. * The TCP connection to rport on the remote will be * forwarded to an instance of the class daemon. * The class specified by daemon must implement * ForwardedTCPIPDaemon. * * @param rport remote port * @param daemon class name, which implements "ForwardedTCPIPDaemon" * @see #setPortForwardingR(String bind_address, int rport, String daemon, Object[] arg) */ public void setPortForwardingR(int rport, String daemon) throws JSchException{ setPortForwardingR(null, rport, daemon, null); } /** * Registers the remote port forwarding for the loopback interface * of the remote. * The TCP connection to rport on the remote will be * forwarded to an instance of the class daemon with * the argument arg. * The class specified by daemon must implement ForwardedTCPIPDaemon. * * @param rport remote port * @param daemon class name, which implements "ForwardedTCPIPDaemon" * @param arg arguments for "daemon" * @see #setPortForwardingR(String bind_address, int rport, String daemon, Object[] arg) */ public void setPortForwardingR(int rport, String daemon, Object[] arg) throws JSchException{ setPortForwardingR(null, rport, daemon, arg); } /** * Registers the remote port forwarding. * If bind_address is an empty string * or "*", the port should be available from all interfaces. * If bind_address is "localhost" or is not given, * the listening port will be bound for local use only. * Note that if GatewayPorts is "no" on the * remote, "localhost" is always used as a bind_address. * The TCP connection to rport on the remote will be * forwarded to an instance of the class daemon with the * argument arg. * The class specified by daemon must implement ForwardedTCPIPDaemon. * * @param bind_address bind address * @param rport remote port * @param daemon class name, which implements "ForwardedTCPIPDaemon" * @param arg arguments for "daemon" * @see #setPortForwardingR(String bind_address, int rport, String daemon, Object[] arg) */ public void setPortForwardingR(String bind_address, int rport, String daemon, Object[] arg) throws JSchException{ int allocated = _setPortForwardingR(bind_address, rport); ChannelForwardedTCPIP.addPort(this, bind_address, rport, allocated, daemon, arg); } /** * Lists the registered remote port forwarding. * * @return a list of "rport:host:hostport" */ public String[] getPortForwardingR() throws JSchException{ return ChannelForwardedTCPIP.getPortForwarding(this); } private class Forwarding { String bind_address = null; int port = -1; String host = null; int hostport = -1; } /** * The given argument may be "[bind_address:]port:host:hostport" or * "[bind_address:]port host:hostport", which is from LocalForward command of * ~/.ssh/config . */ private Forwarding parseForwarding(String conf) throws JSchException { String[] tmp = conf.split(" "); if(tmp.length>1){ // "[bind_address:]port host:hostport" Vector foo = new Vector(); for(int i=0; ibind_address is an empty string or "*", * the port should be available from all interfaces. * If bind_address is "localhost" or is not given, * the listening port will be bound for local use only. * * @param conf configuration of local port forwarding * @return an assigned port number * @see #setPortForwardingL(String bind_address, int lport, String host, int rport) */ public int setPortForwardingL(String conf) throws JSchException { Forwarding f = parseForwarding(conf); return setPortForwardingL(f.bind_address, f.port, f.host, f.hostport); } /** * Registers the remote port forwarding. The argument should be * in the format like "[bind_address:]port:host:hostport". If the * bind_address is not given, the default is to only bind to loopback * addresses. If the bind_address is "*" or an empty string, * then the forwarding is requested to listen on all interfaces. * Note that if GatewayPorts is "no" on the remote, * "localhost" is always used for bind_address. * If the specified remote is "0", * the TCP port will be allocated on the remote. * * @param conf configuration of remote port forwarding * @return an allocated TCP port on the remote. * @see #setPortForwardingR(String bind_address, int rport, String host, int rport) */ public int setPortForwardingR(String conf) throws JSchException { Forwarding f = parseForwarding(conf); int allocated = _setPortForwardingR(f.bind_address, f.port); ChannelForwardedTCPIP.addPort(this, f.bind_address, f.port, allocated, f.host, f.hostport, null); return allocated; } /** * Instantiates an instance of stream-forwarder to host:port. * Set I/O stream to the given channel, and then invoke Channel#connect() method. * * @param host remote host, which the given stream will be plugged to. * @param port remote port, which the given stream will be plugged to. */ public Channel getStreamForwarder(String host, int port) throws JSchException { ChannelDirectTCPIP channel = new ChannelDirectTCPIP(); channel.init(); this.addChannel(channel); channel.setHost(host); channel.setPort(port); return channel; } private class GlobalRequestReply{ private Thread thread=null; private int reply=-1; private int port=0; void setThread(Thread thread){ this.thread=thread; this.reply=-1; } Thread getThread(){ return thread; } void setReply(int reply){ this.reply=reply; } int getReply(){ return this.reply; } int getPort(){ return this.port; } void setPort(int port){ this.port=port; } } private GlobalRequestReply grr=new GlobalRequestReply(); private int _setPortForwardingR(String bind_address, int rport) throws JSchException{ synchronized(grr){ Buffer buf=new Buffer(100); // ?? Packet packet=new Packet(buf); String address_to_bind=ChannelForwardedTCPIP.normalize(bind_address); grr.setThread(Thread.currentThread()); grr.setPort(rport); try{ // byte SSH_MSG_GLOBAL_REQUEST 80 // string "tcpip-forward" // boolean want_reply // string address_to_bind // uint32 port number to bind packet.reset(); buf.putByte((byte) SSH_MSG_GLOBAL_REQUEST); buf.putString(Util.str2byte("tcpip-forward")); buf.putByte((byte)1); buf.putString(Util.str2byte(address_to_bind)); buf.putInt(rport); write(packet); } catch(Exception e){ grr.setThread(null); if(e instanceof Throwable) throw new JSchException(e.toString(), (Throwable)e); throw new JSchException(e.toString()); } int count = 0; int reply = grr.getReply(); while(count < 10 && reply == -1){ try{ Thread.sleep(1000); } catch(Exception e){ } count++; reply = grr.getReply(); } grr.setThread(null); if(reply != 1){ throw new JSchException("remote port forwarding failed for listen port "+rport); } rport=grr.getPort(); } return rport; } /** * Cancels the remote port forwarding assigned at remote TCP port rport. * * @param rport remote TCP port */ public void delPortForwardingR(int rport) throws JSchException{ this.delPortForwardingR(null, rport); } /** * Cancels the remote port forwarding assigned at * remote TCP port rport bound on the interface at * bind_address. * * @param bind_address bind address of the interface on the remote * @param rport remote TCP port */ public void delPortForwardingR(String bind_address, int rport) throws JSchException{ ChannelForwardedTCPIP.delPort(this, bind_address, rport); } private void initDeflater(String method) throws JSchException{ if(method.equals("none")){ deflater=null; return; } String foo=getConfig(method); if(foo!=null){ if(method.equals("zlib") || (isAuthed && method.equals("zlib@openssh.com"))){ try{ Class c=Class.forName(foo); deflater=(Compression)(c.newInstance()); int level=6; try{ level=Integer.parseInt(getConfig("compression_level"));} catch(Exception ee){ } deflater.init(Compression.DEFLATER, level); } catch(NoClassDefFoundError ee){ throw new JSchException(ee.toString(), ee); } catch(Exception ee){ throw new JSchException(ee.toString(), ee); //System.err.println(foo+" isn't accessible."); } } } } private void initInflater(String method) throws JSchException{ if(method.equals("none")){ inflater=null; return; } String foo=getConfig(method); if(foo!=null){ if(method.equals("zlib") || (isAuthed && method.equals("zlib@openssh.com"))){ try{ Class c=Class.forName(foo); inflater=(Compression)(c.newInstance()); inflater.init(Compression.INFLATER, 0); } catch(Exception ee){ throw new JSchException(ee.toString(), ee); //System.err.println(foo+" isn't accessible."); } } } } void addChannel(Channel channel){ channel.setSession(this); } public void setProxy(Proxy proxy){ this.proxy=proxy; } public void setHost(String host){ this.host=host; } public void setPort(int port){ this.port=port; } void setUserName(String username){ this.username=username; } public void setUserInfo(UserInfo userinfo){ this.userinfo=userinfo; } public UserInfo getUserInfo(){ return userinfo; } public void setInputStream(InputStream in){ this.in=in; } public void setOutputStream(OutputStream out){ this.out=out; } public void setX11Host(String host){ ChannelX11.setHost(host); } public void setX11Port(int port){ ChannelX11.setPort(port); } public void setX11Cookie(String cookie){ ChannelX11.setCookie(cookie); } public void setPassword(String password){ if(password!=null) this.password=Util.str2byte(password); } public void setPassword(byte[] password){ if(password!=null){ this.password=new byte[password.length]; System.arraycopy(password, 0, this.password, 0, password.length); } } public void setConfig(java.util.Properties newconf){ setConfig((java.util.Hashtable)newconf); } public void setConfig(java.util.Hashtable newconf){ synchronized(lock){ if(config==null) config=new java.util.Hashtable(); for(java.util.Enumeration e=newconf.keys() ; e.hasMoreElements() ;) { String key=(String)(e.nextElement()); config.put(key, (String)(newconf.get(key))); } } } public void setConfig(String key, String value){ synchronized(lock){ if(config==null){ config=new java.util.Hashtable(); } config.put(key, value); } } public String getConfig(String key){ Object foo=null; if(config!=null){ foo=config.get(key); if(foo instanceof String) return (String)foo; } foo=jsch.getConfig(key); if(foo instanceof String) return (String)foo; return null; } public void setSocketFactory(SocketFactory sfactory){ socket_factory=sfactory; } public boolean isConnected(){ return isConnected; } public int getTimeout(){ return timeout; } public void setTimeout(int timeout) throws JSchException { if(socket==null){ if(timeout<0){ throw new JSchException("invalid timeout value"); } this.timeout=timeout; return; } try{ socket.setSoTimeout(timeout); this.timeout=timeout; } catch(Exception e){ if(e instanceof Throwable) throw new JSchException(e.toString(), (Throwable)e); throw new JSchException(e.toString()); } } public String getServerVersion(){ return Util.byte2str(V_S); } public String getClientVersion(){ return Util.byte2str(V_C); } public void setClientVersion(String cv){ V_C=Util.str2byte(cv); } public void sendIgnore() throws Exception{ Buffer buf=new Buffer(); Packet packet=new Packet(buf); packet.reset(); buf.putByte((byte)SSH_MSG_IGNORE); write(packet); } private static final byte[] keepalivemsg=Util.str2byte("keepalive@jcraft.com"); public void sendKeepAliveMsg() throws Exception{ Buffer buf=new Buffer(); Packet packet=new Packet(buf); packet.reset(); buf.putByte((byte)SSH_MSG_GLOBAL_REQUEST); buf.putString(keepalivemsg); buf.putByte((byte)1); write(packet); } private static final byte[] nomoresessions=Util.str2byte("no-more-sessions@openssh.com"); public void noMoreSessionChannels() throws Exception{ Buffer buf=new Buffer(); Packet packet=new Packet(buf); packet.reset(); buf.putByte((byte)SSH_MSG_GLOBAL_REQUEST); buf.putString(nomoresessions); buf.putByte((byte)0); write(packet); } private HostKey hostkey=null; public HostKey getHostKey(){ return hostkey; } public String getHost(){return host;} public String getUserName(){return username;} public int getPort(){return port;} public void setHostKeyAlias(String hostKeyAlias){ this.hostKeyAlias=hostKeyAlias; } public String getHostKeyAlias(){ return hostKeyAlias; } /** * Sets the interval to send a keep-alive message. If zero is * specified, any keep-alive message must not be sent. The default interval * is zero. * * @param interval the specified interval, in milliseconds. * @see #getServerAliveInterval() */ public void setServerAliveInterval(int interval) throws JSchException { setTimeout(interval); this.serverAliveInterval=interval; } /** * Returns setting for the interval to send a keep-alive message. * * @see #setServerAliveInterval(int) */ public int getServerAliveInterval(){ return this.serverAliveInterval; } /** * Sets the number of keep-alive messages which may be sent without * receiving any messages back from the server. If this threshold is * reached while keep-alive messages are being sent, the connection will * be disconnected. The default value is one. * * @param count the specified count * @see #getServerAliveCountMax() */ public void setServerAliveCountMax(int count){ this.serverAliveCountMax=count; } /** * Returns setting for the threshold to send keep-alive messages. * * @see #setServerAliveCountMax(int) */ public int getServerAliveCountMax(){ return this.serverAliveCountMax; } public void setDaemonThread(boolean enable){ this.daemon_thread=enable; } private String[] checkCiphers(String ciphers){ if(ciphers==null || ciphers.length()==0) return null; if(JSch.getLogger().isEnabled(Logger.INFO)){ JSch.getLogger().log(Logger.INFO, "CheckCiphers: "+ciphers); } String cipherc2s=getConfig("cipher.c2s"); String ciphers2c=getConfig("cipher.s2c"); Vector result=new Vector(); String[] _ciphers=Util.split(ciphers, ","); for(int i=0; i<_ciphers.length; i++){ String cipher=_ciphers[i]; if(ciphers2c.indexOf(cipher) == -1 && cipherc2s.indexOf(cipher) == -1) continue; if(!checkCipher(getConfig(cipher))){ result.addElement(cipher); } } if(result.size()==0) return null; String[] foo=new String[result.size()]; System.arraycopy(result.toArray(), 0, foo, 0, result.size()); if(JSch.getLogger().isEnabled(Logger.INFO)){ for(int i=0; inull. * * @param identityRepository * @see #getIdentityRepository() */ public void setIdentityRepository(IdentityRepository identityRepository){ this.identityRepository = identityRepository; } /** * Gets the identityRepository. * If this.identityRepository is null, * JSch#getIdentityRepository() will be invoked. * * @see JSch#getIdentityRepository() */ IdentityRepository getIdentityRepository(){ if(identityRepository == null) return jsch.getIdentityRepository(); return identityRepository; } /** * Sets the hostkeyRepository, which will be referred in checking host keys. * * @param hostkeyRepository * @see #getHostKeyRepository() */ public void setHostKeyRepository(HostKeyRepository hostkeyRepository){ this.hostkeyRepository = hostkeyRepository; } /** * Gets the hostkeyRepository. * If this.hostkeyRepository is null, * JSch#getHostKeyRepository() will be invoked. * * @see JSch#getHostKeyRepository() */ public HostKeyRepository getHostKeyRepository(){ if(hostkeyRepository == null) return jsch.getHostKeyRepository(); return hostkeyRepository; } /* // setProxyCommand("ssh -l user2 host2 -o 'ProxyCommand ssh user1@host1 nc host2 22' nc %h %p") public void setProxyCommand(String command){ setProxy(new ProxyCommand(command)); } class ProxyCommand implements Proxy { String command; Process p = null; InputStream in = null; OutputStream out = null; ProxyCommand(String command){ this.command = command; } public void connect(SocketFactory socket_factory, String host, int port, int timeout) throws Exception { String _command = command.replace("%h", host); _command = _command.replace("%p", new Integer(port).toString()); p = Runtime.getRuntime().exec(_command); in = p.getInputStream(); out = p.getOutputStream(); } public Socket getSocket() { return null; } public InputStream getInputStream() { return in; } public OutputStream getOutputStream() { return out; } public void close() { try{ if(p!=null){ p.getErrorStream().close(); p.getOutputStream().close(); p.getInputStream().close(); p.destroy(); p=null; } } catch(IOException e){ } } } */ private void applyConfig() throws JSchException { ConfigRepository configRepository = jsch.getConfigRepository(); if(configRepository == null){ return; } ConfigRepository.Config config = configRepository.getConfig(org_host); String value = null; value = config.getUser(); if(value != null) username = value; value = config.getHostname(); if(value != null) host = value; int port = config.getPort(); if(port != -1) this.port = port; checkConfig(config, "kex"); checkConfig(config, "server_host_key"); checkConfig(config, "cipher.c2s"); checkConfig(config, "cipher.s2c"); checkConfig(config, "mac.c2s"); checkConfig(config, "mac.s2c"); checkConfig(config, "compression.c2s"); checkConfig(config, "compression.s2c"); checkConfig(config, "compression_level"); checkConfig(config, "StrictHostKeyChecking"); checkConfig(config, "HashKnownHosts"); checkConfig(config, "PreferredAuthentications"); checkConfig(config, "MaxAuthTries"); checkConfig(config, "ClearAllForwardings"); value = config.getValue("HostKeyAlias"); if(value != null) this.setHostKeyAlias(value); value = config.getValue("UserKnownHostsFile"); if(value != null) { KnownHosts kh = new KnownHosts(jsch); kh.setKnownHosts(value); this.setHostKeyRepository(kh); } String[] values = config.getValues("IdentityFile"); if(values != null) { String[] global = configRepository.getConfig("").getValues("IdentityFile"); if(global != null){ for(int i = 0; i < global.length; i++){ jsch.addIdentity(global[i]); } } else { global = new String[0]; } if(values.length - global.length > 0){ IdentityRepository.Wrapper ir = new IdentityRepository.Wrapper(jsch.getIdentityRepository(), true); for(int i = 0; i < values.length; i++){ String ifile = values[i]; for(int j = 0; j < global.length; j++){ if(!ifile.equals(global[j])) continue; ifile = null; break; } if(ifile == null) continue; Identity identity = IdentityFile.newInstance(ifile, null, jsch); ir.add(identity); } this.setIdentityRepository(ir); } } value = config.getValue("ServerAliveInterval"); if(value != null) { try { this.setServerAliveInterval(Integer.parseInt(value)); } catch(NumberFormatException e){ } } value = config.getValue("ConnectTimeout"); if(value != null) { try { setTimeout(Integer.parseInt(value)); } catch(NumberFormatException e){ } } value = config.getValue("MaxAuthTries"); if(value != null) { setConfig("MaxAuthTries", value); } value = config.getValue("ClearAllForwardings"); if(value != null) { setConfig("ClearAllForwardings", value); } } private void applyConfigChannel(ChannelSession channel) throws JSchException { ConfigRepository configRepository = jsch.getConfigRepository(); if(configRepository == null){ return; } ConfigRepository.Config config = configRepository.getConfig(org_host); String value = null; value = config.getValue("ForwardAgent"); if(value != null){ channel.setAgentForwarding(value.equals("yes")); } value = config.getValue("RequestTTY"); if(value != null){ channel.setPty(value.equals("yes")); } } private void requestPortForwarding() throws JSchException { if(getConfig("ClearAllForwardings").equals("yes")) return; ConfigRepository configRepository = jsch.getConfigRepository(); if(configRepository == null){ return; } ConfigRepository.Config config = configRepository.getConfig(org_host); String[] values = config.getValues("LocalForward"); if(values != null){ for(int i = 0; i < values.length; i++) { setPortForwardingL(values[i]); } } values = config.getValues("RemoteForward"); if(values != null){ for(int i = 0; i < values.length; i++) { setPortForwardingR(values[i]); } } } private void checkConfig(ConfigRepository.Config config, String key){ String value = config.getValue(key); if(value != null) this.setConfig(key, value); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/ECDH.java0000664000000000000000000000333212500162637020212 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public interface ECDH { void init(int size) throws Exception; byte[] getSecret(byte[] r, byte[] s) throws Exception; byte[] getQ() throws Exception; boolean validate(byte[] r, byte[] s) throws Exception; } jsch-0.1.53/src/main/java/com/jcraft/jsch/KeyPairRSA.java0000644000000000000000000003106512500205221021406 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; import java.math.BigInteger; public class KeyPairRSA extends KeyPair{ private byte[] n_array; // modulus p multiply q private byte[] pub_array; // e private byte[] prv_array; // d e^-1 mod (p-1)(q-1) private byte[] p_array; // prime p private byte[] q_array; // prime q private byte[] ep_array; // prime exponent p dmp1 == prv mod (p-1) private byte[] eq_array; // prime exponent q dmq1 == prv mod (q-1) private byte[] c_array; // coefficient iqmp == modinv(q, p) == q^-1 mod p private int key_size=1024; public KeyPairRSA(JSch jsch){ this(jsch, null, null, null); } public KeyPairRSA(JSch jsch, byte[] n_array, byte[] pub_array, byte[] prv_array){ super(jsch); this.n_array = n_array; this.pub_array = pub_array; this.prv_array = prv_array; if(n_array!=null){ key_size = (new java.math.BigInteger(n_array)).bitLength(); } } void generate(int key_size) throws JSchException{ this.key_size=key_size; try{ Class c=Class.forName(jsch.getConfig("keypairgen.rsa")); KeyPairGenRSA keypairgen=(KeyPairGenRSA)(c.newInstance()); keypairgen.init(key_size); pub_array=keypairgen.getE(); prv_array=keypairgen.getD(); n_array=keypairgen.getN(); p_array=keypairgen.getP(); q_array=keypairgen.getQ(); ep_array=keypairgen.getEP(); eq_array=keypairgen.getEQ(); c_array=keypairgen.getC(); keypairgen=null; } catch(Exception e){ //System.err.println("KeyPairRSA: "+e); if(e instanceof Throwable) throw new JSchException(e.toString(), (Throwable)e); throw new JSchException(e.toString()); } } private static final byte[] begin=Util.str2byte("-----BEGIN RSA PRIVATE KEY-----"); private static final byte[] end=Util.str2byte("-----END RSA PRIVATE KEY-----"); byte[] getBegin(){ return begin; } byte[] getEnd(){ return end; } byte[] getPrivateKey(){ int content= 1+countLength(1) + 1 + // INTEGER 1+countLength(n_array.length) + n_array.length + // INTEGER N 1+countLength(pub_array.length) + pub_array.length + // INTEGER pub 1+countLength(prv_array.length) + prv_array.length+ // INTEGER prv 1+countLength(p_array.length) + p_array.length+ // INTEGER p 1+countLength(q_array.length) + q_array.length+ // INTEGER q 1+countLength(ep_array.length) + ep_array.length+ // INTEGER ep 1+countLength(eq_array.length) + eq_array.length+ // INTEGER eq 1+countLength(c_array.length) + c_array.length; // INTEGER c int total= 1+countLength(content)+content; // SEQUENCE byte[] plain=new byte[total]; int index=0; index=writeSEQUENCE(plain, index, content); index=writeINTEGER(plain, index, new byte[1]); // 0 index=writeINTEGER(plain, index, n_array); index=writeINTEGER(plain, index, pub_array); index=writeINTEGER(plain, index, prv_array); index=writeINTEGER(plain, index, p_array); index=writeINTEGER(plain, index, q_array); index=writeINTEGER(plain, index, ep_array); index=writeINTEGER(plain, index, eq_array); index=writeINTEGER(plain, index, c_array); return plain; } boolean parse(byte [] plain){ try{ int index=0; int length=0; if(vendor==VENDOR_PUTTY){ Buffer buf = new Buffer(plain); buf.skip(plain.length); try { byte[][] tmp = buf.getBytes(4, ""); prv_array = tmp[0]; p_array = tmp[1]; q_array = tmp[2]; c_array = tmp[3]; } catch(JSchException e){ return false; } getEPArray(); getEQArray(); return true; } if(vendor==VENDOR_FSECURE){ if(plain[index]!=0x30){ // FSecure Buffer buf=new Buffer(plain); pub_array=buf.getMPIntBits(); prv_array=buf.getMPIntBits(); n_array=buf.getMPIntBits(); byte[] u_array=buf.getMPIntBits(); p_array=buf.getMPIntBits(); q_array=buf.getMPIntBits(); if(n_array!=null){ key_size = (new java.math.BigInteger(n_array)).bitLength(); } getEPArray(); getEQArray(); getCArray(); return true; } return false; } /* Key must be in the following ASN.1 DER encoding, RSAPrivateKey ::= SEQUENCE { version Version, modulus INTEGER, -- n publicExponent INTEGER, -- e privateExponent INTEGER, -- d prime1 INTEGER, -- p prime2 INTEGER, -- q exponent1 INTEGER, -- d mod (p-1) exponent2 INTEGER, -- d mod (q-1) coefficient INTEGER, -- (inverse of q) mod p otherPrimeInfos OtherPrimeInfos OPTIONAL } */ index++; // SEQUENCE length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } if(plain[index]!=0x02)return false; index++; // INTEGER length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } index+=length; index++; length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } n_array=new byte[length]; System.arraycopy(plain, index, n_array, 0, length); index+=length; index++; length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } pub_array=new byte[length]; System.arraycopy(plain, index, pub_array, 0, length); index+=length; index++; length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } prv_array=new byte[length]; System.arraycopy(plain, index, prv_array, 0, length); index+=length; index++; length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } p_array=new byte[length]; System.arraycopy(plain, index, p_array, 0, length); index+=length; index++; length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } q_array=new byte[length]; System.arraycopy(plain, index, q_array, 0, length); index+=length; index++; length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } ep_array=new byte[length]; System.arraycopy(plain, index, ep_array, 0, length); index+=length; index++; length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } eq_array=new byte[length]; System.arraycopy(plain, index, eq_array, 0, length); index+=length; index++; length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } c_array=new byte[length]; System.arraycopy(plain, index, c_array, 0, length); index+=length; if(n_array!=null){ key_size = (new java.math.BigInteger(n_array)).bitLength(); } } catch(Exception e){ //System.err.println(e); return false; } return true; } public byte[] getPublicKeyBlob(){ byte[] foo=super.getPublicKeyBlob(); if(foo!=null) return foo; if(pub_array==null) return null; byte[][] tmp = new byte[3][]; tmp[0] = sshrsa; tmp[1] = pub_array; tmp[2] = n_array; return Buffer.fromBytes(tmp).buffer; } private static final byte[] sshrsa=Util.str2byte("ssh-rsa"); byte[] getKeyTypeName(){return sshrsa;} public int getKeyType(){return RSA;} public int getKeySize(){ return key_size; } public byte[] getSignature(byte[] data){ try{ Class c=Class.forName((String)jsch.getConfig("signature.rsa")); SignatureRSA rsa=(SignatureRSA)(c.newInstance()); rsa.init(); rsa.setPrvKey(prv_array, n_array); rsa.update(data); byte[] sig = rsa.sign(); byte[][] tmp = new byte[2][]; tmp[0] = sshrsa; tmp[1] = sig; return Buffer.fromBytes(tmp).buffer; } catch(Exception e){ } return null; } public Signature getVerifier(){ try{ Class c=Class.forName((String)jsch.getConfig("signature.rsa")); SignatureRSA rsa=(SignatureRSA)(c.newInstance()); rsa.init(); if(pub_array == null && n_array == null && getPublicKeyBlob()!=null){ Buffer buf = new Buffer(getPublicKeyBlob()); buf.getString(); pub_array = buf.getString(); n_array = buf.getString(); } rsa.setPubKey(pub_array, n_array); return rsa; } catch(Exception e){ } return null; } static KeyPair fromSSHAgent(JSch jsch, Buffer buf) throws JSchException { byte[][] tmp = buf.getBytes(8, "invalid key format"); byte[] n_array = tmp[1]; byte[] pub_array = tmp[2]; byte[] prv_array = tmp[3]; KeyPairRSA kpair = new KeyPairRSA(jsch, n_array, pub_array, prv_array); kpair.c_array = tmp[4]; // iqmp kpair.p_array = tmp[5]; kpair.q_array = tmp[6]; kpair.publicKeyComment = new String(tmp[7]); kpair.vendor=VENDOR_OPENSSH; return kpair; } public byte[] forSSHAgent() throws JSchException { if(isEncrypted()){ throw new JSchException("key is encrypted."); } Buffer buf = new Buffer(); buf.putString(sshrsa); buf.putString(n_array); buf.putString(pub_array); buf.putString(prv_array); buf.putString(getCArray()); buf.putString(p_array); buf.putString(q_array); buf.putString(Util.str2byte(publicKeyComment)); byte[] result = new byte[buf.getLength()]; buf.getByte(result, 0, result.length); return result; } private byte[] getEPArray(){ if(ep_array==null){ ep_array=(new BigInteger(prv_array)).mod(new BigInteger(p_array).subtract(BigInteger.ONE)).toByteArray(); } return ep_array; } private byte[] getEQArray(){ if(eq_array==null){ eq_array=(new BigInteger(prv_array)).mod(new BigInteger(q_array).subtract(BigInteger.ONE)).toByteArray(); } return eq_array; } private byte[] getCArray(){ if(c_array==null){ c_array=(new BigInteger(q_array)).modInverse(new BigInteger(p_array)).toByteArray(); } return c_array; } public void dispose(){ super.dispose(); Util.bzero(prv_array); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/Identity.java0000644000000000000000000000554012500205102021262 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public interface Identity{ /** * Decrypts this identity with the specified pass-phrase. * @param passphrase the pass-phrase for this identity. * @return true if the decryption is succeeded * or this identity is not cyphered. */ public boolean setPassphrase(byte[] passphrase) throws JSchException; /** * Returns the public-key blob. * @return the public-key blob */ public byte[] getPublicKeyBlob(); /** * Signs on data with this identity, and returns the result. * @param data data to be signed * @return the signature */ public byte[] getSignature(byte[] data); /** * @deprecated The decryption should be done automatically in #setPassphase(byte[] passphrase) * @see #setPassphrase(byte[] passphrase) */ public boolean decrypt(); /** * Returns the name of the key algorithm. * @return "ssh-rsa" or "ssh-dss" */ public String getAlgName(); /** * Returns the name of this identity. * It will be useful to identify this object in the {@link IdentityRepository}. */ public String getName(); /** * Returns true if this identity is cyphered. * @return true if this identity is cyphered. */ public boolean isEncrypted(); /** * Disposes internally allocated data, like byte array for the private key. */ public void clear(); } jsch-0.1.53/src/main/java/com/jcraft/jsch/KeyPairGenRSA.java0000644000000000000000000000334212500205207022041 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public interface KeyPairGenRSA{ void init(int key_size) throws Exception; byte[] getD(); byte[] getE(); byte[] getN(); byte[] getC(); byte[] getEP(); byte[] getEQ(); byte[] getP(); byte[] getQ(); } jsch-0.1.53/src/main/java/com/jcraft/jsch/KnownHosts.java0000644000000000000000000003777012533602433021636 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; import java.io.*; public class KnownHosts implements HostKeyRepository{ private static final String _known_hosts="known_hosts"; private JSch jsch=null; private String known_hosts=null; private java.util.Vector pool=null; private MAC hmacsha1=null; KnownHosts(JSch jsch){ super(); this.jsch=jsch; pool=new java.util.Vector(); } void setKnownHosts(String filename) throws JSchException{ try{ known_hosts = filename; FileInputStream fis=new FileInputStream(Util.checkTilde(filename)); setKnownHosts(fis); } catch(FileNotFoundException e){ throw new JSchException(e.toString(), (Throwable)e); } } void setKnownHosts(InputStream input) throws JSchException{ pool.removeAllElements(); StringBuffer sb=new StringBuffer(); byte i; int j; boolean error=false; try{ InputStream fis=input; String host; String key=null; int type; byte[] buf=new byte[1024]; int bufl=0; loop: while(true){ bufl=0; while(true){ j=fis.read(); if(j==-1){ if(bufl==0){ break loop; } else{ break; } } if(j==0x0d){ continue; } if(j==0x0a){ break; } if(buf.length<=bufl){ if(bufl>1024*10) break; // too long... byte[] newbuf=new byte[buf.length*2]; System.arraycopy(buf, 0, newbuf, 0, buf.length); buf=newbuf; } buf[bufl++]=(byte)j; } j=0; while(j=bufl){ addInvalidLine(Util.byte2str(buf, 0, bufl)); continue loop; } sb.setLength(0); while(j=bufl || host.length()==0){ addInvalidLine(Util.byte2str(buf, 0, bufl)); continue loop; } while(j=bufl || host.length()==0){ addInvalidLine(Util.byte2str(buf, 0, bufl)); continue loop; } while(j=bufl){ addInvalidLine(Util.byte2str(buf, 0, bufl)); continue loop; } while(j1 ){ return check(host.substring(1, host.indexOf("]:")), key); } return result; } public void add(HostKey hostkey, UserInfo userinfo){ int type=hostkey.type; String host=hostkey.getHost(); byte[] key=hostkey.key; HostKey hk=null; synchronized(pool){ for(int i=0; i1){ HostKey[] tmp = getHostKey(host.substring(1, host.indexOf("]:")), type); if(tmp.length > 0){ HostKey[] bar = new HostKey[foo.length + tmp.length]; System.arraycopy(foo, 0, bar, 0, foo.length); System.arraycopy(tmp, 0, bar, foo.length, tmp.length); foo = bar; } } return foo; } } public void remove(String host, String type){ remove(host, type, null); } public void remove(String host, String type, byte[] key){ boolean sync=false; synchronized(pool){ for(int i=0; i0){ String data=this.host.substring(HASH_MAGIC.length()); String _salt=data.substring(0, data.indexOf(HASH_DELIM)); String _hash=data.substring(data.indexOf(HASH_DELIM)+1); salt=Util.fromBase64(Util.str2byte(_salt), 0, _salt.length()); hash=Util.fromBase64(Util.str2byte(_hash), 0, _hash.length()); if(salt.length!=20 || // block size of hmac-sha1 hash.length!=20){ salt=null; hash=null; return; } hashed=true; } } boolean isMatched(String _host){ if(!hashed){ return super.isMatched(_host); } MAC macsha1=getHMACSHA1(); try{ synchronized(macsha1){ macsha1.init(salt); byte[] foo=Util.str2byte(_host); macsha1.update(foo, 0, foo.length); byte[] bar=new byte[macsha1.getBlockSize()]; macsha1.doFinal(bar, 0); return Util.array_equals(hash, bar); } } catch(Exception e){ System.out.println(e); } return false; } boolean isHashed(){ return hashed; } void hash(){ if(hashed) return; MAC macsha1=getHMACSHA1(); if(salt==null){ Random random=Session.random; synchronized(random){ salt=new byte[macsha1.getBlockSize()]; random.fill(salt, 0, salt.length); } } try{ synchronized(macsha1){ macsha1.init(salt); byte[] foo=Util.str2byte(host); macsha1.update(foo, 0, foo.length); hash=new byte[macsha1.getBlockSize()]; macsha1.doFinal(hash, 0); } } catch(Exception e){ } host=HASH_MAGIC+Util.byte2str(Util.toBase64(salt, 0, salt.length))+ HASH_DELIM+Util.byte2str(Util.toBase64(hash, 0, hash.length)); hashed=true; } } } jsch-0.1.53/src/main/java/com/jcraft/jsch/JSchAuthCancelException.java0000644000000000000000000000350612500205131024131 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; class JSchAuthCancelException extends JSchException{ //private static final long serialVersionUID=3204965907117900987L; String method; JSchAuthCancelException () { super(); } JSchAuthCancelException (String s) { super(s); this.method=s; } public String getMethod(){ return method; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/PortWatcher.java0000644000000000000000000001500712500205276021746 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; import java.net.*; import java.io.*; class PortWatcher implements Runnable{ private static java.util.Vector pool=new java.util.Vector(); private static InetAddress anyLocalAddress=null; static{ // 0.0.0.0 /* try{ anyLocalAddress=InetAddress.getByAddress(new byte[4]); } catch(UnknownHostException e){ } */ try{ anyLocalAddress=InetAddress.getByName("0.0.0.0"); } catch(UnknownHostException e){ } } Session session; int lport; int rport; String host; InetAddress boundaddress; Runnable thread; ServerSocket ss; int connectTimeout=0; static String[] getPortForwarding(Session session){ java.util.Vector foo=new java.util.Vector(); synchronized(pool){ for(int i=0; i0){ socket.setSoTimeout(timeout); } socket.setTcpNoDelay(true); out.write(Util.str2byte("CONNECT "+host+":"+port+" HTTP/1.0\r\n")); if(user!=null && passwd!=null){ byte[] code=Util.str2byte(user+":"+passwd); code=Util.toBase64(code, 0, code.length); out.write(Util.str2byte("Proxy-Authorization: Basic ")); out.write(code); out.write(Util.str2byte("\r\n")); } out.write(Util.str2byte("\r\n")); out.flush(); int foo=0; StringBuffer sb=new StringBuffer(); while(foo>=0){ foo=in.read(); if(foo!=13){sb.append((char)foo); continue;} foo=in.read(); if(foo!=10){continue;} break; } if(foo<0){ throw new IOException(); } String response=sb.toString(); String reason="Unknow reason"; int code=-1; try{ foo=response.indexOf(' '); int bar=response.indexOf(' ', foo+1); code=Integer.parseInt(response.substring(foo+1, bar)); reason=response.substring(bar+1); } catch(Exception e){ } if(code!=200){ throw new IOException("proxy error: "+reason); } /* while(foo>=0){ foo=in.read(); if(foo!=13) continue; foo=in.read(); if(foo!=10) continue; foo=in.read(); if(foo!=13) continue; foo=in.read(); if(foo!=10) continue; break; } */ int count=0; while(true){ count=0; while(foo>=0){ foo=in.read(); if(foo!=13){count++; continue;} foo=in.read(); if(foo!=10){continue;} break; } if(foo<0){ throw new IOException(); } if(count==0)break; } } catch(RuntimeException e){ throw e; } catch(Exception e){ try{ if(socket!=null)socket.close(); } catch(Exception eee){ } String message="ProxyHTTP: "+e.toString(); if(e instanceof Throwable) throw new JSchException(message, (Throwable)e); throw new JSchException(message); } } public InputStream getInputStream(){ return in; } public OutputStream getOutputStream(){ return out; } public Socket getSocket(){ return socket; } public void close(){ try{ if(in!=null)in.close(); if(out!=null)out.close(); if(socket!=null)socket.close(); } catch(Exception e){ } in=null; out=null; socket=null; } public static int getDefaultPort(){ return DEFAULTPORT; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/PBKDF.java0000644000000000000000000000315012500205262020321 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2013-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public interface PBKDF { byte[] getKey(byte[] pass, byte[] salt, int iteration, int size); } jsch-0.1.53/src/main/java/com/jcraft/jsch/ChannelAgentForwarding.java0000644000000000000000000001750712500204667024070 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2006-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; import java.net.*; import java.util.Vector; class ChannelAgentForwarding extends Channel{ static private final int LOCAL_WINDOW_SIZE_MAX=0x20000; static private final int LOCAL_MAXIMUM_PACKET_SIZE=0x4000; private final byte SSH_AGENTC_REQUEST_RSA_IDENTITIES = 1; private final byte SSH_AGENT_RSA_IDENTITIES_ANSWER = 2; private final byte SSH_AGENTC_RSA_CHALLENGE = 3; private final byte SSH_AGENT_RSA_RESPONSE = 4; private final byte SSH_AGENT_FAILURE = 5; private final byte SSH_AGENT_SUCCESS = 6; private final byte SSH_AGENTC_ADD_RSA_IDENTITY = 7; private final byte SSH_AGENTC_REMOVE_RSA_IDENTITY = 8; private final byte SSH_AGENTC_REMOVE_ALL_RSA_IDENTITIES = 9; private final byte SSH2_AGENTC_REQUEST_IDENTITIES=11; private final byte SSH2_AGENT_IDENTITIES_ANSWER=12; private final byte SSH2_AGENTC_SIGN_REQUEST=13; private final byte SSH2_AGENT_SIGN_RESPONSE=14; private final byte SSH2_AGENTC_ADD_IDENTITY=17; private final byte SSH2_AGENTC_REMOVE_IDENTITY=18; private final byte SSH2_AGENTC_REMOVE_ALL_IDENTITIES=19; private final byte SSH2_AGENT_FAILURE=30; boolean init=true; private Buffer rbuf=null; private Buffer wbuf=null; private Packet packet=null; private Buffer mbuf=null; ChannelAgentForwarding(){ super(); setLocalWindowSizeMax(LOCAL_WINDOW_SIZE_MAX); setLocalWindowSize(LOCAL_WINDOW_SIZE_MAX); setLocalPacketSize(LOCAL_MAXIMUM_PACKET_SIZE); type=Util.str2byte("auth-agent@openssh.com"); rbuf=new Buffer(); rbuf.reset(); //wbuf=new Buffer(rmpsize); //packet=new Packet(wbuf); mbuf=new Buffer(); connected=true; } public void run(){ try{ sendOpenConfirmation(); } catch(Exception e){ close=true; disconnect(); } } void write(byte[] foo, int s, int l) throws java.io.IOException { if(packet==null){ wbuf=new Buffer(rmpsize); packet=new Packet(wbuf); } rbuf.shift(); if(rbuf.buffer.lengthrbuf.getLength()){ rbuf.s-=4; return; } int typ=rbuf.getByte(); Session _session=null; try{ _session=getSession(); } catch(JSchException e){ throw new java.io.IOException(e.toString()); } IdentityRepository irepo = _session.getIdentityRepository(); UserInfo userinfo=_session.getUserInfo(); mbuf.reset(); if(typ==SSH2_AGENTC_REQUEST_IDENTITIES){ mbuf.putByte(SSH2_AGENT_IDENTITIES_ANSWER); Vector identities = irepo.getIdentities(); synchronized(identities){ int count=0; for(int i=0; iname and value are needed to be passed * to the remote in your favorite encoding, * use {@link #setEnv(byte[], byte[])}. * Refer to RFC4254 6.4 Environment Variable Passing. * * @param name A name for environment variable. * @param value A value for environment variable. */ public void setEnv(String name, String value){ setEnv(Util.str2byte(name), Util.str2byte(value)); } /** * Set the environment variable. * Refer to RFC4254 6.4 Environment Variable Passing. * * @param name A name of environment variable. * @param value A value of environment variable. * @see #setEnv(String, String) */ public void setEnv(byte[] name, byte[] value){ synchronized(this){ getEnv().put(name, value); } } private Hashtable getEnv(){ if(env==null) env=new Hashtable(); return env; } /** * Allocate a Pseudo-Terminal. * Refer to RFC4254 6.2. Requesting a Pseudo-Terminal. * * @param enable */ public void setPty(boolean enable){ pty=enable; } /** * Set the terminal mode. * * @param terminal_mode */ public void setTerminalMode(byte[] terminal_mode){ this.terminal_mode=terminal_mode; } /** * Change the window dimension interactively. * Refer to RFC4254 6.7. Window Dimension Change Message. * * @param col terminal width, columns * @param row terminal height, rows * @param wp terminal width, pixels * @param hp terminal height, pixels */ public void setPtySize(int col, int row, int wp, int hp){ setPtyType(this.ttype, col, row, wp, hp); if(!pty || !isConnected()){ return; } try{ RequestWindowChange request=new RequestWindowChange(); request.setSize(col, row, wp, hp); request.request(getSession(), this); } catch(Exception e){ //System.err.println("ChannelSessio.setPtySize: "+e); } } /** * Set the terminal type. * This method is not effective after Channel#connect(). * * @param ttype terminal type(for example, "vt100") * @see #setPtyType(String, int, int, int, int) */ public void setPtyType(String ttype){ setPtyType(ttype, 80, 24, 640, 480); } /** * Set the terminal type. * This method is not effective after Channel#connect(). * * @param ttype terminal type(for example, "vt100") * @param col terminal width, columns * @param row terminal height, rows * @param wp terminal width, pixels * @param hp terminal height, pixels */ public void setPtyType(String ttype, int col, int row, int wp, int hp){ this.ttype=ttype; this.tcol=col; this.trow=row; this.twp=wp; this.thp=hp; } protected void sendRequests() throws Exception{ Session _session=getSession(); Request request; if(agent_forwarding){ request=new RequestAgentForwarding(); request.request(_session, this); } if(xforwading){ request=new RequestX11(); request.request(_session, this); } if(pty){ request=new RequestPtyReq(); ((RequestPtyReq)request).setTType(ttype); ((RequestPtyReq)request).setTSize(tcol, trow, twp, thp); if(terminal_mode!=null){ ((RequestPtyReq)request).setTerminalMode(terminal_mode); } request.request(_session, this); } if(env!=null){ for(Enumeration _env=env.keys(); _env.hasMoreElements();){ Object name=_env.nextElement(); Object value=env.get(name); request=new RequestEnv(); ((RequestEnv)request).setEnv(toByteArray(name), toByteArray(value)); request.request(_session, this); } } } private byte[] toByteArray(Object o){ if(o instanceof String){ return Util.str2byte((String)o); } return (byte[])o; } public void run(){ //System.err.println(this+":run >"); Buffer buf=new Buffer(rmpsize); Packet packet=new Packet(buf); int i=-1; try{ while(isConnected() && thread!=null && io!=null && io.in!=null){ i=io.in.read(buf.buffer, 14, buf.buffer.length-14 -Session.buffer_margin ); if(i==0)continue; if(i==-1){ eof(); break; } if(close)break; //System.out.println("write: "+i); packet.reset(); buf.putByte((byte)Session.SSH_MSG_CHANNEL_DATA); buf.putInt(recipient); buf.putInt(i); buf.skip(i); getSession().write(packet, this, i); } } catch(Exception e){ //System.err.println("# ChannelExec.run"); //e.printStackTrace(); } Thread _thread=thread; if(_thread!=null){ synchronized(_thread){ _thread.notifyAll(); } } thread=null; //System.err.println(this+":run <"); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/JSchPartialAuthException.java0000644000000000000000000000353312500205143024343 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; class JSchPartialAuthException extends JSchException{ //private static final long serialVersionUID=-378849862323360367L; String methods; public JSchPartialAuthException () { super(); } public JSchPartialAuthException (String s) { super(s); this.methods=s; } public String getMethods(){ return methods; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/JSch.java0000644000000000000000000005112212534054322020332 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; import java.io.InputStream; import java.util.Vector; public class JSch{ /** * The version number. */ public static final String VERSION = "0.1.53"; static java.util.Hashtable config=new java.util.Hashtable(); static{ config.put("kex", "ecdh-sha2-nistp256,ecdh-sha2-nistp384,ecdh-sha2-nistp521,diffie-hellman-group14-sha1,diffie-hellman-group-exchange-sha256,diffie-hellman-group-exchange-sha1,diffie-hellman-group1-sha1"); config.put("server_host_key", "ssh-rsa,ssh-dss,ecdsa-sha2-nistp256,ecdsa-sha2-nistp384,ecdsa-sha2-nistp521"); config.put("cipher.s2c", "aes128-ctr,aes128-cbc,3des-ctr,3des-cbc,blowfish-cbc,aes192-ctr,aes192-cbc,aes256-ctr,aes256-cbc"); config.put("cipher.c2s", "aes128-ctr,aes128-cbc,3des-ctr,3des-cbc,blowfish-cbc,aes192-ctr,aes192-cbc,aes256-ctr,aes256-cbc"); config.put("mac.s2c", "hmac-md5,hmac-sha1,hmac-sha2-256,hmac-sha1-96,hmac-md5-96"); config.put("mac.c2s", "hmac-md5,hmac-sha1,hmac-sha2-256,hmac-sha1-96,hmac-md5-96"); config.put("compression.s2c", "none"); config.put("compression.c2s", "none"); config.put("lang.s2c", ""); config.put("lang.c2s", ""); config.put("compression_level", "6"); config.put("diffie-hellman-group-exchange-sha1", "com.jcraft.jsch.DHGEX"); config.put("diffie-hellman-group1-sha1", "com.jcraft.jsch.DHG1"); config.put("diffie-hellman-group14-sha1", "com.jcraft.jsch.DHG14"); // available since JDK8. config.put("diffie-hellman-group-exchange-sha256", "com.jcraft.jsch.DHGEX256"); // available since JDK1.4.2. // On JDK8, 2048bits will be used. config.put("ecdsa-sha2-nistp256", "com.jcraft.jsch.jce.SignatureECDSA"); config.put("ecdsa-sha2-nistp384", "com.jcraft.jsch.jce.SignatureECDSA"); config.put("ecdsa-sha2-nistp521", "com.jcraft.jsch.jce.SignatureECDSA"); config.put("ecdh-sha2-nistp256", "com.jcraft.jsch.DHEC256"); config.put("ecdh-sha2-nistp384", "com.jcraft.jsch.DHEC384"); config.put("ecdh-sha2-nistp521", "com.jcraft.jsch.DHEC521"); config.put("ecdh-sha2-nistp", "com.jcraft.jsch.jce.ECDHN"); config.put("dh", "com.jcraft.jsch.jce.DH"); config.put("3des-cbc", "com.jcraft.jsch.jce.TripleDESCBC"); config.put("blowfish-cbc", "com.jcraft.jsch.jce.BlowfishCBC"); config.put("hmac-sha1", "com.jcraft.jsch.jce.HMACSHA1"); config.put("hmac-sha1-96", "com.jcraft.jsch.jce.HMACSHA196"); config.put("hmac-sha2-256", "com.jcraft.jsch.jce.HMACSHA256"); // The "hmac-sha2-512" will require the key-length 2048 for DH, // but Sun's JCE has not allowed to use such a long key. //config.put("hmac-sha2-512", "com.jcraft.jsch.jce.HMACSHA512"); config.put("hmac-md5", "com.jcraft.jsch.jce.HMACMD5"); config.put("hmac-md5-96", "com.jcraft.jsch.jce.HMACMD596"); config.put("sha-1", "com.jcraft.jsch.jce.SHA1"); config.put("sha-256", "com.jcraft.jsch.jce.SHA256"); config.put("sha-384", "com.jcraft.jsch.jce.SHA384"); config.put("sha-512", "com.jcraft.jsch.jce.SHA512"); config.put("md5", "com.jcraft.jsch.jce.MD5"); config.put("signature.dss", "com.jcraft.jsch.jce.SignatureDSA"); config.put("signature.rsa", "com.jcraft.jsch.jce.SignatureRSA"); config.put("signature.ecdsa", "com.jcraft.jsch.jce.SignatureECDSA"); config.put("keypairgen.dsa", "com.jcraft.jsch.jce.KeyPairGenDSA"); config.put("keypairgen.rsa", "com.jcraft.jsch.jce.KeyPairGenRSA"); config.put("keypairgen.ecdsa", "com.jcraft.jsch.jce.KeyPairGenECDSA"); config.put("random", "com.jcraft.jsch.jce.Random"); config.put("none", "com.jcraft.jsch.CipherNone"); config.put("aes128-cbc", "com.jcraft.jsch.jce.AES128CBC"); config.put("aes192-cbc", "com.jcraft.jsch.jce.AES192CBC"); config.put("aes256-cbc", "com.jcraft.jsch.jce.AES256CBC"); config.put("aes128-ctr", "com.jcraft.jsch.jce.AES128CTR"); config.put("aes192-ctr", "com.jcraft.jsch.jce.AES192CTR"); config.put("aes256-ctr", "com.jcraft.jsch.jce.AES256CTR"); config.put("3des-ctr", "com.jcraft.jsch.jce.TripleDESCTR"); config.put("arcfour", "com.jcraft.jsch.jce.ARCFOUR"); config.put("arcfour128", "com.jcraft.jsch.jce.ARCFOUR128"); config.put("arcfour256", "com.jcraft.jsch.jce.ARCFOUR256"); config.put("userauth.none", "com.jcraft.jsch.UserAuthNone"); config.put("userauth.password", "com.jcraft.jsch.UserAuthPassword"); config.put("userauth.keyboard-interactive", "com.jcraft.jsch.UserAuthKeyboardInteractive"); config.put("userauth.publickey", "com.jcraft.jsch.UserAuthPublicKey"); config.put("userauth.gssapi-with-mic", "com.jcraft.jsch.UserAuthGSSAPIWithMIC"); config.put("gssapi-with-mic.krb5", "com.jcraft.jsch.jgss.GSSContextKrb5"); config.put("zlib", "com.jcraft.jsch.jcraft.Compression"); config.put("zlib@openssh.com", "com.jcraft.jsch.jcraft.Compression"); config.put("pbkdf", "com.jcraft.jsch.jce.PBKDF"); config.put("StrictHostKeyChecking", "ask"); config.put("HashKnownHosts", "no"); config.put("PreferredAuthentications", "gssapi-with-mic,publickey,keyboard-interactive,password"); config.put("CheckCiphers", "aes256-ctr,aes192-ctr,aes128-ctr,aes256-cbc,aes192-cbc,aes128-cbc,3des-ctr,arcfour,arcfour128,arcfour256"); config.put("CheckKexes", "diffie-hellman-group14-sha1,ecdh-sha2-nistp256,ecdh-sha2-nistp384,ecdh-sha2-nistp521"); config.put("CheckSignatures", "ecdsa-sha2-nistp256,ecdsa-sha2-nistp384,ecdsa-sha2-nistp521"); config.put("MaxAuthTries", "6"); config.put("ClearAllForwardings", "no"); } private java.util.Vector sessionPool = new java.util.Vector(); private IdentityRepository defaultIdentityRepository = new LocalIdentityRepository(this); private IdentityRepository identityRepository = defaultIdentityRepository; private ConfigRepository configRepository = null; /** * Sets the identityRepository, which will be referred * in the public key authentication. * * @param identityRepository if null is given, * the default repository, which usually refers to ~/.ssh/, will be used. * * @see #getIdentityRepository() */ public synchronized void setIdentityRepository(IdentityRepository identityRepository){ if(identityRepository == null){ this.identityRepository = defaultIdentityRepository; } else{ this.identityRepository = identityRepository; } } public synchronized IdentityRepository getIdentityRepository(){ return this.identityRepository; } public ConfigRepository getConfigRepository() { return this.configRepository; } public void setConfigRepository(ConfigRepository configRepository) { this.configRepository = configRepository; } private HostKeyRepository known_hosts=null; private static final Logger DEVNULL=new Logger(){ public boolean isEnabled(int level){return false;} public void log(int level, String message){} }; static Logger logger=DEVNULL; public JSch(){ /* // The JCE of Sun's Java5 on Mac OS X has the resource leak bug // in calculating HMAC, so we need to use our own implementations. try{ String osname=(String)(System.getProperties().get("os.name")); if(osname!=null && osname.equals("Mac OS X")){ config.put("hmac-sha1", "com.jcraft.jsch.jcraft.HMACSHA1"); config.put("hmac-md5", "com.jcraft.jsch.jcraft.HMACMD5"); config.put("hmac-md5-96", "com.jcraft.jsch.jcraft.HMACMD596"); config.put("hmac-sha1-96", "com.jcraft.jsch.jcraft.HMACSHA196"); } } catch(Exception e){ } */ } /** * Instantiates the Session object with * host. The user name and port number will be retrieved from * ConfigRepository. If user name is not given, * the system property "user.name" will be referred. * * @param host hostname * * @throws JSchException * if username or host are invalid. * * @return the instance of Session class. * * @see #getSession(String username, String host, int port) * @see com.jcraft.jsch.Session * @see com.jcraft.jsch.ConfigRepository */ public Session getSession(String host) throws JSchException { return getSession(null, host, 22); } /** * Instantiates the Session object with * username and host. * The TCP port 22 will be used in making the connection. * Note that the TCP connection must not be established * until Session#connect(). * * @param username user name * @param host hostname * * @throws JSchException * if username or host are invalid. * * @return the instance of Session class. * * @see #getSession(String username, String host, int port) * @see com.jcraft.jsch.Session */ public Session getSession(String username, String host) throws JSchException { return getSession(username, host, 22); } /** * Instantiates the Session object with given * username, host and port. * Note that the TCP connection must not be established * until Session#connect(). * * @param username user name * @param host hostname * @param port port number * * @throws JSchException * if username or host are invalid. * * @return the instance of Session class. * * @see #getSession(String username, String host, int port) * @see com.jcraft.jsch.Session */ public Session getSession(String username, String host, int port) throws JSchException { if(host==null){ throw new JSchException("host must not be null."); } Session s = new Session(this, username, host, port); return s; } protected void addSession(Session session){ synchronized(sessionPool){ sessionPool.addElement(session); } } protected boolean removeSession(Session session){ synchronized(sessionPool){ return sessionPool.remove(session); } } /** * Sets the hostkey repository. * * @param hkrepo * * @see com.jcraft.jsch.HostKeyRepository * @see com.jcraft.jsch.KnownHosts */ public void setHostKeyRepository(HostKeyRepository hkrepo){ known_hosts=hkrepo; } /** * Sets the instance of KnownHosts, which refers * to filename. * * @param filename filename of known_hosts file. * * @throws JSchException * if the given filename is invalid. * * @see com.jcraft.jsch.KnownHosts */ public void setKnownHosts(String filename) throws JSchException{ if(known_hosts==null) known_hosts=new KnownHosts(this); if(known_hosts instanceof KnownHosts){ synchronized(known_hosts){ ((KnownHosts)known_hosts).setKnownHosts(filename); } } } /** * Sets the instance of KnownHosts generated with * stream. * * @param stream the instance of InputStream from known_hosts file. * * @throws JSchException * if an I/O error occurs. * * @see com.jcraft.jsch.KnownHosts */ public void setKnownHosts(InputStream stream) throws JSchException{ if(known_hosts==null) known_hosts=new KnownHosts(this); if(known_hosts instanceof KnownHosts){ synchronized(known_hosts){ ((KnownHosts)known_hosts).setKnownHosts(stream); } } } /** * Returns the current hostkey repository. * By the default, this method will the instance of KnownHosts. * * @return current hostkey repository. * * @see com.jcraft.jsch.HostKeyRepository * @see com.jcraft.jsch.KnownHosts */ public HostKeyRepository getHostKeyRepository(){ if(known_hosts==null) known_hosts=new KnownHosts(this); return known_hosts; } /** * Sets the private key, which will be referred in * the public key authentication. * * @param prvkey filename of the private key. * * @throws JSchException if prvkey is invalid. * * @see #addIdentity(String prvkey, String passphrase) */ public void addIdentity(String prvkey) throws JSchException{ addIdentity(prvkey, (byte[])null); } /** * Sets the private key, which will be referred in * the public key authentication. * Before registering it into identityRepository, * it will be deciphered with passphrase. * * @param prvkey filename of the private key. * @param passphrase passphrase for prvkey. * * @throws JSchException if passphrase is not right. * * @see #addIdentity(String prvkey, byte[] passphrase) */ public void addIdentity(String prvkey, String passphrase) throws JSchException{ byte[] _passphrase=null; if(passphrase!=null){ _passphrase=Util.str2byte(passphrase); } addIdentity(prvkey, _passphrase); if(_passphrase!=null) Util.bzero(_passphrase); } /** * Sets the private key, which will be referred in * the public key authentication. * Before registering it into identityRepository, * it will be deciphered with passphrase. * * @param prvkey filename of the private key. * @param passphrase passphrase for prvkey. * * @throws JSchException if passphrase is not right. * * @see #addIdentity(String prvkey, String pubkey, byte[] passphrase) */ public void addIdentity(String prvkey, byte[] passphrase) throws JSchException{ Identity identity=IdentityFile.newInstance(prvkey, null, this); addIdentity(identity, passphrase); } /** * Sets the private key, which will be referred in * the public key authentication. * Before registering it into identityRepository, * it will be deciphered with passphrase. * * @param prvkey filename of the private key. * @param pubkey filename of the public key. * @param passphrase passphrase for prvkey. * * @throws JSchException if passphrase is not right. */ public void addIdentity(String prvkey, String pubkey, byte[] passphrase) throws JSchException{ Identity identity=IdentityFile.newInstance(prvkey, pubkey, this); addIdentity(identity, passphrase); } /** * Sets the private key, which will be referred in * the public key authentication. * Before registering it into identityRepository, * it will be deciphered with passphrase. * * @param name name of the identity to be used to retrieve it in the identityRepository. * @param prvkey private key in byte array. * @param pubkey public key in byte array. * @param passphrase passphrase for prvkey. * */ public void addIdentity(String name, byte[]prvkey, byte[]pubkey, byte[] passphrase) throws JSchException{ Identity identity=IdentityFile.newInstance(name, prvkey, pubkey, this); addIdentity(identity, passphrase); } /** * Sets the private key, which will be referred in * the public key authentication. * Before registering it into identityRepository, * it will be deciphered with passphrase. * * @param identity private key. * @param passphrase passphrase for identity. * * @throws JSchException if passphrase is not right. */ public void addIdentity(Identity identity, byte[] passphrase) throws JSchException{ if(passphrase!=null){ try{ byte[] goo=new byte[passphrase.length]; System.arraycopy(passphrase, 0, goo, 0, passphrase.length); passphrase=goo; identity.setPassphrase(passphrase); } finally{ Util.bzero(passphrase); } } if(identityRepository instanceof LocalIdentityRepository){ ((LocalIdentityRepository)identityRepository).add(identity); } else if(identity instanceof IdentityFile && !identity.isEncrypted()) { identityRepository.add(((IdentityFile)identity).getKeyPair().forSSHAgent()); } else { synchronized(this){ if(!(identityRepository instanceof IdentityRepository.Wrapper)){ setIdentityRepository(new IdentityRepository.Wrapper(identityRepository)); } } ((IdentityRepository.Wrapper)identityRepository).add(identity); } } /** * @deprecated use #removeIdentity(Identity identity) */ public void removeIdentity(String name) throws JSchException{ Vector identities = identityRepository.getIdentities(); for(int i=0; iidentity is invalid. */ public void removeIdentity(Identity identity) throws JSchException{ identityRepository.remove(identity.getPublicKeyBlob()); } /** * Lists names of identities included in the identityRepository. * * @return names of identities * * @throws JSchException if identityReposory has problems. */ public Vector getIdentityNames() throws JSchException{ Vector foo=new Vector(); Vector identities = identityRepository.getIdentities(); for(int i=0; i0){ for(int i = 0; i < contents.length; i++){ values.addElement(contents[i].getContent()); } } byte[] _data = privateKey.getContent(); KeyPair _kpair = null; if(Util.array_equals(privateKeyAlgorithmID, rsaEncryption)){ _kpair = new KeyPairRSA(jsch); _kpair.copy(this); if(_kpair.parse(_data)){ kpair = _kpair; } } else if(Util.array_equals(privateKeyAlgorithmID, dsaEncryption)){ asn1 = new ASN1(_data); if(values.size() == 0) { // embedded DSA parameters format /* SEQUENCE SEQUENCE INTEGER // P_array INTEGER // Q_array INTEGER // G_array INTEGER // prv_array */ contents = asn1.getContents(); byte[] bar = contents[1].getContent(); contents = contents[0].getContents(); for(int i = 0; i < contents.length; i++){ values.addElement(contents[i].getContent()); } values.addElement(bar); } else { /* INTEGER // prv_array */ values.addElement(asn1.getContent()); } byte[] P_array = (byte[])values.elementAt(0); byte[] Q_array = (byte[])values.elementAt(1); byte[] G_array = (byte[])values.elementAt(2); byte[] prv_array = (byte[])values.elementAt(3); // Y = g^X mode p byte[] pub_array = (new BigInteger(G_array)). modPow(new BigInteger(prv_array), new BigInteger(P_array)). toByteArray(); KeyPairDSA _key = new KeyPairDSA(jsch, P_array, Q_array, G_array, pub_array, prv_array); plain = _key.getPrivateKey(); _kpair = new KeyPairDSA(jsch); _kpair.copy(this); if(_kpair.parse(plain)){ kpair = _kpair; } } } catch(ASN1Exception e){ return false; } catch(Exception e){ //System.err.println(e); return false; } return kpair != null; } public byte[] getPublicKeyBlob(){ return kpair.getPublicKeyBlob(); } byte[] getKeyTypeName(){ return kpair.getKeyTypeName();} public int getKeyType(){return kpair.getKeyType();} public int getKeySize(){ return kpair.getKeySize(); } public byte[] getSignature(byte[] data){ return kpair.getSignature(data); } public Signature getVerifier(){ return kpair.getVerifier(); } public byte[] forSSHAgent() throws JSchException { return kpair.forSSHAgent(); } public boolean decrypt(byte[] _passphrase){ if(!isEncrypted()){ return true; } if(_passphrase==null){ return !isEncrypted(); } /* SEQUENCE SEQUENCE OBJECT :PBES2 SEQUENCE SEQUENCE OBJECT :PBKDF2 SEQUENCE OCTET STRING [HEX DUMP]:E4E24ADC9C00BD4D INTEGER :0800 SEQUENCE OBJECT :aes-128-cbc OCTET STRING [HEX DUMP]:5B66E6B3BF03944C92317BC370CC3AD0 OCTET STRING [HEX DUMP]: or SEQUENCE SEQUENCE OBJECT :pbeWithMD5AndDES-CBC SEQUENCE OCTET STRING [HEX DUMP]:DBF75ECB69E3C0FC INTEGER :0800 OCTET STRING [HEX DUMP] */ try{ ASN1[] contents = null; ASN1 asn1 = new ASN1(data); contents = asn1.getContents(); byte[] _data = contents[1].getContent(); ASN1 pbes = contents[0]; contents = pbes.getContents(); byte[] pbesid = contents[0].getContent(); ASN1 pbesparam = contents[1]; byte[] salt = null; int iterations = 0; byte[] iv = null; byte[] encryptfuncid = null; if(Util.array_equals(pbesid, pbes2)){ contents = pbesparam.getContents(); ASN1 pbkdf = contents[0]; ASN1 encryptfunc = contents[1]; contents = pbkdf.getContents(); byte[] pbkdfid = contents[0].getContent(); ASN1 pbkdffunc = contents[1]; contents = pbkdffunc.getContents(); salt = contents[0].getContent(); iterations = Integer.parseInt((new BigInteger(contents[1].getContent())).toString()); contents = encryptfunc.getContents(); encryptfuncid = contents[0].getContent(); iv = contents[1].getContent(); } else if(Util.array_equals(pbesid, pbeWithMD5AndDESCBC)){ // not supported return false; } else { return false; } Cipher cipher=getCipher(encryptfuncid); if(cipher==null) return false; byte[] key=null; try{ Class c=Class.forName((String)jsch.getConfig("pbkdf")); PBKDF tmp=(PBKDF)(c.newInstance()); key = tmp.getKey(_passphrase, salt, iterations, cipher.getBlockSize()); } catch(Exception ee){ } if(key==null){ return false; } cipher.init(Cipher.DECRYPT_MODE, key, iv); Util.bzero(key); byte[] plain=new byte[_data.length]; cipher.update(_data, 0, _data.length, plain, 0); if(parse(plain)){ encrypted=false; return true; } } catch(ASN1Exception e){ // System.err.println(e); } catch(Exception e){ // System.err.println(e); } return false; } Cipher getCipher(byte[] id){ Cipher cipher=null; String name = null; try{ if(Util.array_equals(id, aes128cbc)){ name="aes128-cbc"; } else if(Util.array_equals(id, aes192cbc)){ name="aes192-cbc"; } else if(Util.array_equals(id, aes256cbc)){ name="aes256-cbc"; } Class c=Class.forName((String)jsch.getConfig(name)); cipher=(Cipher)(c.newInstance()); } catch(Exception e){ if(JSch.getLogger().isEnabled(Logger.FATAL)){ String message=""; if(name==null){ message="unknown oid: "+Util.toHex(id); } else { message="function "+name+" is not supported"; } JSch.getLogger().log(Logger.FATAL, "PKCS8: "+message); } } return cipher; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/DH.java0000644000000000000000000000355012500204774020001 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public interface DH{ void init() throws Exception; void setP(byte[] p); void setG(byte[] g); byte[] getE() throws Exception; void setF(byte[] f); byte[] getK() throws Exception; // checkRange() will check if e and f are in [1,p-1] // as defined at https://tools.ietf.org/html/rfc4253#section-8 void checkRange() throws Exception; } jsch-0.1.53/src/main/java/com/jcraft/jsch/CipherNone.java0000644000000000000000000000364412500204754021542 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public class CipherNone implements Cipher{ private static final int ivsize=8; private static final int bsize=16; public int getIVSize(){return ivsize;} public int getBlockSize(){return bsize;} public void init(int mode, byte[] key, byte[] iv) throws Exception{ } public void update(byte[] foo, int s1, int len, byte[] bar, int s2) throws Exception{ } public boolean isCBC(){return false; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/RequestEnv.java0000644000000000000000000000420612500205351021576 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; class RequestEnv extends Request{ byte[] name=new byte[0]; byte[] value=new byte[0]; void setEnv(byte[] name, byte[] value){ this.name=name; this.value=value; } public void request(Session session, Channel channel) throws Exception{ super.request(session, channel); Buffer buf=new Buffer(); Packet packet=new Packet(buf); packet.reset(); buf.putByte((byte) Session.SSH_MSG_CHANNEL_REQUEST); buf.putInt(channel.getRecipient()); buf.putString(Util.str2byte("env")); buf.putByte((byte)(waitForReply() ? 1 : 0)); buf.putString(name); buf.putString(value); write(packet); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/KeyPairECDSA.java0000664000000000000000000002634412477532467021642 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public class KeyPairECDSA extends KeyPair{ private static byte[][] oids = { {(byte)0x06, (byte)0x08, (byte)0x2a, (byte)0x86, (byte)0x48, // 256 (byte)0xce, (byte)0x3d, (byte)0x03, (byte)0x01, (byte)0x07}, {(byte)0x06, (byte)0x05, (byte)0x2b, (byte)0x81, (byte)0x04, // 384 (byte)0x00, (byte)0x22}, {(byte)0x06, (byte)0x05, (byte)0x2b, (byte)0x81, (byte)0x04, //521 (byte)0x00, (byte)0x23}, }; private static String[] names = { "nistp256", "nistp384", "nistp521" }; private byte[] name=Util.str2byte(names[0]); private byte[] r_array; private byte[] s_array; private byte[] prv_array; private int key_size=256; public KeyPairECDSA(JSch jsch){ this(jsch, null, null, null, null); } public KeyPairECDSA(JSch jsch, byte[] name, byte[] r_array, byte[] s_array, byte[] prv_array){ super(jsch); if(name!=null) this.name = name; this.r_array = r_array; this.s_array = s_array; this.prv_array = prv_array; if(prv_array!=null) key_size = prv_array.length>=64 ? 521 : (prv_array.length>=48 ? 384 : 256); } void generate(int key_size) throws JSchException{ this.key_size=key_size; try{ Class c=Class.forName(jsch.getConfig("keypairgen.ecdsa")); KeyPairGenECDSA keypairgen=(KeyPairGenECDSA)(c.newInstance()); keypairgen.init(key_size); prv_array=keypairgen.getD(); r_array=keypairgen.getR(); s_array=keypairgen.getS(); name=Util.str2byte(names[prv_array.length>=64 ? 2 : (prv_array.length>=48 ? 1 : 0)]); keypairgen=null; } catch(Exception e){ if(e instanceof Throwable) throw new JSchException(e.toString(), (Throwable)e); throw new JSchException(e.toString()); } } private static final byte[] begin = Util.str2byte("-----BEGIN EC PRIVATE KEY-----"); private static final byte[] end = Util.str2byte("-----END EC PRIVATE KEY-----"); byte[] getBegin(){ return begin; } byte[] getEnd(){ return end; } byte[] getPrivateKey(){ byte[] tmp = new byte[1]; tmp[0]=1; byte[] oid = oids[ (r_array.length>=64) ? 2 : ((r_array.length>=48) ? 1 : 0) ]; byte[] point = toPoint(r_array, s_array); int bar = ((point.length+1)&0x80)==0 ? 3 : 4; byte[] foo = new byte[point.length+bar]; System.arraycopy(point, 0, foo, bar, point.length); foo[0]=0x03; // BITSTRING if(bar==3){ foo[1]=(byte)(point.length+1); } else { foo[1]=(byte)0x81; foo[2]=(byte)(point.length+1); } point = foo; int content= 1+countLength(tmp.length) + tmp.length + 1+countLength(prv_array.length) + prv_array.length + 1+countLength(oid.length) + oid.length + 1+countLength(point.length) + point.length; int total= 1+countLength(content)+content; // SEQUENCE byte[] plain=new byte[total]; int index=0; index=writeSEQUENCE(plain, index, content); index=writeINTEGER(plain, index, tmp); index=writeOCTETSTRING(plain, index, prv_array); index=writeDATA(plain, (byte)0xa0, index, oid); index=writeDATA(plain, (byte)0xa1, index, point); return plain; } boolean parse(byte[] plain){ try{ if(vendor==VENDOR_FSECURE){ /* if(plain[0]!=0x30){ // FSecure return true; } return false; */ return false; } else if(vendor==VENDOR_PUTTY){ /* Buffer buf=new Buffer(plain); buf.skip(plain.length); try { byte[][] tmp = buf.getBytes(1, ""); prv_array = tmp[0]; } catch(JSchException e){ return false; } return true; */ return false; } int index=0; int length=0; if(plain[index]!=0x30)return false; index++; // SEQUENCE length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } if(plain[index]!=0x02)return false; index++; // INTEGER length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } index+=length; index++; // 0x04 length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } prv_array=new byte[length]; System.arraycopy(plain, index, prv_array, 0, length); index+=length; index++; // 0xa0 length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } byte[] oid_array=new byte[length]; System.arraycopy(plain, index, oid_array, 0, length); index+=length; for(int i = 0; i0){ length=(length<<8)+(plain[index++]&0xff); } } byte[] Q_array=new byte[length]; System.arraycopy(plain, index, Q_array, 0, length); index+=length; byte[][] tmp = fromPoint(Q_array); r_array = tmp[0]; s_array = tmp[1]; if(prv_array!=null) key_size = prv_array.length>=64 ? 521 : (prv_array.length>=48 ? 384 : 256); } catch(Exception e){ //System.err.println(e); //e.printStackTrace(); return false; } return true; } public byte[] getPublicKeyBlob(){ byte[] foo = super.getPublicKeyBlob(); if(foo!=null) return foo; if(r_array==null) return null; byte[][] tmp = new byte[3][]; tmp[0] = Util.str2byte("ecdsa-sha2-"+new String(name)); tmp[1] = name; tmp[2] = new byte[1+r_array.length+s_array.length]; tmp[2][0] = 4; // POINT_CONVERSION_UNCOMPRESSED System.arraycopy(r_array, 0, tmp[2], 1, r_array.length); System.arraycopy(s_array, 0, tmp[2], 1+r_array.length, s_array.length); return Buffer.fromBytes(tmp).buffer; } byte[] getKeyTypeName(){ return Util.str2byte("ecdsa-sha2-"+new String(name)); } public int getKeyType(){ return ECDSA; } public int getKeySize(){ return key_size; } public byte[] getSignature(byte[] data){ try{ Class c=Class.forName((String)jsch.getConfig("signature.ecdsa")); SignatureECDSA ecdsa=(SignatureECDSA)(c.newInstance()); ecdsa.init(); ecdsa.setPrvKey(prv_array); ecdsa.update(data); byte[] sig = ecdsa.sign(); byte[][] tmp = new byte[2][]; tmp[0] = Util.str2byte("ecdsa-sha2-"+new String(name)); tmp[1] = sig; return Buffer.fromBytes(tmp).buffer; } catch(Exception e){ //System.err.println("e "+e); } return null; } public Signature getVerifier(){ try{ Class c=Class.forName((String)jsch.getConfig("signature.ecdsa")); final SignatureECDSA ecdsa=(SignatureECDSA)(c.newInstance()); ecdsa.init(); if(r_array == null && s_array == null && getPublicKeyBlob()!=null){ Buffer buf = new Buffer(getPublicKeyBlob()); buf.getString(); // ecdsa-sha2-nistp256 buf.getString(); // nistp256 byte[][] tmp = fromPoint(buf.getString()); r_array = tmp[0]; s_array = tmp[1]; } ecdsa.setPubKey(r_array, s_array); return ecdsa; } catch(Exception e){ //System.err.println("e "+e); } return null; } static KeyPair fromSSHAgent(JSch jsch, Buffer buf) throws JSchException { byte[][] tmp = buf.getBytes(5, "invalid key format"); byte[] name = tmp[1]; // nistp256 byte[][] foo = fromPoint(tmp[2]); byte[] r_array = foo[0]; byte[] s_array = foo[1]; byte[] prv_array = tmp[3]; KeyPairECDSA kpair = new KeyPairECDSA(jsch, name, r_array, s_array, prv_array); kpair.publicKeyComment = new String(tmp[4]); kpair.vendor=VENDOR_OPENSSH; return kpair; } public byte[] forSSHAgent() throws JSchException { if(isEncrypted()){ throw new JSchException("key is encrypted."); } Buffer buf = new Buffer(); buf.putString(Util.str2byte("ecdsa-sha2-"+new String(name))); buf.putString(name); buf.putString(toPoint(r_array, s_array)); buf.putString(prv_array); buf.putString(Util.str2byte(publicKeyComment)); byte[] result = new byte[buf.getLength()]; buf.getByte(result, 0, result.length); return result; } static byte[] toPoint(byte[] r_array, byte[] s_array) { byte[] tmp = new byte[1+r_array.length+s_array.length]; tmp[0]=0x04; System.arraycopy(r_array, 0, tmp, 1, r_array.length); System.arraycopy(s_array, 0, tmp, 1+r_array.length, s_array.length); return tmp; } static byte[][] fromPoint(byte[] point) { int i = 0; while(point[i]!=4) i++; i++; byte[][] tmp = new byte[2][]; byte[] r_array = new byte[(point.length-i)/2]; byte[] s_array = new byte[(point.length-i)/2]; // point[0] == 0x04 == POINT_CONVERSION_UNCOMPRESSED System.arraycopy(point, i, r_array, 0, r_array.length); System.arraycopy(point, i+r_array.length, s_array, 0, s_array.length); tmp[0] = r_array; tmp[1] = s_array; return tmp; } public void dispose(){ super.dispose(); Util.bzero(prv_array); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/ChannelExec.java0000644000000000000000000000554612500204701021660 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; import java.util.*; public class ChannelExec extends ChannelSession{ byte[] command=new byte[0]; public void start() throws JSchException{ Session _session=getSession(); try{ sendRequests(); Request request=new RequestExec(command); request.request(_session, this); } catch(Exception e){ if(e instanceof JSchException) throw (JSchException)e; if(e instanceof Throwable) throw new JSchException("ChannelExec", (Throwable)e); throw new JSchException("ChannelExec"); } if(io.in!=null){ thread=new Thread(this); thread.setName("Exec thread "+_session.getHost()); if(_session.daemon_thread){ thread.setDaemon(_session.daemon_thread); } thread.start(); } } public void setCommand(String command){ this.command=Util.str2byte(command); } public void setCommand(byte[] command){ this.command=command; } void init() throws JSchException { io.setInputStream(getSession().in); io.setOutputStream(getSession().out); } public void setErrStream(java.io.OutputStream out){ setExtOutputStream(out); } public void setErrStream(java.io.OutputStream out, boolean dontclose){ setExtOutputStream(out, dontclose); } public java.io.InputStream getErrStream() throws java.io.IOException { return getExtInputStream(); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/ConfigRepository.java0000644000000000000000000000433412500204767023016 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2013-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public interface ConfigRepository { public Config getConfig(String host); public interface Config { public String getHostname(); public String getUser(); public int getPort(); public String getValue(String key); public String[] getValues(String key); } static final Config defaultConfig = new Config() { public String getHostname() {return null;} public String getUser() {return null;} public int getPort() {return -1;} public String getValue(String key) {return null;} public String[] getValues(String key) {return null;} }; static final ConfigRepository nullConfig = new ConfigRepository(){ public Config getConfig(String host) { return defaultConfig; } }; } jsch-0.1.53/src/main/java/com/jcraft/jsch/SftpStatVFS.java0000644000000000000000000000752112500205461021631 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; import java.text.SimpleDateFormat; import java.util.Date; public class SftpStatVFS { /* It seems data is serializsed according to sys/statvfs.h; for example, http://pubs.opengroup.org/onlinepubs/009604499/basedefs/sys/statvfs.h.html */ private long bsize; private long frsize; private long blocks; private long bfree; private long bavail; private long files; private long ffree; private long favail; private long fsid; private long flag; private long namemax; int flags=0; long size; int uid; int gid; int permissions; int atime; int mtime; String[] extended=null; private SftpStatVFS(){ } static SftpStatVFS getStatVFS(Buffer buf){ SftpStatVFS statvfs=new SftpStatVFS(); statvfs.bsize = buf.getLong(); statvfs.frsize = buf.getLong(); statvfs.blocks = buf.getLong(); statvfs.bfree = buf.getLong(); statvfs.bavail = buf.getLong(); statvfs.files = buf.getLong(); statvfs.ffree = buf.getLong(); statvfs.favail = buf.getLong(); statvfs.fsid = buf.getLong(); int flag = (int)buf.getLong(); statvfs.namemax = buf.getLong(); statvfs.flag = (flag & 1/*SSH2_FXE_STATVFS_ST_RDONLY*/) != 0 ? 1/*ST_RDONLY*/ : 0; statvfs.flag |= (flag & 2/*SSH2_FXE_STATVFS_ST_NOSUID*/) != 0 ? 2/*ST_NOSUID*/ : 0; return statvfs; } public long getBlockSize() { return bsize; } public long getFragmentSize() { return frsize; } public long getBlocks() { return blocks; } public long getFreeBlocks() { return bfree; } public long getAvailBlocks() { return bavail; } public long getINodes() { return files; } public long getFreeINodes() { return ffree; } public long getAvailINodes() { return favail; } public long getFileSystemID() { return fsid; } public long getMountFlag() { return flag; } public long getMaximumFilenameLength() { return namemax; } public long getSize(){ return getFragmentSize()*getBlocks()/1024; } public long getUsed(){ return getFragmentSize()*(getBlocks()-getFreeBlocks())/1024; } public long getAvailForNonRoot(){ return getFragmentSize()*getAvailBlocks()/1024; } public long getAvail(){ return getFragmentSize()*getFreeBlocks()/1024; } public int getCapacity(){ return (int)(100*(getBlocks()-getFreeBlocks())/getBlocks()); } // public String toString() { return ""; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/KeyPairGenDSA.java0000644000000000000000000000325412500205177022033 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public interface KeyPairGenDSA{ void init(int key_size) throws Exception; byte[] getX(); byte[] getY(); byte[] getP(); byte[] getQ(); byte[] getG(); } jsch-0.1.53/src/main/java/com/jcraft/jsch/DHGEX256.java0000644000000000000000000000312712533576670020617 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public class DHGEX256 extends DHGEX { DHGEX256(){ hash="sha-256"; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/ServerSocketFactory.java0000644000000000000000000000330112500205430023435 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; import java.net.*; import java.io.*; public interface ServerSocketFactory{ public ServerSocket createServerSocket(int port, int backlog, InetAddress bindAddr) throws IOException; } jsch-0.1.53/src/main/java/com/jcraft/jsch/HostKey.java0000644000000000000000000001103112500221002021044 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public class HostKey{ private static final byte[][] names = { Util.str2byte("ssh-dss"), Util.str2byte("ssh-rsa"), Util.str2byte("ecdsa-sha2-nistp256"), Util.str2byte("ecdsa-sha2-nistp384"), Util.str2byte("ecdsa-sha2-nistp521") }; protected static final int GUESS=0; public static final int SSHDSS=1; public static final int SSHRSA=2; public static final int ECDSA256=3; public static final int ECDSA384=4; public static final int ECDSA521=5; static final int UNKNOWN=6; protected String marker; protected String host; protected int type; protected byte[] key; protected String comment; public HostKey(String host, byte[] key) throws JSchException { this(host, GUESS, key); } public HostKey(String host, int type, byte[] key) throws JSchException { this(host, type, key, null); } public HostKey(String host, int type, byte[] key, String comment) throws JSchException { this("", host, type, key, comment); } public HostKey(String marker, String host, int type, byte[] key, String comment) throws JSchException { this.marker=marker; this.host=host; if(type==GUESS){ if(key[8]=='d'){ this.type=SSHDSS; } else if(key[8]=='r'){ this.type=SSHRSA; } else if(key[8]=='a' && key[20]=='2'){ this.type=ECDSA256; } else if(key[8]=='a' && key[20]=='3'){ this.type=ECDSA384; } else if(key[8]=='a' && key[20]=='5'){ this.type=ECDSA521; } else { throw new JSchException("invalid key type");} } else{ this.type=type; } this.key=key; this.comment=comment; } public String getHost(){ return host; } public String getType(){ if(type==SSHDSS || type==SSHRSA || type==ECDSA256 || type==ECDSA384 || type==ECDSA521){ return Util.byte2str(names[type-1]); } return "UNKNOWN"; } protected static int name2type(String name){ for(int i = 0; i < names.length; i++){ if(Util.byte2str(names[i]).equals(name)){ return i + 1; } } return UNKNOWN; } public String getKey(){ return Util.byte2str(Util.toBase64(key, 0, key.length)); } public String getFingerPrint(JSch jsch){ HASH hash=null; try{ Class c=Class.forName(jsch.getConfig("md5")); hash=(HASH)(c.newInstance()); } catch(Exception e){ System.err.println("getFingerPrint: "+e); } return Util.getFingerPrint(hash, key); } public String getComment(){ return comment; } public String getMarker(){ return marker; } boolean isMatched(String _host){ return isIncluded(_host); } private boolean isIncluded(String _host){ int i=0; String hosts=this.host; int hostslen=hosts.length(); int hostlen=_host.length(); int j; while(i0){ length=(length<<8)+(plain[index++]&0xff); } } if(plain[index]!=0x02)return false; index++; // INTEGER length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } index+=length; index++; length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } P_array=new byte[length]; System.arraycopy(plain, index, P_array, 0, length); index+=length; index++; length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } Q_array=new byte[length]; System.arraycopy(plain, index, Q_array, 0, length); index+=length; index++; length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } G_array=new byte[length]; System.arraycopy(plain, index, G_array, 0, length); index+=length; index++; length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } pub_array=new byte[length]; System.arraycopy(plain, index, pub_array, 0, length); index+=length; index++; length=plain[index++]&0xff; if((length&0x80)!=0){ int foo=length&0x7f; length=0; while(foo-->0){ length=(length<<8)+(plain[index++]&0xff); } } prv_array=new byte[length]; System.arraycopy(plain, index, prv_array, 0, length); index+=length; if(P_array!=null) key_size = (new java.math.BigInteger(P_array)).bitLength(); } catch(Exception e){ //System.err.println(e); //e.printStackTrace(); return false; } return true; } public byte[] getPublicKeyBlob(){ byte[] foo=super.getPublicKeyBlob(); if(foo!=null) return foo; if(P_array==null) return null; byte[][] tmp = new byte[5][]; tmp[0] = sshdss; tmp[1] = P_array; tmp[2] = Q_array; tmp[3] = G_array; tmp[4] = pub_array; return Buffer.fromBytes(tmp).buffer; } private static final byte[] sshdss=Util.str2byte("ssh-dss"); byte[] getKeyTypeName(){return sshdss;} public int getKeyType(){return DSA;} public int getKeySize(){ return key_size; } public byte[] getSignature(byte[] data){ try{ Class c=Class.forName((String)jsch.getConfig("signature.dss")); SignatureDSA dsa=(SignatureDSA)(c.newInstance()); dsa.init(); dsa.setPrvKey(prv_array, P_array, Q_array, G_array); dsa.update(data); byte[] sig = dsa.sign(); byte[][] tmp = new byte[2][]; tmp[0] = sshdss; tmp[1] = sig; return Buffer.fromBytes(tmp).buffer; } catch(Exception e){ //System.err.println("e "+e); } return null; } public Signature getVerifier(){ try{ Class c=Class.forName((String)jsch.getConfig("signature.dss")); SignatureDSA dsa=(SignatureDSA)(c.newInstance()); dsa.init(); if(pub_array == null && P_array == null && getPublicKeyBlob()!=null){ Buffer buf = new Buffer(getPublicKeyBlob()); buf.getString(); P_array = buf.getString(); Q_array = buf.getString(); G_array = buf.getString(); pub_array = buf.getString(); } dsa.setPubKey(pub_array, P_array, Q_array, G_array); return dsa; } catch(Exception e){ //System.err.println("e "+e); } return null; } static KeyPair fromSSHAgent(JSch jsch, Buffer buf) throws JSchException { byte[][] tmp = buf.getBytes(7, "invalid key format"); byte[] P_array = tmp[1]; byte[] Q_array = tmp[2]; byte[] G_array = tmp[3]; byte[] pub_array = tmp[4]; byte[] prv_array = tmp[5]; KeyPairDSA kpair = new KeyPairDSA(jsch, P_array, Q_array, G_array, pub_array, prv_array); kpair.publicKeyComment = new String(tmp[6]); kpair.vendor=VENDOR_OPENSSH; return kpair; } public byte[] forSSHAgent() throws JSchException { if(isEncrypted()){ throw new JSchException("key is encrypted."); } Buffer buf = new Buffer(); buf.putString(sshdss); buf.putString(P_array); buf.putString(Q_array); buf.putString(G_array); buf.putString(pub_array); buf.putString(prv_array); buf.putString(Util.str2byte(publicKeyComment)); byte[] result = new byte[buf.getLength()]; buf.getByte(result, 0, result.length); return result; } public void dispose(){ super.dispose(); Util.bzero(prv_array); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/RequestPtyReq.java0000644000000000000000000000512612500205364022300 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; class RequestPtyReq extends Request{ private String ttype="vt100"; private int tcol=80; private int trow=24; private int twp=640; private int thp=480; private byte[] terminal_mode=Util.empty; void setCode(String cookie){ } void setTType(String ttype){ this.ttype=ttype; } void setTerminalMode(byte[] terminal_mode){ this.terminal_mode=terminal_mode; } void setTSize(int tcol, int trow, int twp, int thp){ this.tcol=tcol; this.trow=trow; this.twp=twp; this.thp=thp; } public void request(Session session, Channel channel) throws Exception{ super.request(session, channel); Buffer buf=new Buffer(); Packet packet=new Packet(buf); packet.reset(); buf.putByte((byte) Session.SSH_MSG_CHANNEL_REQUEST); buf.putInt(channel.getRecipient()); buf.putString(Util.str2byte("pty-req")); buf.putByte((byte)(waitForReply() ? 1 : 0)); buf.putString(Util.str2byte(ttype)); buf.putInt(tcol); buf.putInt(trow); buf.putInt(twp); buf.putInt(thp); buf.putString(terminal_mode); write(packet); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/DHECN.java0000664000000000000000000001324712500162771020335 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public abstract class DHECN extends KeyExchange{ private static final int SSH_MSG_KEX_ECDH_INIT = 30; private static final int SSH_MSG_KEX_ECDH_REPLY= 31; private int state; byte[] Q_C; byte[] V_S; byte[] V_C; byte[] I_S; byte[] I_C; byte[] e; private Buffer buf; private Packet packet; private ECDH ecdh; protected String sha_name; protected int key_size; public void init(Session session, byte[] V_S, byte[] V_C, byte[] I_S, byte[] I_C) throws Exception{ this.session=session; this.V_S=V_S; this.V_C=V_C; this.I_S=I_S; this.I_C=I_C; try{ Class c=Class.forName(session.getConfig(sha_name)); sha=(HASH)(c.newInstance()); sha.init(); } catch(Exception e){ System.err.println(e); } buf=new Buffer(); packet=new Packet(buf); packet.reset(); buf.putByte((byte)SSH_MSG_KEX_ECDH_INIT); try{ Class c=Class.forName(session.getConfig("ecdh-sha2-nistp")); ecdh=(ECDH)(c.newInstance()); ecdh.init(key_size); Q_C = ecdh.getQ(); buf.putString(Q_C); } catch(Exception e){ if(e instanceof Throwable) throw new JSchException(e.toString(), (Throwable)e); throw new JSchException(e.toString()); } if(V_S==null){ // This is a really ugly hack for Session.checkKexes ;-( return; } session.write(packet); if(JSch.getLogger().isEnabled(Logger.INFO)){ JSch.getLogger().log(Logger.INFO, "SSH_MSG_KEX_ECDH_INIT sent"); JSch.getLogger().log(Logger.INFO, "expecting SSH_MSG_KEX_ECDH_REPLY"); } state=SSH_MSG_KEX_ECDH_REPLY; } public boolean next(Buffer _buf) throws Exception{ int i,j; switch(state){ case SSH_MSG_KEX_ECDH_REPLY: // The server responds with: // byte SSH_MSG_KEX_ECDH_REPLY // string K_S, server's public host key // string Q_S, server's ephemeral public key octet string // string the signature on the exchange hash j=_buf.getInt(); j=_buf.getByte(); j=_buf.getByte(); if(j!=31){ System.err.println("type: must be 31 "+j); return false; } K_S=_buf.getString(); byte[] Q_S=_buf.getString(); byte[][] r_s = KeyPairECDSA.fromPoint(Q_S); // RFC 5656, // 4. ECDH Key Exchange // All elliptic curve public keys MUST be validated after they are // received. An example of a validation algorithm can be found in // Section 3.2.2 of [SEC1]. If a key fails validation, // the key exchange MUST fail. if(!ecdh.validate(r_s[0], r_s[1])){ return false; } K = ecdh.getSecret(r_s[0], r_s[1]); K=normalize(K); byte[] sig_of_H=_buf.getString(); //The hash H is computed as the HASH hash of the concatenation of the //following: // string V_C, client's identification string (CR and LF excluded) // string V_S, server's identification string (CR and LF excluded) // string I_C, payload of the client's SSH_MSG_KEXINIT // string I_S, payload of the server's SSH_MSG_KEXINIT // string K_S, server's public host key // string Q_C, client's ephemeral public key octet string // string Q_S, server's ephemeral public key octet string // mpint K, shared secret // This value is called the exchange hash, and it is used to authenti- // cate the key exchange. buf.reset(); buf.putString(V_C); buf.putString(V_S); buf.putString(I_C); buf.putString(I_S); buf.putString(K_S); buf.putString(Q_C); buf.putString(Q_S); buf.putMPInt(K); byte[] foo=new byte[buf.getLength()]; buf.getByte(foo); sha.update(foo, 0, foo.length); H=sha.digest(); i=0; j=0; j=((K_S[i++]<<24)&0xff000000)|((K_S[i++]<<16)&0x00ff0000)| ((K_S[i++]<<8)&0x0000ff00)|((K_S[i++])&0x000000ff); String alg=Util.byte2str(K_S, i, j); i+=j; boolean result = verify(alg, K_S, i, sig_of_H); state=STATE_END; return result; } return false; } public int getState(){return state; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/DHG14.java0000644000000000000000000002005512500205014020240 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public class DHG14 extends KeyExchange{ static final byte[] g={ 2 }; static final byte[] p={ (byte)0x00, (byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF, (byte)0xC9,(byte)0x0F,(byte)0xDA,(byte)0xA2,(byte)0x21,(byte)0x68,(byte)0xC2,(byte)0x34, (byte)0xC4,(byte)0xC6,(byte)0x62,(byte)0x8B,(byte)0x80,(byte)0xDC,(byte)0x1C,(byte)0xD1, (byte)0x29,(byte)0x02,(byte)0x4E,(byte)0x08,(byte)0x8A,(byte)0x67,(byte)0xCC,(byte)0x74, (byte)0x02,(byte)0x0B,(byte)0xBE,(byte)0xA6,(byte)0x3B,(byte)0x13,(byte)0x9B,(byte)0x22, (byte)0x51,(byte)0x4A,(byte)0x08,(byte)0x79,(byte)0x8E,(byte)0x34,(byte)0x04,(byte)0xDD, (byte)0xEF,(byte)0x95,(byte)0x19,(byte)0xB3,(byte)0xCD,(byte)0x3A,(byte)0x43,(byte)0x1B, (byte)0x30,(byte)0x2B,(byte)0x0A,(byte)0x6D,(byte)0xF2,(byte)0x5F,(byte)0x14,(byte)0x37, (byte)0x4F,(byte)0xE1,(byte)0x35,(byte)0x6D,(byte)0x6D,(byte)0x51,(byte)0xC2,(byte)0x45, (byte)0xE4,(byte)0x85,(byte)0xB5,(byte)0x76,(byte)0x62,(byte)0x5E,(byte)0x7E,(byte)0xC6, (byte)0xF4,(byte)0x4C,(byte)0x42,(byte)0xE9,(byte)0xA6,(byte)0x37,(byte)0xED,(byte)0x6B, (byte)0x0B,(byte)0xFF,(byte)0x5C,(byte)0xB6,(byte)0xF4,(byte)0x06,(byte)0xB7,(byte)0xED, (byte)0xEE,(byte)0x38,(byte)0x6B,(byte)0xFB,(byte)0x5A,(byte)0x89,(byte)0x9F,(byte)0xA5, (byte)0xAE,(byte)0x9F,(byte)0x24,(byte)0x11,(byte)0x7C,(byte)0x4B,(byte)0x1F,(byte)0xE6, (byte)0x49,(byte)0x28,(byte)0x66,(byte)0x51,(byte)0xEC,(byte)0xE4,(byte)0x5B,(byte)0x3D, (byte)0xC2,(byte)0x00,(byte)0x7C,(byte)0xB8,(byte)0xA1,(byte)0x63,(byte)0xBF,(byte)0x05, (byte)0x98,(byte)0xDA,(byte)0x48,(byte)0x36,(byte)0x1C,(byte)0x55,(byte)0xD3,(byte)0x9A, (byte)0x69,(byte)0x16,(byte)0x3F,(byte)0xA8,(byte)0xFD,(byte)0x24,(byte)0xCF,(byte)0x5F, (byte)0x83,(byte)0x65,(byte)0x5D,(byte)0x23,(byte)0xDC,(byte)0xA3,(byte)0xAD,(byte)0x96, (byte)0x1C,(byte)0x62,(byte)0xF3,(byte)0x56,(byte)0x20,(byte)0x85,(byte)0x52,(byte)0xBB, (byte)0x9E,(byte)0xD5,(byte)0x29,(byte)0x07,(byte)0x70,(byte)0x96,(byte)0x96,(byte)0x6D, (byte)0x67,(byte)0x0C,(byte)0x35,(byte)0x4E,(byte)0x4A,(byte)0xBC,(byte)0x98,(byte)0x04, (byte)0xF1,(byte)0x74,(byte)0x6C,(byte)0x08,(byte)0xCA,(byte)0x18,(byte)0x21,(byte)0x7C, (byte)0x32,(byte)0x90,(byte)0x5E,(byte)0x46,(byte)0x2E,(byte)0x36,(byte)0xCE,(byte)0x3B, (byte)0xE3,(byte)0x9E,(byte)0x77,(byte)0x2C,(byte)0x18,(byte)0x0E,(byte)0x86,(byte)0x03, (byte)0x9B,(byte)0x27,(byte)0x83,(byte)0xA2,(byte)0xEC,(byte)0x07,(byte)0xA2,(byte)0x8F, (byte)0xB5,(byte)0xC5,(byte)0x5D,(byte)0xF0,(byte)0x6F,(byte)0x4C,(byte)0x52,(byte)0xC9, (byte)0xDE,(byte)0x2B,(byte)0xCB,(byte)0xF6,(byte)0x95,(byte)0x58,(byte)0x17,(byte)0x18, (byte)0x39,(byte)0x95,(byte)0x49,(byte)0x7C,(byte)0xEA,(byte)0x95,(byte)0x6A,(byte)0xE5, (byte)0x15,(byte)0xD2,(byte)0x26,(byte)0x18,(byte)0x98,(byte)0xFA,(byte)0x05,(byte)0x10, (byte)0x15,(byte)0x72,(byte)0x8E,(byte)0x5A,(byte)0x8A,(byte)0xAC,(byte)0xAA,(byte)0x68, (byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF }; private static final int SSH_MSG_KEXDH_INIT= 30; private static final int SSH_MSG_KEXDH_REPLY= 31; private int state; DH dh; byte[] V_S; byte[] V_C; byte[] I_S; byte[] I_C; byte[] e; private Buffer buf; private Packet packet; public void init(Session session, byte[] V_S, byte[] V_C, byte[] I_S, byte[] I_C) throws Exception{ this.session=session; this.V_S=V_S; this.V_C=V_C; this.I_S=I_S; this.I_C=I_C; try{ Class c=Class.forName(session.getConfig("sha-1")); sha=(HASH)(c.newInstance()); sha.init(); } catch(Exception e){ System.err.println(e); } buf=new Buffer(); packet=new Packet(buf); try{ Class c=Class.forName(session.getConfig("dh")); dh=(DH)(c.newInstance()); dh.init(); } catch(Exception e){ //System.err.println(e); throw e; } dh.setP(p); dh.setG(g); // The client responds with: // byte SSH_MSG_KEXDH_INIT(30) // mpint e <- g^x mod p // x is a random number (1 < x < (p-1)/2) e=dh.getE(); packet.reset(); buf.putByte((byte)SSH_MSG_KEXDH_INIT); buf.putMPInt(e); if(V_S==null){ // This is a really ugly hack for Session.checkKexes ;-( return; } session.write(packet); if(JSch.getLogger().isEnabled(Logger.INFO)){ JSch.getLogger().log(Logger.INFO, "SSH_MSG_KEXDH_INIT sent"); JSch.getLogger().log(Logger.INFO, "expecting SSH_MSG_KEXDH_REPLY"); } state=SSH_MSG_KEXDH_REPLY; } public boolean next(Buffer _buf) throws Exception{ int i,j; switch(state){ case SSH_MSG_KEXDH_REPLY: // The server responds with: // byte SSH_MSG_KEXDH_REPLY(31) // string server public host key and certificates (K_S) // mpint f // string signature of H j=_buf.getInt(); j=_buf.getByte(); j=_buf.getByte(); if(j!=31){ System.err.println("type: must be 31 "+j); return false; } K_S=_buf.getString(); byte[] f=_buf.getMPInt(); byte[] sig_of_H=_buf.getString(); dh.setF(f); dh.checkRange(); K=normalize(dh.getK()); //The hash H is computed as the HASH hash of the concatenation of the //following: // string V_C, the client's version string (CR and NL excluded) // string V_S, the server's version string (CR and NL excluded) // string I_C, the payload of the client's SSH_MSG_KEXINIT // string I_S, the payload of the server's SSH_MSG_KEXINIT // string K_S, the host key // mpint e, exchange value sent by the client // mpint f, exchange value sent by the server // mpint K, the shared secret // This value is called the exchange hash, and it is used to authenti- // cate the key exchange. buf.reset(); buf.putString(V_C); buf.putString(V_S); buf.putString(I_C); buf.putString(I_S); buf.putString(K_S); buf.putMPInt(e); buf.putMPInt(f); buf.putMPInt(K); byte[] foo=new byte[buf.getLength()]; buf.getByte(foo); sha.update(foo, 0, foo.length); H=sha.digest(); //System.err.print("H -> "); //dump(H, 0, H.length); i=0; j=0; j=((K_S[i++]<<24)&0xff000000)|((K_S[i++]<<16)&0x00ff0000)| ((K_S[i++]<<8)&0x0000ff00)|((K_S[i++])&0x000000ff); String alg=Util.byte2str(K_S, i, j); i+=j; boolean result = verify(alg, K_S, i, sig_of_H); state=STATE_END; return result; } return false; } public int getState(){return state; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/SftpATTRS.java0000644000000000000000000002256712500205442021242 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; import java.text.SimpleDateFormat; import java.util.Date; /* uint32 flags uint64 size present only if flag SSH_FILEXFER_ATTR_SIZE uint32 uid present only if flag SSH_FILEXFER_ATTR_UIDGID uint32 gid present only if flag SSH_FILEXFER_ATTR_UIDGID uint32 permissions present only if flag SSH_FILEXFER_ATTR_PERMISSIONS uint32 atime present only if flag SSH_FILEXFER_ACMODTIME uint32 mtime present only if flag SSH_FILEXFER_ACMODTIME uint32 extended_count present only if flag SSH_FILEXFER_ATTR_EXTENDED string extended_type string extended_data ... more extended data (extended_type - extended_data pairs), so that number of pairs equals extended_count */ public class SftpATTRS { static final int S_ISUID = 04000; // set user ID on execution static final int S_ISGID = 02000; // set group ID on execution static final int S_ISVTX = 01000; // sticky bit ****** NOT DOCUMENTED ***** static final int S_IRUSR = 00400; // read by owner static final int S_IWUSR = 00200; // write by owner static final int S_IXUSR = 00100; // execute/search by owner static final int S_IREAD = 00400; // read by owner static final int S_IWRITE= 00200; // write by owner static final int S_IEXEC = 00100; // execute/search by owner static final int S_IRGRP = 00040; // read by group static final int S_IWGRP = 00020; // write by group static final int S_IXGRP = 00010; // execute/search by group static final int S_IROTH = 00004; // read by others static final int S_IWOTH = 00002; // write by others static final int S_IXOTH = 00001; // execute/search by others private static final int pmask = 0xFFF; public String getPermissionsString() { StringBuffer buf = new StringBuffer(10); if(isDir()) buf.append('d'); else if(isLink()) buf.append('l'); else buf.append('-'); if((permissions & S_IRUSR)!=0) buf.append('r'); else buf.append('-'); if((permissions & S_IWUSR)!=0) buf.append('w'); else buf.append('-'); if((permissions & S_ISUID)!=0) buf.append('s'); else if ((permissions & S_IXUSR)!=0) buf.append('x'); else buf.append('-'); if((permissions & S_IRGRP)!=0) buf.append('r'); else buf.append('-'); if((permissions & S_IWGRP)!=0) buf.append('w'); else buf.append('-'); if((permissions & S_ISGID)!=0) buf.append('s'); else if((permissions & S_IXGRP)!=0) buf.append('x'); else buf.append('-'); if((permissions & S_IROTH) != 0) buf.append('r'); else buf.append('-'); if((permissions & S_IWOTH) != 0) buf.append('w'); else buf.append('-'); if((permissions & S_IXOTH) != 0) buf.append('x'); else buf.append('-'); return (buf.toString()); } public String getAtimeString(){ Date date= new Date(((long)atime)*1000L); return (date.toString()); } public String getMtimeString(){ Date date= new Date(((long)mtime)*1000L); return (date.toString()); } public static final int SSH_FILEXFER_ATTR_SIZE= 0x00000001; public static final int SSH_FILEXFER_ATTR_UIDGID= 0x00000002; public static final int SSH_FILEXFER_ATTR_PERMISSIONS= 0x00000004; public static final int SSH_FILEXFER_ATTR_ACMODTIME= 0x00000008; public static final int SSH_FILEXFER_ATTR_EXTENDED= 0x80000000; static final int S_IFMT=0xf000; static final int S_IFIFO=0x1000; static final int S_IFCHR=0x2000; static final int S_IFDIR=0x4000; static final int S_IFBLK=0x6000; static final int S_IFREG=0x8000; static final int S_IFLNK=0xa000; static final int S_IFSOCK=0xc000; int flags=0; long size; int uid; int gid; int permissions; int atime; int mtime; String[] extended=null; private SftpATTRS(){ } static SftpATTRS getATTR(Buffer buf){ SftpATTRS attr=new SftpATTRS(); attr.flags=buf.getInt(); if((attr.flags&SSH_FILEXFER_ATTR_SIZE)!=0){ attr.size=buf.getLong(); } if((attr.flags&SSH_FILEXFER_ATTR_UIDGID)!=0){ attr.uid=buf.getInt(); attr.gid=buf.getInt(); } if((attr.flags&SSH_FILEXFER_ATTR_PERMISSIONS)!=0){ attr.permissions=buf.getInt(); } if((attr.flags&SSH_FILEXFER_ATTR_ACMODTIME)!=0){ attr.atime=buf.getInt(); } if((attr.flags&SSH_FILEXFER_ATTR_ACMODTIME)!=0){ attr.mtime=buf.getInt(); } if((attr.flags&SSH_FILEXFER_ATTR_EXTENDED)!=0){ int count=buf.getInt(); if(count>0){ attr.extended=new String[count*2]; for(int i=0; i0){ for(int i=0; i0){ for(int i=0; i>>2)); if(buf[i+3]==(byte)'='){ j+=2; break;} foo[j+2]=(byte)(((val(buf[i+2])&0x03)<<6)|(val(buf[i+3])&0x3f)); j+=3; } byte[] bar=new byte[j]; System.arraycopy(foo, 0, bar, 0, j); return bar; } catch(ArrayIndexOutOfBoundsException e) { throw new JSchException("fromBase64: invalid base64 data", e); } } static byte[] toBase64(byte[] buf, int start, int length){ byte[] tmp=new byte[length*2]; int i,j,k; int foo=(length/3)*3+start; i=0; for(j=start; j>>2)&0x3f; tmp[i++]=b64[k]; k=(buf[j]&0x03)<<4|(buf[j+1]>>>4)&0x0f; tmp[i++]=b64[k]; k=(buf[j+1]&0x0f)<<2|(buf[j+2]>>>6)&0x03; tmp[i++]=b64[k]; k=buf[j+2]&0x3f; tmp[i++]=b64[k]; } foo=(start+length)-foo; if(foo==1){ k=(buf[j]>>>2)&0x3f; tmp[i++]=b64[k]; k=((buf[j]&0x03)<<4)&0x3f; tmp[i++]=b64[k]; tmp[i++]=(byte)'='; tmp[i++]=(byte)'='; } else if(foo==2){ k=(buf[j]>>>2)&0x3f; tmp[i++]=b64[k]; k=(buf[j]&0x03)<<4|(buf[j+1]>>>4)&0x0f; tmp[i++]=b64[k]; k=((buf[j+1]&0x0f)<<2)&0x3f; tmp[i++]=b64[k]; tmp[i++]=(byte)'='; } byte[] bar=new byte[i]; System.arraycopy(tmp, 0, bar, 0, i); return bar; // return sun.misc.BASE64Encoder().encode(buf); } static String[] split(String foo, String split){ if(foo==null) return null; byte[] buf=Util.str2byte(foo); java.util.Vector bar=new java.util.Vector(); int start=0; int index; while(true){ index=foo.indexOf(split, start); if(index>=0){ bar.addElement(Util.byte2str(buf, start, index-start)); start=index+1; continue; } bar.addElement(Util.byte2str(buf, start, buf.length-start)); break; } String[] result=new String[bar.size()]; for(int i=0; i0 && name[0]=='.'){ if(pattern.length>0 && pattern[0]=='.'){ if(pattern.length==2 && pattern[1]=='*') return true; return glob(pattern, pattern_index+1, name, name_index+1); } return false; } return glob(pattern, pattern_index, name, name_index); } static private boolean glob(byte[] pattern, int pattern_index, byte[] name, int name_index){ //System.err.println("glob: "+new String(pattern)+", "+pattern_index+" "+new String(name)+", "+name_index); int patternlen=pattern.length; if(patternlen==0) return false; int namelen=name.length; int i=pattern_index; int j=name_index; while(i>>4)&0xf]); sb.append(chars[(bar)&0xf]); if(i+1>>8); bar[j++]=(byte)foo[i]; } } return bar; } */ static void bzero(byte[] foo){ if(foo==null) return; for(int i=0; i0); } void out_close(){ try{ if(out!=null && !out_dontclose) out.close(); out=null; } catch(Exception ee){} } public void close(){ try{ if(in!=null && !in_dontclose) in.close(); in=null; } catch(Exception ee){} out_close(); try{ if(out_ext!=null && !out_ext_dontclose) out_ext.close(); out_ext=null; } catch(Exception ee){} } /* public void finalize() throws Throwable{ try{ if(in!=null) in.close(); } catch(Exception ee){} try{ if(out!=null) out.close(); } catch(Exception ee){} try{ if(out_ext!=null) out_ext.close(); } catch(Exception ee){} } */ } jsch-0.1.53/src/main/java/com/jcraft/jsch/SocketFactory.java0000644000000000000000000000350512500205510022253 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; import java.net.*; import java.io.*; public interface SocketFactory{ public Socket createSocket(String host, int port)throws IOException, UnknownHostException; public InputStream getInputStream(Socket socket)throws IOException; public OutputStream getOutputStream(Socket socket)throws IOException; } jsch-0.1.53/src/main/java/com/jcraft/jsch/Logger.java0000644000000000000000000000415112500205241020711 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2006-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public interface Logger{ public final int DEBUG=0; public final int INFO=1; public final int WARN=2; public final int ERROR=3; public final int FATAL=4; public boolean isEnabled(int level); public void log(int level, String message); /* public final Logger SIMPLE_LOGGER=new Logger(){ public boolean isEnabled(int level){return true;} public void log(int level, String message){System.err.println(message);} }; final Logger DEVNULL=new Logger(){ public boolean isEnabled(int level){return false;} public void log(int level, String message){} }; */ } jsch-0.1.53/src/main/java/com/jcraft/jsch/jcraft/0000755000000000000000000000000012500206242020101 5ustar rootrootjsch-0.1.53/src/main/java/com/jcraft/jsch/jcraft/HMAC.java0000644000000000000000000000636312500206166021471 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2006-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jcraft; import java.security.*; class HMAC{ /* * Refer to RFC2104. * * H(K XOR opad, H(K XOR ipad, text)) * * where K is an n byte key * ipad is the byte 0x36 repeated 64 times * opad is the byte 0x5c repeated 64 times * and text is the data being protected */ private static final int B=64; private byte[] k_ipad=null; private byte[] k_opad=null; private MessageDigest md=null; private int bsize=0; protected void setH(MessageDigest md){ this.md=md; bsize=md.getDigestLength(); } public int getBlockSize(){return bsize;}; public void init(byte[] key) throws Exception{ md.reset(); if(key.length>bsize){ byte[] tmp=new byte[bsize]; System.arraycopy(key, 0, tmp, 0, bsize); key=tmp; } /* if key is longer than B bytes reset it to key=MD5(key) */ if(key.length>B){ md.update(key, 0, key.length); key=md.digest(); } k_ipad=new byte[B]; System.arraycopy(key, 0, k_ipad, 0, key.length); k_opad=new byte[B]; System.arraycopy(key, 0, k_opad, 0, key.length); /* XOR key with ipad and opad values */ for(int i=0; i>>24); tmp[1]=(byte)(i>>>16); tmp[2]=(byte)(i>>>8); tmp[3]=(byte)i; update(tmp, 0, 4); } public void update(byte foo[], int s, int l){ md.update(foo, s, l); } public void doFinal(byte[] buf, int offset){ byte[] result=md.digest(); md.update(k_opad, 0, B); md.update(result, 0, bsize); try{md.digest(buf, offset, bsize);}catch(Exception e){} md.update(k_ipad, 0, B); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jcraft/HMACSHA196.java0000644000000000000000000000370312500206213022251 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2006-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jcraft; import com.jcraft.jsch.MAC; public class HMACSHA196 extends HMACSHA1{ private static final String name="hmac-sha1-96"; private static final int BSIZE=12; public int getBlockSize(){return BSIZE;}; private final byte[] _buf16=new byte[20]; public void doFinal(byte[] buf, int offset){ super.doFinal(_buf16, 0); System.arraycopy(_buf16, 0, buf, offset, BSIZE); } public String getName(){ return name; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jcraft/Compression.java0000644000000000000000000001112512500206161023245 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jcraft; import com.jcraft.jzlib.*; import com.jcraft.jsch.*; public class Compression implements com.jcraft.jsch.Compression { static private final int BUF_SIZE=4096; private final int buffer_margin=32+20; // AES256 + HMACSHA1 private int type; private ZStream stream; private byte[] tmpbuf=new byte[BUF_SIZE]; public Compression(){ stream=new ZStream(); } public void init(int type, int level){ if(type==DEFLATER){ stream.deflateInit(level); this.type=DEFLATER; } else if(type==INFLATER){ stream.inflateInit(); inflated_buf=new byte[BUF_SIZE]; this.type=INFLATER; } } private byte[] inflated_buf; public byte[] compress(byte[] buf, int start, int[] len){ stream.next_in=buf; stream.next_in_index=start; stream.avail_in=len[0]-start; int status; int outputlen=start; byte[] outputbuf=buf; int tmp=0; do{ stream.next_out=tmpbuf; stream.next_out_index=0; stream.avail_out=BUF_SIZE; status=stream.deflate(JZlib.Z_PARTIAL_FLUSH); switch(status){ case JZlib.Z_OK: tmp=BUF_SIZE-stream.avail_out; if(outputbuf.lengthbuffer.length-start){ byte[] foo=new byte[inflated_end+start]; System.arraycopy(buffer, 0, foo, 0, start); System.arraycopy(inflated_buf, 0, foo, start, inflated_end); buffer=foo; } else{ System.arraycopy(inflated_buf, 0, buffer, start, inflated_end); } length[0]=inflated_end; return buffer; default: System.err.println("uncompress: inflate returnd "+status); return null; } } } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jcraft/HMACMD596.java0000644000000000000000000000370012500206201022134 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2006-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jcraft; import com.jcraft.jsch.MAC; public class HMACMD596 extends HMACMD5{ private static final String name="hmac-md5-96"; private static final int BSIZE=12; public int getBlockSize(){return BSIZE;}; private final byte[] _buf16=new byte[16]; public void doFinal(byte[] buf, int offset){ super.doFinal(_buf16, 0); System.arraycopy(_buf16, 0, buf, offset, BSIZE); } public String getName(){ return name; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jcraft/HMACMD5.java0000644000000000000000000000362312500206175021773 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2006-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jcraft; import com.jcraft.jsch.MAC; import java.security.*; public class HMACMD5 extends HMAC implements MAC{ private static final String name="hmac-md5"; public HMACMD5(){ super(); MessageDigest md=null; try{ md=MessageDigest.getInstance("MD5"); } catch(Exception e){ System.err.println(e); } setH(md); } public String getName(){ return name; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jcraft/HMACSHA1.java0000644000000000000000000000363012500206207022074 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2006-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jcraft; import com.jcraft.jsch.MAC; import java.security.*; public class HMACSHA1 extends HMAC implements MAC{ private static final String name="hmac-sha1"; public HMACSHA1(){ super(); MessageDigest md=null; try{ md=MessageDigest.getInstance("SHA-1"); } catch(Exception e){ System.err.println(e); } setH(md); } public String getName(){ return name; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/GSSContext.java0000644000000000000000000000344512500205047021504 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2004-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public interface GSSContext{ public void create(String user, String host) throws JSchException; public boolean isEstablished(); public byte[] init(byte[] token, int s, int l) throws JSchException; public byte[] getMIC(byte[] message, int s, int l); public void dispose(); } jsch-0.1.53/src/main/java/com/jcraft/jsch/KeyExchange.java0000644000000000000000000002411112500447312021672 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public abstract class KeyExchange{ static final int PROPOSAL_KEX_ALGS=0; static final int PROPOSAL_SERVER_HOST_KEY_ALGS=1; static final int PROPOSAL_ENC_ALGS_CTOS=2; static final int PROPOSAL_ENC_ALGS_STOC=3; static final int PROPOSAL_MAC_ALGS_CTOS=4; static final int PROPOSAL_MAC_ALGS_STOC=5; static final int PROPOSAL_COMP_ALGS_CTOS=6; static final int PROPOSAL_COMP_ALGS_STOC=7; static final int PROPOSAL_LANG_CTOS=8; static final int PROPOSAL_LANG_STOC=9; static final int PROPOSAL_MAX=10; //static String kex_algs="diffie-hellman-group-exchange-sha1"+ // ",diffie-hellman-group1-sha1"; //static String kex="diffie-hellman-group-exchange-sha1"; static String kex="diffie-hellman-group1-sha1"; static String server_host_key="ssh-rsa,ssh-dss"; static String enc_c2s="blowfish-cbc"; static String enc_s2c="blowfish-cbc"; static String mac_c2s="hmac-md5"; // hmac-md5,hmac-sha1,hmac-ripemd160, // hmac-sha1-96,hmac-md5-96 static String mac_s2c="hmac-md5"; //static String comp_c2s="none"; // zlib //static String comp_s2c="none"; static String lang_c2s=""; static String lang_s2c=""; public static final int STATE_END=0; protected Session session=null; protected HASH sha=null; protected byte[] K=null; protected byte[] H=null; protected byte[] K_S=null; public abstract void init(Session session, byte[] V_S, byte[] V_C, byte[] I_S, byte[] I_C) throws Exception; public abstract boolean next(Buffer buf) throws Exception; public abstract int getState(); protected final int RSA=0; protected final int DSS=1; protected final int ECDSA=2; private int type=0; private String key_alg_name = ""; public String getKeyType() { if(type==DSS) return "DSA"; if(type==RSA) return "RSA"; return "ECDSA"; } public String getKeyAlgorithName() { return key_alg_name; } protected static String[] guess(byte[]I_S, byte[]I_C){ String[] guess=new String[PROPOSAL_MAX]; Buffer sb=new Buffer(I_S); sb.setOffSet(17); Buffer cb=new Buffer(I_C); cb.setOffSet(17); if(JSch.getLogger().isEnabled(Logger.INFO)){ for(int i=0; iclient"+ " "+guess[PROPOSAL_ENC_ALGS_STOC]+ " "+guess[PROPOSAL_MAC_ALGS_STOC]+ " "+guess[PROPOSAL_COMP_ALGS_STOC]); JSch.getLogger().log(Logger.INFO, "kex: client->server"+ " "+guess[PROPOSAL_ENC_ALGS_CTOS]+ " "+guess[PROPOSAL_MAC_ALGS_CTOS]+ " "+guess[PROPOSAL_COMP_ALGS_CTOS]); } return guess; } public String getFingerPrint(){ HASH hash=null; try{ Class c=Class.forName(session.getConfig("md5")); hash=(HASH)(c.newInstance()); } catch(Exception e){ System.err.println("getFingerPrint: "+e); } return Util.getFingerPrint(hash, getHostKey()); } byte[] getK(){ return K; } byte[] getH(){ return H; } HASH getHash(){ return sha; } byte[] getHostKey(){ return K_S; } /* * It seems JCE included in Oracle's Java7u6(and later) has suddenly changed * its behavior. The secrete generated by KeyAgreement#generateSecret() * may start with 0, even if it is a positive value. */ protected byte[] normalize(byte[] secret) { if(secret.length > 1 && secret[0] == 0 && (secret[1]&0x80) == 0) { byte[] tmp=new byte[secret.length-1]; System.arraycopy(secret, 1, tmp, 0, tmp.length); return normalize(tmp); } else { return secret; } } protected boolean verify(String alg, byte[] K_S, int index, byte[] sig_of_H) throws Exception { int i,j; i=index; boolean result=false; if(alg.equals("ssh-rsa")){ byte[] tmp; byte[] ee; byte[] n; type=RSA; key_alg_name=alg; j=((K_S[i++]<<24)&0xff000000)|((K_S[i++]<<16)&0x00ff0000)| ((K_S[i++]<<8)&0x0000ff00)|((K_S[i++])&0x000000ff); tmp=new byte[j]; System.arraycopy(K_S, i, tmp, 0, j); i+=j; ee=tmp; j=((K_S[i++]<<24)&0xff000000)|((K_S[i++]<<16)&0x00ff0000)| ((K_S[i++]<<8)&0x0000ff00)|((K_S[i++])&0x000000ff); tmp=new byte[j]; System.arraycopy(K_S, i, tmp, 0, j); i+=j; n=tmp; SignatureRSA sig=null; try{ Class c=Class.forName(session.getConfig("signature.rsa")); sig=(SignatureRSA)(c.newInstance()); sig.init(); } catch(Exception e){ System.err.println(e); } sig.setPubKey(ee, n); sig.update(H); result=sig.verify(sig_of_H); if(JSch.getLogger().isEnabled(Logger.INFO)){ JSch.getLogger().log(Logger.INFO, "ssh_rsa_verify: signature "+result); } } else if(alg.equals("ssh-dss")){ byte[] q=null; byte[] tmp; byte[] p; byte[] g; byte[] f; type=DSS; key_alg_name=alg; j=((K_S[i++]<<24)&0xff000000)|((K_S[i++]<<16)&0x00ff0000)| ((K_S[i++]<<8)&0x0000ff00)|((K_S[i++])&0x000000ff); tmp=new byte[j]; System.arraycopy(K_S, i, tmp, 0, j); i+=j; p=tmp; j=((K_S[i++]<<24)&0xff000000)|((K_S[i++]<<16)&0x00ff0000)| ((K_S[i++]<<8)&0x0000ff00)|((K_S[i++])&0x000000ff); tmp=new byte[j]; System.arraycopy(K_S, i, tmp, 0, j); i+=j; q=tmp; j=((K_S[i++]<<24)&0xff000000)|((K_S[i++]<<16)&0x00ff0000)| ((K_S[i++]<<8)&0x0000ff00)|((K_S[i++])&0x000000ff); tmp=new byte[j]; System.arraycopy(K_S, i, tmp, 0, j); i+=j; g=tmp; j=((K_S[i++]<<24)&0xff000000)|((K_S[i++]<<16)&0x00ff0000)| ((K_S[i++]<<8)&0x0000ff00)|((K_S[i++])&0x000000ff); tmp=new byte[j]; System.arraycopy(K_S, i, tmp, 0, j); i+=j; f=tmp; SignatureDSA sig=null; try{ Class c=Class.forName(session.getConfig("signature.dss")); sig=(SignatureDSA)(c.newInstance()); sig.init(); } catch(Exception e){ System.err.println(e); } sig.setPubKey(f, p, q, g); sig.update(H); result=sig.verify(sig_of_H); if(JSch.getLogger().isEnabled(Logger.INFO)){ JSch.getLogger().log(Logger.INFO, "ssh_dss_verify: signature "+result); } } else if(alg.equals("ecdsa-sha2-nistp256") || alg.equals("ecdsa-sha2-nistp384") || alg.equals("ecdsa-sha2-nistp521")) { byte[] tmp; byte[] r; byte[] s; // RFC 5656, type=ECDSA; key_alg_name=alg; j=((K_S[i++]<<24)&0xff000000)|((K_S[i++]<<16)&0x00ff0000)| ((K_S[i++]<<8)&0x0000ff00)|((K_S[i++])&0x000000ff); tmp=new byte[j]; System.arraycopy(K_S, i, tmp, 0, j); i+=j; j=((K_S[i++]<<24)&0xff000000)|((K_S[i++]<<16)&0x00ff0000)| ((K_S[i++]<<8)&0x0000ff00)|((K_S[i++])&0x000000ff); i++; tmp=new byte[(j-1)/2]; System.arraycopy(K_S, i, tmp, 0, tmp.length); i+=(j-1)/2; r=tmp; tmp=new byte[(j-1)/2]; System.arraycopy(K_S, i, tmp, 0, tmp.length); i+=(j-1)/2; s=tmp; SignatureECDSA sig=null; try{ Class c=Class.forName(session.getConfig("signature.ecdsa")); sig=(SignatureECDSA)(c.newInstance()); sig.init(); } catch(Exception e){ System.err.println(e); } sig.setPubKey(r, s); sig.update(H); result=sig.verify(sig_of_H); } else{ System.err.println("unknown alg"); } return result; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/UIKeyboardInteractive.java0000644000000000000000000000332312500205515023672 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public interface UIKeyboardInteractive{ String[] promptKeyboardInteractive(String destination, String name, String instruction, String[] prompt, boolean[] echo); } jsch-0.1.53/src/main/java/com/jcraft/jsch/HostKeyRepository.java0000644000000000000000000000626212500205067023173 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2004-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public interface HostKeyRepository{ final int OK=0; final int NOT_INCLUDED=1; final int CHANGED=2; /** * Checks if host is included with the key. * * @return #NOT_INCLUDED, #OK or #CHANGED * @see #NOT_INCLUDED * @see #OK * @see #CHANGED */ int check(String host, byte[] key); /** * Adds a host key hostkey * * @param hostkey a host key to be added * @param ui a user interface for showing messages or promping inputs. * @see UserInfo */ void add(HostKey hostkey, UserInfo ui); /** * Removes a host key if there exists mached key with * host, type. * * @see #remove(String host, String type, byte[] key) */ void remove(String host, String type); /** * Removes a host key if there exists a matched key with * host, type and key. */ void remove(String host, String type, byte[] key); /** * Returns id of this repository. * * @return identity in String */ String getKnownHostsRepositoryID(); /** * Retuns a list for host keys managed in this repository. * * @see #getHostKey(String host, String type) */ HostKey[] getHostKey(); /** * Retuns a list for host keys managed in this repository. * * @param host a hostname used in searching host keys. * If null is given, every host key will be listed. * @param type a key type used in searching host keys, * and it should be "ssh-dss" or "ssh-rsa". * If null is given, a key type type will not be ignored. */ HostKey[] getHostKey(String host, String type); } jsch-0.1.53/src/main/java/com/jcraft/jsch/DHG1.java0000644000000000000000000001507412500205007020163 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public class DHG1 extends KeyExchange{ static final byte[] g={ 2 }; static final byte[] p={ (byte)0x00, (byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF, (byte)0xC9,(byte)0x0F,(byte)0xDA,(byte)0xA2,(byte)0x21,(byte)0x68,(byte)0xC2,(byte)0x34, (byte)0xC4,(byte)0xC6,(byte)0x62,(byte)0x8B,(byte)0x80,(byte)0xDC,(byte)0x1C,(byte)0xD1, (byte)0x29,(byte)0x02,(byte)0x4E,(byte)0x08,(byte)0x8A,(byte)0x67,(byte)0xCC,(byte)0x74, (byte)0x02,(byte)0x0B,(byte)0xBE,(byte)0xA6,(byte)0x3B,(byte)0x13,(byte)0x9B,(byte)0x22, (byte)0x51,(byte)0x4A,(byte)0x08,(byte)0x79,(byte)0x8E,(byte)0x34,(byte)0x04,(byte)0xDD, (byte)0xEF,(byte)0x95,(byte)0x19,(byte)0xB3,(byte)0xCD,(byte)0x3A,(byte)0x43,(byte)0x1B, (byte)0x30,(byte)0x2B,(byte)0x0A,(byte)0x6D,(byte)0xF2,(byte)0x5F,(byte)0x14,(byte)0x37, (byte)0x4F,(byte)0xE1,(byte)0x35,(byte)0x6D,(byte)0x6D,(byte)0x51,(byte)0xC2,(byte)0x45, (byte)0xE4,(byte)0x85,(byte)0xB5,(byte)0x76,(byte)0x62,(byte)0x5E,(byte)0x7E,(byte)0xC6, (byte)0xF4,(byte)0x4C,(byte)0x42,(byte)0xE9,(byte)0xA6,(byte)0x37,(byte)0xED,(byte)0x6B, (byte)0x0B,(byte)0xFF,(byte)0x5C,(byte)0xB6,(byte)0xF4,(byte)0x06,(byte)0xB7,(byte)0xED, (byte)0xEE,(byte)0x38,(byte)0x6B,(byte)0xFB,(byte)0x5A,(byte)0x89,(byte)0x9F,(byte)0xA5, (byte)0xAE,(byte)0x9F,(byte)0x24,(byte)0x11,(byte)0x7C,(byte)0x4B,(byte)0x1F,(byte)0xE6, (byte)0x49,(byte)0x28,(byte)0x66,(byte)0x51,(byte)0xEC,(byte)0xE6,(byte)0x53,(byte)0x81, (byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF,(byte)0xFF }; private static final int SSH_MSG_KEXDH_INIT= 30; private static final int SSH_MSG_KEXDH_REPLY= 31; private int state; DH dh; byte[] V_S; byte[] V_C; byte[] I_S; byte[] I_C; byte[] e; private Buffer buf; private Packet packet; public void init(Session session, byte[] V_S, byte[] V_C, byte[] I_S, byte[] I_C) throws Exception{ this.session=session; this.V_S=V_S; this.V_C=V_C; this.I_S=I_S; this.I_C=I_C; try{ Class c=Class.forName(session.getConfig("sha-1")); sha=(HASH)(c.newInstance()); sha.init(); } catch(Exception e){ System.err.println(e); } buf=new Buffer(); packet=new Packet(buf); try{ Class c=Class.forName(session.getConfig("dh")); dh=(DH)(c.newInstance()); dh.init(); } catch(Exception e){ //System.err.println(e); throw e; } dh.setP(p); dh.setG(g); // The client responds with: // byte SSH_MSG_KEXDH_INIT(30) // mpint e <- g^x mod p // x is a random number (1 < x < (p-1)/2) e=dh.getE(); packet.reset(); buf.putByte((byte)SSH_MSG_KEXDH_INIT); buf.putMPInt(e); session.write(packet); if(JSch.getLogger().isEnabled(Logger.INFO)){ JSch.getLogger().log(Logger.INFO, "SSH_MSG_KEXDH_INIT sent"); JSch.getLogger().log(Logger.INFO, "expecting SSH_MSG_KEXDH_REPLY"); } state=SSH_MSG_KEXDH_REPLY; } public boolean next(Buffer _buf) throws Exception{ int i,j; switch(state){ case SSH_MSG_KEXDH_REPLY: // The server responds with: // byte SSH_MSG_KEXDH_REPLY(31) // string server public host key and certificates (K_S) // mpint f // string signature of H j=_buf.getInt(); j=_buf.getByte(); j=_buf.getByte(); if(j!=31){ System.err.println("type: must be 31 "+j); return false; } K_S=_buf.getString(); byte[] f=_buf.getMPInt(); byte[] sig_of_H=_buf.getString(); dh.setF(f); dh.checkRange(); K=normalize(dh.getK()); //The hash H is computed as the HASH hash of the concatenation of the //following: // string V_C, the client's version string (CR and NL excluded) // string V_S, the server's version string (CR and NL excluded) // string I_C, the payload of the client's SSH_MSG_KEXINIT // string I_S, the payload of the server's SSH_MSG_KEXINIT // string K_S, the host key // mpint e, exchange value sent by the client // mpint f, exchange value sent by the server // mpint K, the shared secret // This value is called the exchange hash, and it is used to authenti- // cate the key exchange. buf.reset(); buf.putString(V_C); buf.putString(V_S); buf.putString(I_C); buf.putString(I_S); buf.putString(K_S); buf.putMPInt(e); buf.putMPInt(f); buf.putMPInt(K); byte[] foo=new byte[buf.getLength()]; buf.getByte(foo); sha.update(foo, 0, foo.length); H=sha.digest(); //System.err.print("H -> "); //dump(H, 0, H.length); i=0; j=0; j=((K_S[i++]<<24)&0xff000000)|((K_S[i++]<<16)&0x00ff0000)| ((K_S[i++]<<8)&0x0000ff00)|((K_S[i++])&0x000000ff); String alg=Util.byte2str(K_S, i, j); i+=j; boolean result = verify(alg, K_S, i, sig_of_H); state=STATE_END; return result; } return false; } public int getState(){return state; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jgss/0000755000000000000000000000000012500206242017576 5ustar rootrootjsch-0.1.53/src/main/java/com/jcraft/jsch/jgss/GSSContextKrb5.java0000644000000000000000000001356212500206224023175 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2006-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jgss; import com.jcraft.jsch.JSchException; import java.net.InetAddress; import java.net.UnknownHostException; import org.ietf.jgss.GSSContext; import org.ietf.jgss.GSSCredential; import org.ietf.jgss.GSSException; import org.ietf.jgss.GSSManager; import org.ietf.jgss.GSSName; import org.ietf.jgss.MessageProp; import org.ietf.jgss.Oid; public class GSSContextKrb5 implements com.jcraft.jsch.GSSContext{ private static final String pUseSubjectCredsOnly = "javax.security.auth.useSubjectCredsOnly"; private static String useSubjectCredsOnly = getSystemProperty(pUseSubjectCredsOnly); private GSSContext context=null; public void create(String user, String host) throws JSchException{ try{ // RFC 1964 Oid krb5=new Oid("1.2.840.113554.1.2.2"); // Kerberos Principal Name Form Oid principalName=new Oid("1.2.840.113554.1.2.2.1"); GSSManager mgr=GSSManager.getInstance(); GSSCredential crd=null; /* try{ GSSName _user=mgr.createName(user, principalName); crd=mgr.createCredential(_user, GSSCredential.DEFAULT_LIFETIME, krb5, GSSCredential.INITIATE_ONLY); } catch(GSSException crdex){ } */ String cname=host; try{ cname=InetAddress.getByName(cname).getCanonicalHostName(); } catch(UnknownHostException e){ } GSSName _host=mgr.createName("host/"+cname, principalName); context=mgr.createContext(_host, krb5, crd, GSSContext.DEFAULT_LIFETIME); // RFC4462 3.4. GSS-API Session // // When calling GSS_Init_sec_context(), the client MUST set // integ_req_flag to "true" to request that per-message integrity // protection be supported for this context. In addition, // deleg_req_flag MAY be set to "true" to request access delegation, if // requested by the user. // // Since the user authentication process by its nature authenticates // only the client, the setting of mutual_req_flag is not needed for // this process. This flag SHOULD be set to "false". // TODO: OpenSSH's sshd does accepts 'false' for mutual_req_flag //context.requestMutualAuth(false); context.requestMutualAuth(true); context.requestConf(true); context.requestInteg(true); // for MIC context.requestCredDeleg(true); context.requestAnonymity(false); return; } catch(GSSException ex){ throw new JSchException(ex.toString()); } } public boolean isEstablished(){ return context.isEstablished(); } public byte[] init(byte[] token, int s, int l) throws JSchException { try{ // Without setting "javax.security.auth.useSubjectCredsOnly" to "false", // Sun's JVM for Un*x will show messages to stderr in // processing context.initSecContext(). // This hack is not thread safe ;-<. // If that property is explicitly given as "true" or "false", // this hack must not be invoked. if(useSubjectCredsOnly==null){ setSystemProperty(pUseSubjectCredsOnly, "false"); } return context.initSecContext(token, 0, l); } catch(GSSException ex){ throw new JSchException(ex.toString()); } catch(java.lang.SecurityException ex){ throw new JSchException(ex.toString()); } finally{ if(useSubjectCredsOnly==null){ // By the default, it must be "true". setSystemProperty(pUseSubjectCredsOnly, "true"); } } } public byte[] getMIC(byte[] message, int s, int l){ try{ MessageProp prop = new MessageProp(0, true); return context.getMIC(message, s, l, prop); } catch(GSSException ex){ return null; } } public void dispose(){ try{ context.dispose(); } catch(GSSException ex){ } } private static String getSystemProperty(String key){ try{ return System.getProperty(key); } catch(Exception e){ // We are not allowed to get the System properties. return null; } } private static void setSystemProperty(String key, String value){ try{ System.setProperty(key, value); } catch(Exception e){ // We are not allowed to set the System properties. } } } jsch-0.1.53/src/main/java/com/jcraft/jsch/ProxySOCKS4.java0000644000000000000000000001571012500205315021507 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2006-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ /* This file depends on following documents, - SOCKS: A protocol for TCP proxy across firewalls, Ying-Da Lee http://www.socks.nec.com/protocol/socks4.protocol */ package com.jcraft.jsch; import java.io.*; import java.net.*; public class ProxySOCKS4 implements Proxy{ private static int DEFAULTPORT=1080; private String proxy_host; private int proxy_port; private InputStream in; private OutputStream out; private Socket socket; private String user; private String passwd; public ProxySOCKS4(String proxy_host){ int port=DEFAULTPORT; String host=proxy_host; if(proxy_host.indexOf(':')!=-1){ try{ host=proxy_host.substring(0, proxy_host.indexOf(':')); port=Integer.parseInt(proxy_host.substring(proxy_host.indexOf(':')+1)); } catch(Exception e){ } } this.proxy_host=host; this.proxy_port=port; } public ProxySOCKS4(String proxy_host, int proxy_port){ this.proxy_host=proxy_host; this.proxy_port=proxy_port; } public void setUserPasswd(String user, String passwd){ this.user=user; this.passwd=passwd; } public void connect(SocketFactory socket_factory, String host, int port, int timeout) throws JSchException{ try{ if(socket_factory==null){ socket=Util.createSocket(proxy_host, proxy_port, timeout); //socket=new Socket(proxy_host, proxy_port); in=socket.getInputStream(); out=socket.getOutputStream(); } else{ socket=socket_factory.createSocket(proxy_host, proxy_port); in=socket_factory.getInputStream(socket); out=socket_factory.getOutputStream(socket); } if(timeout>0){ socket.setSoTimeout(timeout); } socket.setTcpNoDelay(true); byte[] buf=new byte[1024]; int index=0; /* 1) CONNECT The client connects to the SOCKS server and sends a CONNECT request when it wants to establish a connection to an application server. The client includes in the request packet the IP address and the port number of the destination host, and userid, in the following format. +----+----+----+----+----+----+----+----+----+----+....+----+ | VN | CD | DSTPORT | DSTIP | USERID |NULL| +----+----+----+----+----+----+----+----+----+----+....+----+ # of bytes: 1 1 2 4 variable 1 VN is the SOCKS protocol version number and should be 4. CD is the SOCKS command code and should be 1 for CONNECT request. NULL is a byte of all zero bits. */ index=0; buf[index++]=4; buf[index++]=1; buf[index++]=(byte)(port>>>8); buf[index++]=(byte)(port&0xff); try{ InetAddress addr=InetAddress.getByName(host); byte[] byteAddress = addr.getAddress(); for (int i = 0; i < byteAddress.length; i++) { buf[index++]=byteAddress[i]; } } catch(UnknownHostException uhe){ throw new JSchException("ProxySOCKS4: "+uhe.toString(), uhe); } if(user!=null){ System.arraycopy(Util.str2byte(user), 0, buf, index, user.length()); index+=user.length(); } buf[index++]=0; out.write(buf, 0, index); /* The SOCKS server checks to see whether such a request should be granted based on any combination of source IP address, destination IP address, destination port number, the userid, and information it may obtain by consulting IDENT, cf. RFC 1413. If the request is granted, the SOCKS server makes a connection to the specified port of the destination host. A reply packet is sent to the client when this connection is established, or when the request is rejected or the operation fails. +----+----+----+----+----+----+----+----+ | VN | CD | DSTPORT | DSTIP | +----+----+----+----+----+----+----+----+ # of bytes: 1 1 2 4 VN is the version of the reply code and should be 0. CD is the result code with one of the following values: 90: request granted 91: request rejected or failed 92: request rejected becasue SOCKS server cannot connect to identd on the client 93: request rejected because the client program and identd report different user-ids The remaining fields are ignored. */ int len=8; int s=0; while(sbsize){ byte[] tmp = new byte[bsize]; System.arraycopy(key, 0, tmp, 0, bsize); key = tmp; } SecretKeySpec skey = new SecretKeySpec(key, algorithm); mac = Mac.getInstance(algorithm); mac.init(skey); } private final byte[] tmp = new byte[4]; public void update(int i){ tmp[0] = (byte)(i>>>24); tmp[1] = (byte)(i>>>16); tmp[2] = (byte)(i>>>8); tmp[3] = (byte)i; update(tmp, 0, 4); } public void update(byte foo[], int s, int l){ mac.update(foo, s, l); } public void doFinal(byte[] buf, int offset){ try{ mac.doFinal(buf, offset); } catch(ShortBufferException e){ System.err.println(e); } } public String getName(){ return name; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/ARCFOUR128.java0000644000000000000000000000543512500205655021606 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2008-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import com.jcraft.jsch.Cipher; import javax.crypto.*; import javax.crypto.spec.*; public class ARCFOUR128 implements Cipher{ private static final int ivsize=8; private static final int bsize=16; private static final int skip=1536; private javax.crypto.Cipher cipher; public int getIVSize(){return ivsize;} public int getBlockSize(){return bsize;} public void init(int mode, byte[] key, byte[] iv) throws Exception{ byte[] tmp; if(key.length>bsize){ tmp=new byte[bsize]; System.arraycopy(key, 0, tmp, 0, tmp.length); key=tmp; } try{ cipher=javax.crypto.Cipher.getInstance("RC4"); SecretKeySpec _key = new SecretKeySpec(key, "RC4"); synchronized(javax.crypto.Cipher.class){ cipher.init((mode==ENCRYPT_MODE? javax.crypto.Cipher.ENCRYPT_MODE: javax.crypto.Cipher.DECRYPT_MODE), _key); } byte[] foo=new byte[1]; for(int i=0; iivsize){ tmp=new byte[ivsize]; System.arraycopy(iv, 0, tmp, 0, tmp.length); iv=tmp; } if(key.length>bsize){ tmp=new byte[bsize]; System.arraycopy(key, 0, tmp, 0, tmp.length); key=tmp; } try{ SecretKeySpec skeySpec = new SecretKeySpec(key, "Blowfish"); cipher=javax.crypto.Cipher.getInstance("Blowfish/CBC/"+pad); synchronized(javax.crypto.Cipher.class){ cipher.init((mode==ENCRYPT_MODE? javax.crypto.Cipher.ENCRYPT_MODE: javax.crypto.Cipher.DECRYPT_MODE), skeySpec, new IvParameterSpec(iv)); } } catch(Exception e){ throw e; } } public void update(byte[] foo, int s1, int len, byte[] bar, int s2) throws Exception{ cipher.update(foo, s1, len, bar, s2); } public boolean isCBC(){return true; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/SignatureECDSA.java0000644000000000000000000001377112501675356022767 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import java.math.BigInteger; import java.security.*; import java.security.spec.*; import com.jcraft.jsch.Buffer; public class SignatureECDSA implements com.jcraft.jsch.SignatureECDSA { Signature signature; KeyFactory keyFactory; public void init() throws Exception{ signature=java.security.Signature.getInstance("SHA256withECDSA"); keyFactory=KeyFactory.getInstance("EC"); } public void setPubKey(byte[] r, byte[] s) throws Exception{ // r and s must be unsigned values. r=insert0(r); s=insert0(s); String name="secp256r1"; if(r.length>=64) name="secp521r1"; else if(r.length>=48) name="secp384r1"; AlgorithmParameters param = AlgorithmParameters.getInstance("EC"); param.init(new ECGenParameterSpec(name)); ECParameterSpec ecparam = (ECParameterSpec)param.getParameterSpec(ECParameterSpec.class); ECPoint w = new ECPoint(new BigInteger(1, r), new BigInteger(1, s)); PublicKey pubKey = keyFactory.generatePublic(new ECPublicKeySpec(w, ecparam)); signature.initVerify(pubKey); } public void setPrvKey(byte[] d) throws Exception{ // d must be unsigned value. d=insert0(d); String name="secp256r1"; if(d.length>=64) name="secp521r1"; else if(d.length>=48) name="secp384r1"; AlgorithmParameters param = AlgorithmParameters.getInstance("EC"); param.init(new ECGenParameterSpec(name)); ECParameterSpec ecparam = (ECParameterSpec)param.getParameterSpec(ECParameterSpec.class); BigInteger _d = new BigInteger(1, d); PrivateKey prvKey = keyFactory.generatePrivate(new ECPrivateKeySpec(_d, ecparam)); signature.initSign(prvKey); } public byte[] sign() throws Exception{ byte[] sig=signature.sign(); // It seems that the output from SunEC is in ASN.1, // so we have to convert it. if(sig[0]==0x30 && // in ASN.1 ((sig[1]+2 == sig.length) || ((sig[1]&0x80)!=0 && (sig[2]&0xff)+3==sig.length))){// 2bytes for len int index=3; if((sig[1]&0x80)!=0 && (sig[2]&0xff)+3==sig.length) index=4; byte[] r = new byte[sig[index]]; byte[] s = new byte[sig[index+2+sig[index]]]; System.arraycopy(sig, index+1, r, 0, r.length); System.arraycopy(sig, index+3+sig[index], s, 0, s.length); r = chop0(r); s = chop0(s); Buffer buf = new Buffer(); buf.putMPInt(r); buf.putMPInt(s); sig=new byte[buf.getLength()]; buf.setOffSet(0); buf.getByte(sig); } return sig; } public void update(byte[] foo) throws Exception{ signature.update(foo); } public boolean verify(byte[] sig) throws Exception{ // It seems that SunEC expects ASN.1 data, // so we have to convert it. if(!(sig[0]==0x30 && // not in ASN.1 ((sig[1]+2 == sig.length) || ((sig[1]&0x80)!=0 && (sig[2]&0xff)+3==sig.length)))) { Buffer b = new Buffer(sig); b.getString(); // ecdsa-sha2-nistp256 b.getInt(); byte[] r = b.getMPInt(); byte[] s = b.getMPInt(); r=insert0(r); s=insert0(s); byte[] asn1 = null; if(r.length<64){ asn1 = new byte[6+r.length+s.length]; asn1[0] = (byte)0x30; asn1[1] = (byte)(4+r.length+s.length); asn1[2] = (byte)0x02; asn1[3] = (byte)r.length; System.arraycopy(r, 0, asn1, 4, r.length); asn1[r.length+4] = (byte)0x02; asn1[r.length+5] = (byte)s.length; System.arraycopy(s, 0, asn1, (6+r.length), s.length); } else { asn1 = new byte[6+r.length+s.length+1]; asn1[0] = (byte)0x30; asn1[1] = (byte)0x81; asn1[2] = (byte)(4+r.length+s.length); asn1[3] = (byte)0x02; asn1[4] = (byte)r.length; System.arraycopy(r, 0, asn1, 5, r.length); asn1[r.length+5] = (byte)0x02; asn1[r.length+6] = (byte)s.length; System.arraycopy(s, 0, asn1, (7+r.length), s.length); } sig=asn1; } return signature.verify(sig); } private byte[] insert0(byte[] buf){ if ((buf[0] & 0x80) == 0) return buf; byte[] tmp = new byte[buf.length+1]; System.arraycopy(buf, 0, tmp, 1, buf.length); bzero(buf); return tmp; } private byte[] chop0(byte[] buf){ if(buf[0]!=0) return buf; byte[] tmp = new byte[buf.length-1]; System.arraycopy(buf, 1, tmp, 0, tmp.length); bzero(buf); return tmp; } private void bzero(byte[] buf){ for(int i = 0; ibsize){ tmp=new byte[bsize]; System.arraycopy(key, 0, tmp, 0, tmp.length); key=tmp; } try{ cipher=javax.crypto.Cipher.getInstance("RC4"); SecretKeySpec _key = new SecretKeySpec(key, "RC4"); synchronized(javax.crypto.Cipher.class){ cipher.init((mode==ENCRYPT_MODE? javax.crypto.Cipher.ENCRYPT_MODE: javax.crypto.Cipher.DECRYPT_MODE), _key); } byte[] foo=new byte[1]; for(int i=0; itmp.length){ tmp=new byte[len]; } random.nextBytes(tmp); System.arraycopy(tmp, 0, foo, start, len); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/HMACSHA196.java0000644000000000000000000000352512500205743021552 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; public class HMACSHA196 extends HMACSHA1 { public HMACSHA196(){ name = "hmac-sha1-96"; } public int getBlockSize(){ return 12; }; private final byte[] _buf20 = new byte[20]; public void doFinal(byte[] buf, int offset){ super.doFinal(_buf20, 0); System.arraycopy(_buf20, 0, buf, offset, 12); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/ECDH384.java0000664000000000000000000000322112477533373021223 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; public class ECDH384 extends ECDHN implements com.jcraft.jsch.ECDH { public void init() throws Exception { super.init(384); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/KeyPairGenRSA.java0000644000000000000000000000562412500205772022616 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import java.security.*; import java.security.interfaces.*; public class KeyPairGenRSA implements com.jcraft.jsch.KeyPairGenRSA{ byte[] d; // private byte[] e; // public byte[] n; byte[] c; // coefficient byte[] ep; // exponent p byte[] eq; // exponent q byte[] p; // prime p byte[] q; // prime q public void init(int key_size) throws Exception{ KeyPairGenerator keyGen = KeyPairGenerator.getInstance("RSA"); keyGen.initialize(key_size, new SecureRandom()); KeyPair pair = keyGen.generateKeyPair(); PublicKey pubKey=pair.getPublic(); PrivateKey prvKey=pair.getPrivate(); d=((RSAPrivateKey)prvKey).getPrivateExponent().toByteArray(); e=((RSAPublicKey)pubKey).getPublicExponent().toByteArray(); n=((RSAPrivateKey)prvKey).getModulus().toByteArray(); c=((RSAPrivateCrtKey)prvKey).getCrtCoefficient().toByteArray(); ep=((RSAPrivateCrtKey)prvKey).getPrimeExponentP().toByteArray(); eq=((RSAPrivateCrtKey)prvKey).getPrimeExponentQ().toByteArray(); p=((RSAPrivateCrtKey)prvKey).getPrimeP().toByteArray(); q=((RSAPrivateCrtKey)prvKey).getPrimeQ().toByteArray(); } public byte[] getD(){return d;} public byte[] getE(){return e;} public byte[] getN(){return n;} public byte[] getC(){return c;} public byte[] getEP(){return ep;} public byte[] getEQ(){return eq;} public byte[] getP(){return p;} public byte[] getQ(){return q;} } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/AES128CTR.java0000644000000000000000000000546512500205620021461 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2008-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import com.jcraft.jsch.Cipher; import javax.crypto.spec.*; public class AES128CTR implements Cipher{ private static final int ivsize=16; private static final int bsize=16; private javax.crypto.Cipher cipher; public int getIVSize(){return ivsize;} public int getBlockSize(){return bsize;} public void init(int mode, byte[] key, byte[] iv) throws Exception{ String pad="NoPadding"; byte[] tmp; if(iv.length>ivsize){ tmp=new byte[ivsize]; System.arraycopy(iv, 0, tmp, 0, tmp.length); iv=tmp; } if(key.length>bsize){ tmp=new byte[bsize]; System.arraycopy(key, 0, tmp, 0, tmp.length); key=tmp; } try{ SecretKeySpec keyspec=new SecretKeySpec(key, "AES"); cipher=javax.crypto.Cipher.getInstance("AES/CTR/"+pad); synchronized(javax.crypto.Cipher.class){ cipher.init((mode==ENCRYPT_MODE? javax.crypto.Cipher.ENCRYPT_MODE: javax.crypto.Cipher.DECRYPT_MODE), keyspec, new IvParameterSpec(iv)); } } catch(Exception e){ cipher=null; throw e; } } public void update(byte[] foo, int s1, int len, byte[] bar, int s2) throws Exception{ cipher.update(foo, s1, len, bar, s2); } public boolean isCBC(){return false; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/AES256CTR.java0000644000000000000000000000546312500205643021466 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2008-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import com.jcraft.jsch.Cipher; import javax.crypto.spec.*; public class AES256CTR implements Cipher{ private static final int ivsize=16; private static final int bsize=32; private javax.crypto.Cipher cipher; public int getIVSize(){return ivsize;} public int getBlockSize(){return bsize;} public void init(int mode, byte[] key, byte[] iv) throws Exception{ String pad="NoPadding"; byte[] tmp; if(iv.length>ivsize){ tmp=new byte[ivsize]; System.arraycopy(iv, 0, tmp, 0, tmp.length); iv=tmp; } if(key.length>bsize){ tmp=new byte[bsize]; System.arraycopy(key, 0, tmp, 0, tmp.length); key=tmp; } try{ SecretKeySpec keyspec=new SecretKeySpec(key, "AES"); cipher=javax.crypto.Cipher.getInstance("AES/CTR/"+pad); synchronized(javax.crypto.Cipher.class){ cipher.init((mode==ENCRYPT_MODE? javax.crypto.Cipher.ENCRYPT_MODE: javax.crypto.Cipher.DECRYPT_MODE), keyspec, new IvParameterSpec(iv)); } } catch(Exception e){ cipher=null; throw e; } } public void update(byte[] foo, int s1, int len, byte[] bar, int s2) throws Exception{ cipher.update(foo, s1, len, bar, s2); } public boolean isCBC(){return false; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/HMACMD596.java0000644000000000000000000000351612500205731021440 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; public class HMACMD596 extends HMACMD5 { public HMACMD596(){ name="hmac-md5-96"; } public int getBlockSize(){ return 12; }; private final byte[] _buf16 = new byte[16]; public void doFinal(byte[] buf, int offset){ super.doFinal(_buf16, 0); System.arraycopy(_buf16, 0, buf, offset, 12); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/HMACMD5.java0000644000000000000000000000333512500205724021262 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import com.jcraft.jsch.MAC; import javax.crypto.*; import javax.crypto.spec.*; public class HMACMD5 extends HMAC { public HMACMD5(){ name = "hmac-md5"; bsize = 16; algorithm = "HmacMD5"; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/PBKDF.java0000644000000000000000000000451612500206005021065 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2013-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import com.jcraft.jsch.HASH; import javax.crypto.spec.PBEKeySpec; import javax.crypto.SecretKeyFactory; import java.security.spec.InvalidKeySpecException; import java.security.NoSuchAlgorithmException; public class PBKDF implements com.jcraft.jsch.PBKDF{ public byte[] getKey(byte[] _pass, byte[] salt, int iterations, int size){ char[] pass=new char[_pass.length]; for(int i = 0; i < _pass.length; i++){ pass[i]=(char)(_pass[i]&0xff); } try { PBEKeySpec spec = new PBEKeySpec(pass, salt, iterations, size*8); SecretKeyFactory skf = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA1"); byte[] key = skf.generateSecret(spec).getEncoded(); return key; } catch(InvalidKeySpecException e){ } catch(NoSuchAlgorithmException e){ } return null; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/HMACSHA512.java0000644000000000000000000000323312500205755021541 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2012-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; public class HMACSHA512 extends HMAC { public HMACSHA512(){ name = "hmac-sha2-512"; bsize = 64; algorithm = "HmacSHA512"; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/SHA512.java0000664000000000000000000000374412500206114021107 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import java.security.*; public class SHA512 implements com.jcraft.jsch.HASH { MessageDigest md; public int getBlockSize(){return 64;} public void init() throws Exception { try{ md=MessageDigest.getInstance("SHA-512"); } catch(Exception e){ System.err.println(e); } } public void update(byte[] foo, int start, int len) throws Exception { md.update(foo, start, len); } public byte[] digest() throws Exception { return md.digest(); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/TripleDESCBC.java0000644000000000000000000000642012500206141022337 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import com.jcraft.jsch.Cipher; import javax.crypto.*; import javax.crypto.spec.*; public class TripleDESCBC implements Cipher{ private static final int ivsize=8; private static final int bsize=24; private javax.crypto.Cipher cipher; public int getIVSize(){return ivsize;} public int getBlockSize(){return bsize;} public void init(int mode, byte[] key, byte[] iv) throws Exception{ String pad="NoPadding"; //if(padding) pad="PKCS5Padding"; byte[] tmp; if(iv.length>ivsize){ tmp=new byte[ivsize]; System.arraycopy(iv, 0, tmp, 0, tmp.length); iv=tmp; } if(key.length>bsize){ tmp=new byte[bsize]; System.arraycopy(key, 0, tmp, 0, tmp.length); key=tmp; } try{ cipher=javax.crypto.Cipher.getInstance("DESede/CBC/"+pad); /* // The following code does not work on IBM's JDK 1.4.1 SecretKeySpec skeySpec = new SecretKeySpec(key, "DESede"); cipher.init((mode==ENCRYPT_MODE? javax.crypto.Cipher.ENCRYPT_MODE: javax.crypto.Cipher.DECRYPT_MODE), skeySpec, new IvParameterSpec(iv)); */ DESedeKeySpec keyspec=new DESedeKeySpec(key); SecretKeyFactory keyfactory=SecretKeyFactory.getInstance("DESede"); SecretKey _key=keyfactory.generateSecret(keyspec); synchronized(javax.crypto.Cipher.class){ cipher.init((mode==ENCRYPT_MODE? javax.crypto.Cipher.ENCRYPT_MODE: javax.crypto.Cipher.DECRYPT_MODE), _key, new IvParameterSpec(iv)); } } catch(Exception e){ cipher=null; throw e; } } public void update(byte[] foo, int s1, int len, byte[] bar, int s2) throws Exception{ cipher.update(foo, s1, len, bar, s2); } public boolean isCBC(){return true; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/TripleDESCTR.java0000644000000000000000000000642112500206146022406 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2008-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import com.jcraft.jsch.Cipher; import javax.crypto.*; import javax.crypto.spec.*; public class TripleDESCTR implements Cipher{ private static final int ivsize=8; private static final int bsize=24; private javax.crypto.Cipher cipher; public int getIVSize(){return ivsize;} public int getBlockSize(){return bsize;} public void init(int mode, byte[] key, byte[] iv) throws Exception{ String pad="NoPadding"; //if(padding) pad="PKCS5Padding"; byte[] tmp; if(iv.length>ivsize){ tmp=new byte[ivsize]; System.arraycopy(iv, 0, tmp, 0, tmp.length); iv=tmp; } if(key.length>bsize){ tmp=new byte[bsize]; System.arraycopy(key, 0, tmp, 0, tmp.length); key=tmp; } try{ cipher=javax.crypto.Cipher.getInstance("DESede/CTR/"+pad); /* // The following code does not work on IBM's JDK 1.4.1 SecretKeySpec skeySpec = new SecretKeySpec(key, "DESede"); cipher.init((mode==ENCRYPT_MODE? javax.crypto.Cipher.ENCRYPT_MODE: javax.crypto.Cipher.DECRYPT_MODE), skeySpec, new IvParameterSpec(iv)); */ DESedeKeySpec keyspec=new DESedeKeySpec(key); SecretKeyFactory keyfactory=SecretKeyFactory.getInstance("DESede"); SecretKey _key=keyfactory.generateSecret(keyspec); synchronized(javax.crypto.Cipher.class){ cipher.init((mode==ENCRYPT_MODE? javax.crypto.Cipher.ENCRYPT_MODE: javax.crypto.Cipher.DECRYPT_MODE), _key, new IvParameterSpec(iv)); } } catch(Exception e){ cipher=null; throw e; } } public void update(byte[] foo, int s1, int len, byte[] bar, int s2) throws Exception{ cipher.update(foo, s1, len, bar, s2); } public boolean isCBC(){return false; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/ECDH256.java0000664000000000000000000000322112477533277021224 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; public class ECDH256 extends ECDHN implements com.jcraft.jsch.ECDH { public void init() throws Exception { super.init(256); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/SHA256.java0000644000000000000000000000376712500206025021120 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import com.jcraft.jsch.HASH; import java.security.*; public class SHA256 implements HASH { MessageDigest md; public int getBlockSize(){return 32;} public void init() throws Exception { try{ md=MessageDigest.getInstance("SHA-256"); } catch(Exception e){ System.err.println(e); } } public void update(byte[] foo, int start, int len) throws Exception { md.update(foo, start, len); } public byte[] digest() throws Exception { return md.digest(); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/DH.java0000644000000000000000000000725612501677020020550 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import java.math.BigInteger; import java.security.*; import javax.crypto.*; import javax.crypto.spec.*; import com.jcraft.jsch.JSchException; public class DH implements com.jcraft.jsch.DH{ BigInteger p; BigInteger g; BigInteger e; // my public key byte[] e_array; BigInteger f; // your public key BigInteger K; // shared secret key byte[] K_array; private KeyPairGenerator myKpairGen; private KeyAgreement myKeyAgree; public void init() throws Exception{ myKpairGen=KeyPairGenerator.getInstance("DH"); myKeyAgree=KeyAgreement.getInstance("DH"); } public byte[] getE() throws Exception{ if(e==null){ DHParameterSpec dhSkipParamSpec=new DHParameterSpec(p, g); myKpairGen.initialize(dhSkipParamSpec); KeyPair myKpair=myKpairGen.generateKeyPair(); myKeyAgree.init(myKpair.getPrivate()); e=((javax.crypto.interfaces.DHPublicKey)(myKpair.getPublic())).getY(); e_array=e.toByteArray(); } return e_array; } public byte[] getK() throws Exception{ if(K==null){ KeyFactory myKeyFac=KeyFactory.getInstance("DH"); DHPublicKeySpec keySpec=new DHPublicKeySpec(f, p, g); PublicKey yourPubKey=myKeyFac.generatePublic(keySpec); myKeyAgree.doPhase(yourPubKey, true); byte[] mySharedSecret=myKeyAgree.generateSecret(); K=new BigInteger(1, mySharedSecret); K_array=K.toByteArray(); K_array=mySharedSecret; } return K_array; } public void setP(byte[] p){ setP(new BigInteger(1, p)); } public void setG(byte[] g){ setG(new BigInteger(1, g)); } public void setF(byte[] f){ setF(new BigInteger(1, f)); } void setP(BigInteger p){this.p=p;} void setG(BigInteger g){this.g=g;} void setF(BigInteger f){this.f=f;} // e, f must be in [1, p-1]. public void checkRange() throws Exception { /* checkRange(e); checkRange(f); */ } private void checkRange(BigInteger tmp) throws Exception { BigInteger one = BigInteger.ONE; BigInteger p_1 = p.subtract(one); // !(1ivsize){ tmp=new byte[ivsize]; System.arraycopy(iv, 0, tmp, 0, tmp.length); iv=tmp; } if(key.length>bsize){ tmp=new byte[bsize]; System.arraycopy(key, 0, tmp, 0, tmp.length); key=tmp; } try{ SecretKeySpec keyspec=new SecretKeySpec(key, "AES"); cipher=javax.crypto.Cipher.getInstance("AES/CTR/"+pad); synchronized(javax.crypto.Cipher.class){ cipher.init((mode==ENCRYPT_MODE? javax.crypto.Cipher.ENCRYPT_MODE: javax.crypto.Cipher.DECRYPT_MODE), keyspec, new IvParameterSpec(iv)); } } catch(Exception e){ cipher=null; throw e; } } public void update(byte[] foo, int s1, int len, byte[] bar, int s2) throws Exception{ cipher.update(foo, s1, len, bar, s2); } public boolean isCBC(){return false; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/AES128CBC.java0000644000000000000000000000546412500205613021421 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2005-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import com.jcraft.jsch.Cipher; import javax.crypto.spec.*; public class AES128CBC implements Cipher{ private static final int ivsize=16; private static final int bsize=16; private javax.crypto.Cipher cipher; public int getIVSize(){return ivsize;} public int getBlockSize(){return bsize;} public void init(int mode, byte[] key, byte[] iv) throws Exception{ String pad="NoPadding"; byte[] tmp; if(iv.length>ivsize){ tmp=new byte[ivsize]; System.arraycopy(iv, 0, tmp, 0, tmp.length); iv=tmp; } if(key.length>bsize){ tmp=new byte[bsize]; System.arraycopy(key, 0, tmp, 0, tmp.length); key=tmp; } try{ SecretKeySpec keyspec=new SecretKeySpec(key, "AES"); cipher=javax.crypto.Cipher.getInstance("AES/CBC/"+pad); synchronized(javax.crypto.Cipher.class){ cipher.init((mode==ENCRYPT_MODE? javax.crypto.Cipher.ENCRYPT_MODE: javax.crypto.Cipher.DECRYPT_MODE), keyspec, new IvParameterSpec(iv)); } } catch(Exception e){ cipher=null; throw e; } } public void update(byte[] foo, int s1, int len, byte[] bar, int s2) throws Exception{ cipher.update(foo, s1, len, bar, s2); } public boolean isCBC(){return true; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/AES192CBC.java0000644000000000000000000000546212500205625021423 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2005-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import com.jcraft.jsch.Cipher; import javax.crypto.spec.*; public class AES192CBC implements Cipher{ private static final int ivsize=16; private static final int bsize=24; private javax.crypto.Cipher cipher; public int getIVSize(){return ivsize;} public int getBlockSize(){return bsize;} public void init(int mode, byte[] key, byte[] iv) throws Exception{ String pad="NoPadding"; byte[] tmp; if(iv.length>ivsize){ tmp=new byte[ivsize]; System.arraycopy(iv, 0, tmp, 0, tmp.length); iv=tmp; } if(key.length>bsize){ tmp=new byte[bsize]; System.arraycopy(key, 0, tmp, 0, tmp.length); key=tmp; } try{ SecretKeySpec keyspec=new SecretKeySpec(key, "AES"); cipher=javax.crypto.Cipher.getInstance("AES/CBC/"+pad); synchronized(javax.crypto.Cipher.class){ cipher.init((mode==ENCRYPT_MODE? javax.crypto.Cipher.ENCRYPT_MODE: javax.crypto.Cipher.DECRYPT_MODE), keyspec, new IvParameterSpec(iv)); } } catch(Exception e){ cipher=null; throw e; } } public void update(byte[] foo, int s1, int len, byte[] bar, int s2) throws Exception{ cipher.update(foo, s1, len, bar, s2); } public boolean isCBC(){return true; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/AES256CBC.java0000644000000000000000000000546212500205636021426 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2005-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import com.jcraft.jsch.Cipher; import javax.crypto.spec.*; public class AES256CBC implements Cipher{ private static final int ivsize=16; private static final int bsize=32; private javax.crypto.Cipher cipher; public int getIVSize(){return ivsize;} public int getBlockSize(){return bsize;} public void init(int mode, byte[] key, byte[] iv) throws Exception{ String pad="NoPadding"; byte[] tmp; if(iv.length>ivsize){ tmp=new byte[ivsize]; System.arraycopy(iv, 0, tmp, 0, tmp.length); iv=tmp; } if(key.length>bsize){ tmp=new byte[bsize]; System.arraycopy(key, 0, tmp, 0, tmp.length); key=tmp; } try{ SecretKeySpec keyspec=new SecretKeySpec(key, "AES"); cipher=javax.crypto.Cipher.getInstance("AES/CBC/"+pad); synchronized(javax.crypto.Cipher.class){ cipher.init((mode==ENCRYPT_MODE? javax.crypto.Cipher.ENCRYPT_MODE: javax.crypto.Cipher.DECRYPT_MODE), keyspec, new IvParameterSpec(iv)); } } catch(Exception e){ cipher=null; throw e; } } public void update(byte[] foo, int s1, int len, byte[] bar, int s2) throws Exception{ cipher.update(foo, s1, len, bar, s2); } public boolean isCBC(){return true; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/MD5.java0000644000000000000000000000375412500205777020646 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import com.jcraft.jsch.HASH; import java.security.*; public class MD5 implements HASH{ MessageDigest md; public int getBlockSize(){return 16;} public void init() throws Exception{ try{ md=MessageDigest.getInstance("MD5"); } catch(Exception e){ System.err.println(e); } } public void update(byte[] foo, int start, int len) throws Exception{ md.update(foo, start, len); } public byte[] digest() throws Exception{ return md.digest(); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/SHA1.java0000644000000000000000000000375712500206020020736 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import com.jcraft.jsch.HASH; import java.security.*; public class SHA1 implements HASH{ MessageDigest md; public int getBlockSize(){return 20;} public void init() throws Exception{ try{ md=MessageDigest.getInstance("SHA-1"); } catch(Exception e){ System.err.println(e); } } public void update(byte[] foo, int start, int len) throws Exception{ md.update(foo, start, len); } public byte[] digest() throws Exception{ return md.digest(); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/HMACSHA1.java0000644000000000000000000000322112500205736021366 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; public class HMACSHA1 extends HMAC { public HMACSHA1(){ name = "hmac-sha1"; bsize = 20; algorithm = "HmacSHA1"; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/ARCFOUR.java0000644000000000000000000000522712500205650021345 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2008-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import com.jcraft.jsch.Cipher; import javax.crypto.*; import javax.crypto.spec.*; public class ARCFOUR implements Cipher{ private static final int ivsize=8; private static final int bsize=16; private javax.crypto.Cipher cipher; public int getIVSize(){return ivsize;} public int getBlockSize(){return bsize;} public void init(int mode, byte[] key, byte[] iv) throws Exception{ String pad="NoPadding"; byte[] tmp; if(key.length>bsize){ tmp=new byte[bsize]; System.arraycopy(key, 0, tmp, 0, tmp.length); key=tmp; } try{ cipher=javax.crypto.Cipher.getInstance("RC4"); SecretKeySpec _key = new SecretKeySpec(key, "RC4"); synchronized(javax.crypto.Cipher.class){ cipher.init((mode==ENCRYPT_MODE? javax.crypto.Cipher.ENCRYPT_MODE: javax.crypto.Cipher.DECRYPT_MODE), _key); } } catch(Exception e){ cipher=null; throw e; } } public void update(byte[] foo, int s1, int len, byte[] bar, int s2) throws Exception{ cipher.update(foo, s1, len, bar, s2); } public boolean isCBC(){return false; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/jce/ECDHN.java0000664000000000000000000001175612500205711021071 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch.jce; import java.math.BigInteger; import java.security.*; import javax.crypto.*; import java.security.spec.*; import java.security.interfaces.*; public class ECDHN implements com.jcraft.jsch.ECDH { byte[] Q_array; ECPublicKey publicKey; private KeyAgreement myKeyAgree; public void init(int size) throws Exception{ myKeyAgree = KeyAgreement.getInstance("ECDH"); KeyPairGenECDSA kpair = new KeyPairGenECDSA(); kpair.init(size); publicKey = kpair.getPublicKey(); byte[] r = kpair.getR(); byte[] s = kpair.getS(); Q_array = toPoint(r, s); myKeyAgree.init(kpair.getPrivateKey()); } public byte[] getQ() throws Exception{ return Q_array; } public byte[] getSecret(byte[] r, byte[] s) throws Exception{ KeyFactory kf = KeyFactory.getInstance("EC"); ECPoint w = new ECPoint(new BigInteger(1, r), new BigInteger(1, s)); ECPublicKeySpec spec = new ECPublicKeySpec(w, publicKey.getParams()); PublicKey theirPublicKey = kf.generatePublic(spec); myKeyAgree.doPhase(theirPublicKey, true); return myKeyAgree.generateSecret(); } private static BigInteger two = BigInteger.ONE.add(BigInteger.ONE); private static BigInteger three = two.add(BigInteger.ONE); // SEC 1: Elliptic Curve Cryptography, Version 2.0 // http://www.secg.org/sec1-v2.pdf // 3.2.2.1 Elliptic Curve Public Key Validation Primitive public boolean validate(byte[] r, byte[] s) throws Exception{ BigInteger x = new BigInteger(1, r); BigInteger y = new BigInteger(1, s); // Step.1 // Check that Q != O ECPoint w = new ECPoint(x, y); if(w.equals(ECPoint.POINT_INFINITY)){ return false; } // Step.2 // If T represents elliptic curve domain parameters over Fp, // check that xQ and yQ are integers in the interval [0, p-1], // and that: // y^2 = x^3 + x*a + b (mod p) ECParameterSpec params = publicKey.getParams(); EllipticCurve curve = params.getCurve(); BigInteger p=((ECFieldFp)curve.getField()).getP(); //nistp should be Fp. // xQ and yQ should be integers in the interval [0, p-1] BigInteger p_sub1=p.subtract(BigInteger.ONE); if(!(x.compareTo(p_sub1)<=0 && y.compareTo(p_sub1)<=0)){ return false; } // y^2 = x^3 + x*a + b (mod p) BigInteger tmp=x.multiply(curve.getA()). add(curve.getB()). add(x.modPow(three, p)). mod(p); BigInteger y_2=y.modPow(two, p); if(!(y_2.equals(tmp))){ return false; } // Step.3 // Check that nQ = O. // Unfortunately, JCE does not provide the point multiplication method. /* if(!w.multiply(params.getOrder()).equals(ECPoint.POINT_INFINITY)){ return false; } */ return true; } private byte[] toPoint(byte[] r_array, byte[] s_array) { byte[] tmp = new byte[1+r_array.length+s_array.length]; tmp[0]=0x04; System.arraycopy(r_array, 0, tmp, 1, r_array.length); System.arraycopy(s_array, 0, tmp, 1+r_array.length, s_array.length); return tmp; } private byte[] insert0(byte[] buf){ if ((buf[0] & 0x80) == 0) return buf; byte[] tmp = new byte[buf.length+1]; System.arraycopy(buf, 0, tmp, 1, buf.length); bzero(buf); return tmp; } private byte[] chop0(byte[] buf){ if(buf[0]!=0) return buf; byte[] tmp = new byte[buf.length-1]; System.arraycopy(buf, 1, tmp, 0, tmp.length); bzero(buf); return tmp; } private void bzero(byte[] buf){ for(int i = 0; i "); dump(H, 0, H.length); i=0; j=0; j=((K_S[i++]<<24)&0xff000000)|((K_S[i++]<<16)&0x00ff0000)| ((K_S[i++]<<8)&0x0000ff00)|((K_S[i++])&0x000000ff); String alg=Util.byte2str(K_S, i, j); i+=j; boolean result = verify(alg, K_S, i, sig_of_H); state=STATE_END; return result; } return false; } public int getState(){return state; } protected int check2048(Class c, int _max) throws Exception { DH dh=(com.jcraft.jsch.DH)(c.newInstance()); dh.init(); byte[] foo = new byte[257]; foo[1]=(byte)0xdd; foo[256]=0x73; dh.setP(foo); byte[] bar = {(byte)0x02}; dh.setG(bar); try { dh.getE(); _max=2048; } catch(Exception e){ } return _max; } } jsch-0.1.53/src/main/java/com/jcraft/jsch/Packet.java0000644000000000000000000000701612500205270020706 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public class Packet{ private static Random random=null; static void setRandom(Random foo){ random=foo;} Buffer buffer; byte[] ba4=new byte[4]; public Packet(Buffer buffer){ this.buffer=buffer; } public void reset(){ buffer.index=5; } void padding(int bsize){ int len=buffer.index; int pad=(-len)&(bsize-1); if(pad>>24); ba4[1]=(byte)(len>>>16); ba4[2]=(byte)(len>>>8); ba4[3]=(byte)(len); System.arraycopy(ba4, 0, buffer.buffer, 0, 4); buffer.buffer[4]=(byte)pad; synchronized(random){ random.fill(buffer.buffer, buffer.index, pad); } buffer.skip(pad); //buffer.putPad(pad); /* for(int i=0; i0) rq = new RequestQueue(bulk_requests); else throw new JSchException("setBulkRequests: "+ bulk_requests+" must be greater than 0."); } /** * This method will return the value how many requests may be * sent at any one time. * * @return how many requests may be sent at any one time. */ public int getBulkRequests(){ return rq.size(); } public ChannelSftp(){ super(); setLocalWindowSizeMax(LOCAL_WINDOW_SIZE_MAX); setLocalWindowSize(LOCAL_WINDOW_SIZE_MAX); setLocalPacketSize(LOCAL_MAXIMUM_PACKET_SIZE); } void init(){ } public void start() throws JSchException{ try{ PipedOutputStream pos=new PipedOutputStream(); io.setOutputStream(pos); PipedInputStream pis=new MyPipedInputStream(pos, rmpsize); io.setInputStream(pis); io_in=io.in; if(io_in==null){ throw new JSchException("channel is down"); } Request request=new RequestSftp(); request.request(getSession(), this); /* System.err.println("lmpsize: "+lmpsize); System.err.println("lwsize: "+lwsize); System.err.println("rmpsize: "+rmpsize); System.err.println("rwsize: "+rwsize); */ buf=new Buffer(lmpsize); packet=new Packet(buf); obuf=new Buffer(rmpsize); opacket=new Packet(obuf); int i=0; int length; int type; byte[] str; // send SSH_FXP_INIT sendINIT(); // receive SSH_FXP_VERSION Header header=new Header(); header=header(buf, header); length=header.length; if(length > MAX_MSG_LENGTH){ throw new SftpException(SSH_FX_FAILURE, "Received message is too long: " + length); } type=header.type; // 2 -> SSH_FXP_VERSION server_version=header.rid; //System.err.println("SFTP protocol server-version="+server_version); extensions=new java.util.Hashtable(); if(length>0){ // extension data fill(buf, length); byte[] extension_name=null; byte[] extension_data=null; while(length>0){ extension_name=buf.getString(); length-=(4+extension_name.length); extension_data=buf.getString(); length-=(4+extension_data.length); extensions.put(Util.byte2str(extension_name), Util.byte2str(extension_data)); } } if(extensions.get("posix-rename@openssh.com")!=null && extensions.get("posix-rename@openssh.com").equals("1")){ extension_posix_rename = true; } if(extensions.get("statvfs@openssh.com")!=null && extensions.get("statvfs@openssh.com").equals("2")){ extension_statvfs = true; } /* if(extensions.get("fstatvfs@openssh.com")!=null && extensions.get("fstatvfs@openssh.com").equals("2")){ extension_fstatvfs = true; } */ if(extensions.get("hardlink@openssh.com")!=null && extensions.get("hardlink@openssh.com").equals("1")){ extension_hardlink = true; } lcwd=new File(".").getCanonicalPath(); } catch(Exception e){ //System.err.println(e); if(e instanceof JSchException) throw (JSchException)e; if(e instanceof Throwable) throw new JSchException(e.toString(), (Throwable)e); throw new JSchException(e.toString()); } } public void quit(){ disconnect();} public void exit(){ disconnect();} public void lcd(String path) throws SftpException{ path=localAbsolutePath(path); if((new File(path)).isDirectory()){ try{ path=(new File(path)).getCanonicalPath(); } catch(Exception e){} lcwd=path; return; } throw new SftpException(SSH_FX_NO_SUCH_FILE, "No such directory"); } public void cd(String path) throws SftpException{ try{ ((MyPipedInputStream)io_in).updateReadSide(); path=remoteAbsolutePath(path); path=isUnique(path); byte[] str=_realpath(path); SftpATTRS attr=_stat(str); if((attr.getFlags()&SftpATTRS.SSH_FILEXFER_ATTR_PERMISSIONS)==0){ throw new SftpException(SSH_FX_FAILURE, "Can't change directory: "+path); } if(!attr.isDir()){ throw new SftpException(SSH_FX_FAILURE, "Can't change directory: "+path); } setCwd(Util.byte2str(str, fEncoding)); } catch(Exception e){ if(e instanceof SftpException) throw (SftpException)e; if(e instanceof Throwable) throw new SftpException(SSH_FX_FAILURE, "", (Throwable)e); throw new SftpException(SSH_FX_FAILURE, ""); } } public void put(String src, String dst) throws SftpException{ put(src, dst, null, OVERWRITE); } public void put(String src, String dst, int mode) throws SftpException{ put(src, dst, null, mode); } public void put(String src, String dst, SftpProgressMonitor monitor) throws SftpException{ put(src, dst, monitor, OVERWRITE); } /** * Sends data from src file to dst file. * The mode should be OVERWRITE, * RESUME or APPEND. * * @param src source file * @param dst destination file * @param monitor progress monitor * @param mode how data should be added to dst */ public void put(String src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException{ try{ ((MyPipedInputStream)io_in).updateReadSide(); src=localAbsolutePath(src); dst=remoteAbsolutePath(dst); Vector v=glob_remote(dst); int vsize=v.size(); if(vsize!=1){ if(vsize==0){ if(isPattern(dst)) throw new SftpException(SSH_FX_FAILURE, dst); else dst=Util.unquote(dst); } throw new SftpException(SSH_FX_FAILURE, v.toString()); } else{ dst=(String)(v.elementAt(0)); } boolean isRemoteDir=isRemoteDir(dst); v=glob_local(src); vsize=v.size(); StringBuffer dstsb=null; if(isRemoteDir){ if(!dst.endsWith("/")){ dst+="/"; } dstsb=new StringBuffer(dst); } else if(vsize>1){ throw new SftpException(SSH_FX_FAILURE, "Copying multiple files, but the destination is missing or a file."); } for(int j=0; ji) i=ii; } if(i==-1) dstsb.append(_src); else dstsb.append(_src.substring(i + 1)); _dst=dstsb.toString(); dstsb.delete(dst.length(), _dst.length()); } else{ _dst=dst; } //System.err.println("_dst "+_dst); long size_of_dst=0; if(mode==RESUME){ try{ SftpATTRS attr=_stat(_dst); size_of_dst=attr.getSize(); } catch(Exception eee){ //System.err.println(eee); } long size_of_src=new File(_src).length(); if(size_of_srcsrc to dst file. * The mode should be OVERWRITE, * RESUME or APPEND. * * @param src input stream * @param dst destination file * @param monitor progress monitor * @param mode how data should be added to dst */ public void put(InputStream src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException{ try{ ((MyPipedInputStream)io_in).updateReadSide(); dst=remoteAbsolutePath(dst); Vector v=glob_remote(dst); int vsize=v.size(); if(vsize!=1){ if(vsize==0){ if(isPattern(dst)) throw new SftpException(SSH_FX_FAILURE, dst); else dst=Util.unquote(dst); } throw new SftpException(SSH_FX_FAILURE, v.toString()); } else{ dst=(String)(v.elementAt(0)); } if(monitor!=null){ monitor.init(SftpProgressMonitor.PUT, "-", dst, SftpProgressMonitor.UNKNOWN_SIZE); } _put(src, dst, monitor, mode); } catch(Exception e){ if(e instanceof SftpException) { if(((SftpException)e).id == SSH_FX_FAILURE && isRemoteDir(dst)) { throw new SftpException(SSH_FX_FAILURE, dst+" is a directory"); } throw (SftpException)e; } if(e instanceof Throwable) throw new SftpException(SSH_FX_FAILURE, e.toString(), (Throwable)e); throw new SftpException(SSH_FX_FAILURE, e.toString()); } } public void _put(InputStream src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException{ try{ ((MyPipedInputStream)io_in).updateReadSide(); byte[] dstb=Util.str2byte(dst, fEncoding); long skip=0; if(mode==RESUME || mode==APPEND){ try{ SftpATTRS attr=_stat(dstb); skip=attr.getSize(); } catch(Exception eee){ //System.err.println(eee); } } if(mode==RESUME && skip>0){ long skipped=src.skip(skip); if(skipped0){ int sent=sendWRITE(handle, _offset[0], d, s, _len); writecount++; _offset[0]+=sent; s+=sent; _len-=sent; if((seq-1)==startid || io_in.available()>=1024){ while(io_in.available()>0){ if(checkStatus(ackid, header)){ _ackid=ackid[0]; if(startid>_ackid || _ackid>seq-1){ throw new SftpException(SSH_FX_FAILURE, ""); } ackcount++; } else{ break; } } } } if(monitor!=null && !monitor.count(len)){ close(); throw new IOException("canceled"); } } catch(IOException e){ throw e; } catch(Exception e){ throw new IOException(e.toString()); } } byte[] _data=new byte[1]; public void write(int foo) throws java.io.IOException{ _data[0]=(byte)foo; write(_data, 0, 1); } public void flush() throws java.io.IOException{ if(isClosed){ throw new IOException("stream already closed"); } if(!init){ try{ while(writecount>ackcount){ if(!checkStatus(null, header)){ break; } ackcount++; } } catch(SftpException e){ throw new IOException(e.toString()); } } } public void close() throws java.io.IOException{ if(isClosed){ return; } flush(); if(monitor!=null)monitor.end(); try{ _sendCLOSE(handle, header); } catch(IOException e){ throw e; } catch(Exception e){ throw new IOException(e.toString()); } isClosed=true; } }; return out; } catch(Exception e){ if(e instanceof SftpException) throw (SftpException)e; if(e instanceof Throwable) throw new SftpException(SSH_FX_FAILURE, "", (Throwable)e); throw new SftpException(SSH_FX_FAILURE, ""); } } public void get(String src, String dst) throws SftpException{ get(src, dst, null, OVERWRITE); } public void get(String src, String dst, SftpProgressMonitor monitor) throws SftpException{ get(src, dst, monitor, OVERWRITE); } public void get(String src, String dst, SftpProgressMonitor monitor, int mode) throws SftpException{ // System.out.println("get: "+src+" "+dst); boolean _dstExist = false; String _dst=null; try{ ((MyPipedInputStream)io_in).updateReadSide(); src=remoteAbsolutePath(src); dst=localAbsolutePath(dst); Vector v=glob_remote(src); int vsize=v.size(); if(vsize==0){ throw new SftpException(SSH_FX_NO_SUCH_FILE, "No such file"); } File dstFile=new File(dst); boolean isDstDir=dstFile.isDirectory(); StringBuffer dstsb=null; if(isDstDir){ if(!dst.endsWith(file_separator)){ dst+=file_separator; } dstsb=new StringBuffer(dst); } else if(vsize>1){ throw new SftpException(SSH_FX_FAILURE, "Copying multiple files, but destination is missing or a file."); } for(int j=0; jsize_of_src){ throw new SftpException(SSH_FX_FAILURE, "failed to resume for "+_dst); } if(size_of_dst==size_of_src){ return; } } if(monitor!=null){ monitor.init(SftpProgressMonitor.GET, _src, _dst, attr.getSize()); if(mode==RESUME){ monitor.count(_dstFile.length()); } } FileOutputStream fos=null; _dstExist = _dstFile.exists(); try{ if(mode==OVERWRITE){ fos=new FileOutputStream(_dst); } else{ fos=new FileOutputStream(_dst, true); // append } // System.err.println("_get: "+_src+", "+_dst); _get(_src, fos, monitor, mode, new File(_dst).length()); } finally{ if(fos!=null){ fos.close(); } } } } catch(Exception e){ if(!_dstExist && _dst!=null){ File _dstFile = new File(_dst); if(_dstFile.exists() && _dstFile.length()==0){ _dstFile.delete(); } } if(e instanceof SftpException) throw (SftpException)e; if(e instanceof Throwable) throw new SftpException(SSH_FX_FAILURE, "", (Throwable)e); throw new SftpException(SSH_FX_FAILURE, ""); } } public void get(String src, OutputStream dst) throws SftpException{ get(src, dst, null, OVERWRITE, 0); } public void get(String src, OutputStream dst, SftpProgressMonitor monitor) throws SftpException{ get(src, dst, monitor, OVERWRITE, 0); } public void get(String src, OutputStream dst, SftpProgressMonitor monitor, int mode, long skip) throws SftpException{ //System.err.println("get: "+src+", "+dst); try{ ((MyPipedInputStream)io_in).updateReadSide(); src=remoteAbsolutePath(src); src=isUnique(src); if(monitor!=null){ SftpATTRS attr=_stat(src); monitor.init(SftpProgressMonitor.GET, src, "??", attr.getSize()); if(mode==RESUME){ monitor.count(skip); } } _get(src, dst, monitor, mode, skip); } catch(Exception e){ if(e instanceof SftpException) throw (SftpException)e; if(e instanceof Throwable) throw new SftpException(SSH_FX_FAILURE, "", (Throwable)e); throw new SftpException(SSH_FX_FAILURE, ""); } } private void _get(String src, OutputStream dst, SftpProgressMonitor monitor, int mode, long skip) throws SftpException{ //System.err.println("_get: "+src+", "+dst); byte[] srcb=Util.str2byte(src, fEncoding); try{ sendOPENR(srcb); Header header=new Header(); header=header(buf, header); int length=header.length; int type=header.type; fill(buf, length); if(type!=SSH_FXP_STATUS && type!=SSH_FXP_HANDLE){ throw new SftpException(SSH_FX_FAILURE, ""); } if(type==SSH_FXP_STATUS){ int i=buf.getInt(); throwStatusError(buf, i); } byte[] handle=buf.getString(); // filename long offset=0; if(mode==RESUME){ offset+=skip; } int request_max=1; rq.init(); long request_offset=offset; int request_len = buf.buffer.length-13; if(server_version==0){ request_len=1024; } loop: while(true){ while(rq.count() < request_max){ sendREAD(handle, request_offset, request_len, rq); request_offset += request_len; } header=header(buf, header); length=header.length; type=header.type; RequestQueue.Request rr = null; try{ rr = rq.get(header.rid); } catch(RequestQueue.OutOfOrderException e){ request_offset = e.offset; skip(header.length); rq.cancel(header, buf); continue; } if(type==SSH_FXP_STATUS){ fill(buf, length); int i=buf.getInt(); if(i==SSH_FX_EOF){ break loop; } throwStatusError(buf, i); } if(type!=SSH_FXP_DATA){ break loop; } buf.rewind(); fill(buf.buffer, 0, 4); length-=4; int length_of_data = buf.getInt(); // length of data /** Since sftp protocol version 6, "end-of-file" has been defined, byte SSH_FXP_DATA uint32 request-id string data bool end-of-file [optional] but some sftpd server will send such a field in the sftp protocol 3 ;-( */ int optional_data = length - length_of_data; int foo = length_of_data; while(foo>0){ int bar=foo; if(bar>buf.buffer.length){ bar=buf.buffer.length; } int data_len = io_in.read(buf.buffer, 0, bar); if(data_len<0){ break loop; } dst.write(buf.buffer, 0, data_len); offset+=data_len; foo-=data_len; if(monitor!=null){ if(!monitor.count(data_len)){ skip(foo); if(optional_data>0){ skip(optional_data); } break loop; } } } //System.err.println("length: "+length); // length should be 0 if(optional_data>0){ skip(optional_data); } if(length_of_data=rrq.length) tail -= rrq.length; rrq[tail].id=id; rrq[tail].offset=offset; rrq[tail].length=length; count++; } Request get(int id) throws OutOfOrderException, SftpException { count -= 1; int i = head; head++; if(head==rrq.length) head=0; if(rrq[i].id != id){ long offset = getOffset(); boolean find = false; for(int j = 0; jrrq[i].offset) result=rrq[i].offset; } return result; } } public InputStream get(String src) throws SftpException{ return get(src, null, 0L); } public InputStream get(String src, SftpProgressMonitor monitor) throws SftpException{ return get(src, monitor, 0L); } /** * @deprecated This method will be deleted in the future. */ public InputStream get(String src, int mode) throws SftpException{ return get(src, null, 0L); } /** * @deprecated This method will be deleted in the future. */ public InputStream get(String src, final SftpProgressMonitor monitor, final int mode) throws SftpException{ return get(src, monitor, 0L); } public InputStream get(String src, final SftpProgressMonitor monitor, final long skip) throws SftpException{ try{ ((MyPipedInputStream)io_in).updateReadSide(); src=remoteAbsolutePath(src); src=isUnique(src); byte[] srcb=Util.str2byte(src, fEncoding); SftpATTRS attr=_stat(srcb); if(monitor!=null){ monitor.init(SftpProgressMonitor.GET, src, "??", attr.getSize()); } sendOPENR(srcb); Header header=new Header(); header=header(buf, header); int length=header.length; int type=header.type; fill(buf, length); if(type!=SSH_FXP_STATUS && type!=SSH_FXP_HANDLE){ throw new SftpException(SSH_FX_FAILURE, ""); } if(type==SSH_FXP_STATUS){ int i=buf.getInt(); throwStatusError(buf, i); } final byte[] handle=buf.getString(); // handle rq.init(); java.io.InputStream in=new java.io.InputStream(){ long offset=skip; boolean closed=false; int rest_length=0; byte[] _data=new byte[1]; byte[] rest_byte=new byte[1024]; Header header=new Header(); int request_max=1; long request_offset=offset; public int read() throws java.io.IOException{ if(closed)return -1; int i=read(_data, 0, 1); if (i==-1) { return -1; } else { return _data[0]&0xff; } } public int read(byte[] d) throws java.io.IOException{ if(closed)return -1; return read(d, 0, d.length); } public int read(byte[] d, int s, int len) throws java.io.IOException{ if(closed)return -1; if(d==null){throw new NullPointerException();} if(s<0 || len <0 || s+len>d.length){ throw new IndexOutOfBoundsException(); } if(len==0){ return 0; } if(rest_length>0){ int foo=rest_length; if(foo>len) foo=len; System.arraycopy(rest_byte, 0, d, s, foo); if(foo!=rest_length){ System.arraycopy(rest_byte, foo, rest_byte, 0, rest_length-foo); } if(monitor!=null){ if(!monitor.count(foo)){ close(); return -1; } } rest_length-=foo; return foo; } if(buf.buffer.length-131024){ len=1024; } if(rq.count()==0) { int request_len = buf.buffer.length-13; if(server_version==0){ request_len=1024; } while(rq.count() < request_max){ try{ sendREAD(handle, request_offset, request_len, rq); } catch(Exception e){ throw new IOException("error"); } request_offset += request_len; } } header=header(buf, header); rest_length=header.length; int type=header.type; int id=header.rid; RequestQueue.Request rr = null; try{ rr = rq.get(header.rid); } catch(RequestQueue.OutOfOrderException e){ request_offset = e.offset; skip(header.length); rq.cancel(header, buf); return 0; } catch(SftpException e){ throw new IOException("error: "+e.toString()); } if(type!=SSH_FXP_STATUS && type!=SSH_FXP_DATA){ throw new IOException("error"); } if(type==SSH_FXP_STATUS){ fill(buf, rest_length); int i=buf.getInt(); rest_length=0; if(i==SSH_FX_EOF){ close(); return -1; } //throwStatusError(buf, i); throw new IOException("error"); } buf.rewind(); fill(buf.buffer, 0, 4); int length_of_data = buf.getInt(); rest_length-=4; /** Since sftp protocol version 6, "end-of-file" has been defined, byte SSH_FXP_DATA uint32 request-id string data bool end-of-file [optional] but some sftpd server will send such a field in the sftp protocol 3 ;-( */ int optional_data = rest_length - length_of_data; offset += length_of_data; int foo = length_of_data; if(foo>0){ int bar=foo; if(bar>len){ bar=len; } int i=io_in.read(d, s, bar); if(i<0){ return -1; } foo-=i; rest_length=foo; if(foo>0){ if(rest_byte.length0){ j=io_in.read(rest_byte, _s, _len); if(j<=0)break; _s+=j; _len-=j; } } if(optional_data>0){ io_in.skip(optional_data); } if(length_of_datapath. * Each files and directories will be passed to * LsEntrySelector#select(LsEntry) method, and if that method * returns LsEntrySelector#BREAK, the operation will be * canceled immediately. * * @see ChannelSftp.LsEntrySelector * @since 0.1.47 */ public void ls(String path, LsEntrySelector selector) throws SftpException{ //System.out.println("ls: "+path); try{ ((MyPipedInputStream)io_in).updateReadSide(); path=remoteAbsolutePath(path); byte[] pattern=null; java.util.Vector v=new java.util.Vector(); int foo=path.lastIndexOf('/'); String dir=path.substring(0, ((foo==0)?1:foo)); String _pattern=path.substring(foo+1); dir=Util.unquote(dir); // If pattern has included '*' or '?', we need to convert // to UTF-8 string before globbing. byte[][] _pattern_utf8=new byte[1][]; boolean pattern_has_wildcard=isPattern(_pattern, _pattern_utf8); if(pattern_has_wildcard){ pattern=_pattern_utf8[0]; } else{ String upath=Util.unquote(path); //SftpATTRS attr=_lstat(upath); SftpATTRS attr=_stat(upath); if(attr.isDir()){ pattern=null; dir=upath; } else{ /* // If we can generage longname by ourself, // we don't have to use openDIR. String filename=Util.unquote(_pattern); String longname=... v.addElement(new LsEntry(filename, longname, attr)); return v; */ if(fEncoding_is_utf8){ pattern=_pattern_utf8[0]; pattern=Util.unquote(pattern); } else{ _pattern=Util.unquote(_pattern); pattern=Util.str2byte(_pattern, fEncoding); } } } sendOPENDIR(Util.str2byte(dir, fEncoding)); Header header=new Header(); header=header(buf, header); int length=header.length; int type=header.type; fill(buf, length); if(type!=SSH_FXP_STATUS && type!=SSH_FXP_HANDLE){ throw new SftpException(SSH_FX_FAILURE, ""); } if(type==SSH_FXP_STATUS){ int i=buf.getInt(); throwStatusError(buf, i); } int cancel = LsEntrySelector.CONTINUE; byte[] handle=buf.getString(); // handle while(cancel==LsEntrySelector.CONTINUE){ sendREADDIR(handle); header=header(buf, header); length=header.length; type=header.type; if(type!=SSH_FXP_STATUS && type!=SSH_FXP_NAME){ throw new SftpException(SSH_FX_FAILURE, ""); } if(type==SSH_FXP_STATUS){ fill(buf, length); int i=buf.getInt(); if(i==SSH_FX_EOF) break; throwStatusError(buf, i); } buf.rewind(); fill(buf.buffer, 0, 4); length-=4; int count=buf.getInt(); byte[] str; int flags; buf.reset(); while(count>0){ if(length>0){ buf.shift(); int j=(buf.buffer.length>(buf.index+length)) ? length : (buf.buffer.length-buf.index); int i=fill(buf.buffer, buf.index, j); buf.index+=i; length-=i; } byte[] filename=buf.getString(); byte[] longname=null; if(server_version<=3){ longname=buf.getString(); } SftpATTRS attrs=SftpATTRS.getATTR(buf); if(cancel==LsEntrySelector.BREAK){ count--; continue; } boolean find=false; String f=null; if(pattern==null){ find=true; } else if(!pattern_has_wildcard){ find=Util.array_equals(pattern, filename); } else{ byte[] _filename=filename; if(!fEncoding_is_utf8){ f=Util.byte2str(_filename, fEncoding); _filename=Util.str2byte(f, UTF8); } find=Util.glob(pattern, _filename); } if(find){ if(f==null){ f=Util.byte2str(filename, fEncoding); } String l=null; if(longname==null){ // TODO: we need to generate long name from attrs // for the sftp protocol 4(and later). l=attrs.toString()+" "+f; } else{ l=Util.byte2str(longname, fEncoding); } cancel = selector.select(new LsEntry(f, l, attrs)); } count--; } } _sendCLOSE(handle, header); /* if(v.size()==1 && pattern_has_wildcard){ LsEntry le=(LsEntry)v.elementAt(0); if(le.getAttrs().isDir()){ String f=le.getFilename(); if(isPattern(f)){ f=Util.quote(f); } if(!dir.endsWith("/")){ dir+="/"; } v=null; return ls(dir+f); } } */ } catch(Exception e){ if(e instanceof SftpException) throw (SftpException)e; if(e instanceof Throwable) throw new SftpException(SSH_FX_FAILURE, "", (Throwable)e); throw new SftpException(SSH_FX_FAILURE, ""); } } public String readlink(String path) throws SftpException{ try{ if(server_version<3){ throw new SftpException(SSH_FX_OP_UNSUPPORTED, "The remote sshd is too old to support symlink operation."); } ((MyPipedInputStream)io_in).updateReadSide(); path=remoteAbsolutePath(path); path=isUnique(path); sendREADLINK(Util.str2byte(path, fEncoding)); Header header=new Header(); header=header(buf, header); int length=header.length; int type=header.type; fill(buf, length); if(type!=SSH_FXP_STATUS && type!=SSH_FXP_NAME){ throw new SftpException(SSH_FX_FAILURE, ""); } if(type==SSH_FXP_NAME){ int count=buf.getInt(); // count byte[] filename=null; for(int i=0; i=2){ throw new SftpException(SSH_FX_FAILURE, v.toString()); } if(vsize==1){ newpath=(String)(v.elementAt(0)); } else{ // vsize==0 if(isPattern(newpath)) throw new SftpException(SSH_FX_FAILURE, newpath); newpath=Util.unquote(newpath); } sendRENAME(Util.str2byte(oldpath, fEncoding), Util.str2byte(newpath, fEncoding)); Header header=new Header(); header=header(buf, header); int length=header.length; int type=header.type; fill(buf, length); if(type!=SSH_FXP_STATUS){ throw new SftpException(SSH_FX_FAILURE, ""); } int i=buf.getInt(); if(i==SSH_FX_OK) return; throwStatusError(buf, i); } catch(Exception e){ if(e instanceof SftpException) throw (SftpException)e; if(e instanceof Throwable) throw new SftpException(SSH_FX_FAILURE, "", (Throwable)e); throw new SftpException(SSH_FX_FAILURE, ""); } } public void rm(String path) throws SftpException{ try{ ((MyPipedInputStream)io_in).updateReadSide(); path=remoteAbsolutePath(path); Vector v=glob_remote(path); int vsize=v.size(); Header header=new Header(); for(int j=0; j0){ str=buf.getString(); // absolute path; if(server_version<=3){ byte[] lname=buf.getString(); // long filename } SftpATTRS attr=SftpATTRS.getATTR(buf); // dummy attribute } return str; } public void setStat(String path, SftpATTRS attr) throws SftpException{ try{ ((MyPipedInputStream)io_in).updateReadSide(); path=remoteAbsolutePath(path); Vector v=glob_remote(path); int vsize=v.size(); for(int j=0; j0){ i=io_in.read(buf, s, l); if(i<=0){ throw new SftpException(SSH_FX_FAILURE, ""); } s+=i; l-=i; } } private boolean checkStatus(int[] ackid, Header header) throws IOException, SftpException{ header=header(buf, header); int length=header.length; int type=header.type; if(ackid!=null) ackid[0]=header.rid; fill(buf, length); if(type!=SSH_FXP_STATUS){ throw new SftpException(SSH_FX_FAILURE, ""); } int i=buf.getInt(); if(i!=SSH_FX_OK){ throwStatusError(buf, i); } return true; } private boolean _sendCLOSE(byte[] handle, Header header) throws Exception{ sendCLOSE(handle); return checkStatus(null, header); } private void sendINIT() throws Exception{ packet.reset(); putHEAD(SSH_FXP_INIT, 5); buf.putInt(3); // version 3 getSession().write(packet, this, 5+4); } private void sendREALPATH(byte[] path) throws Exception{ sendPacketPath(SSH_FXP_REALPATH, path); } private void sendSTAT(byte[] path) throws Exception{ sendPacketPath(SSH_FXP_STAT, path); } private void sendSTATVFS(byte[] path) throws Exception{ sendPacketPath((byte)0, path, "statvfs@openssh.com"); } /* private void sendFSTATVFS(byte[] handle) throws Exception{ sendPacketPath((byte)0, handle, "fstatvfs@openssh.com"); } */ private void sendLSTAT(byte[] path) throws Exception{ sendPacketPath(SSH_FXP_LSTAT, path); } private void sendFSTAT(byte[] handle) throws Exception{ sendPacketPath(SSH_FXP_FSTAT, handle); } private void sendSETSTAT(byte[] path, SftpATTRS attr) throws Exception{ packet.reset(); putHEAD(SSH_FXP_SETSTAT, 9+path.length+attr.length()); buf.putInt(seq++); buf.putString(path); // path attr.dump(buf); getSession().write(packet, this, 9+path.length+attr.length()+4); } private void sendREMOVE(byte[] path) throws Exception{ sendPacketPath(SSH_FXP_REMOVE, path); } private void sendMKDIR(byte[] path, SftpATTRS attr) throws Exception{ packet.reset(); putHEAD(SSH_FXP_MKDIR, 9+path.length+(attr!=null?attr.length():4)); buf.putInt(seq++); buf.putString(path); // path if(attr!=null) attr.dump(buf); else buf.putInt(0); getSession().write(packet, this, 9+path.length+(attr!=null?attr.length():4)+4); } private void sendRMDIR(byte[] path) throws Exception{ sendPacketPath(SSH_FXP_RMDIR, path); } private void sendSYMLINK(byte[] p1, byte[] p2) throws Exception{ sendPacketPath(SSH_FXP_SYMLINK, p1, p2); } private void sendHARDLINK(byte[] p1, byte[] p2) throws Exception{ sendPacketPath((byte)0, p1, p2, "hardlink@openssh.com"); } private void sendREADLINK(byte[] path) throws Exception{ sendPacketPath(SSH_FXP_READLINK, path); } private void sendOPENDIR(byte[] path) throws Exception{ sendPacketPath(SSH_FXP_OPENDIR, path); } private void sendREADDIR(byte[] path) throws Exception{ sendPacketPath(SSH_FXP_READDIR, path); } private void sendRENAME(byte[] p1, byte[] p2) throws Exception{ sendPacketPath(SSH_FXP_RENAME, p1, p2, extension_posix_rename ? "posix-rename@openssh.com" : null); } private void sendCLOSE(byte[] path) throws Exception{ sendPacketPath(SSH_FXP_CLOSE, path); } private void sendOPENR(byte[] path) throws Exception{ sendOPEN(path, SSH_FXF_READ); } private void sendOPENW(byte[] path) throws Exception{ sendOPEN(path, SSH_FXF_WRITE|SSH_FXF_CREAT|SSH_FXF_TRUNC); } private void sendOPENA(byte[] path) throws Exception{ sendOPEN(path, SSH_FXF_WRITE|/*SSH_FXF_APPEND|*/SSH_FXF_CREAT); } private void sendOPEN(byte[] path, int mode) throws Exception{ packet.reset(); putHEAD(SSH_FXP_OPEN, 17+path.length); buf.putInt(seq++); buf.putString(path); buf.putInt(mode); buf.putInt(0); // attrs getSession().write(packet, this, 17+path.length+4); } private void sendPacketPath(byte fxp, byte[] path) throws Exception{ sendPacketPath(fxp, path, (String)null); } private void sendPacketPath(byte fxp, byte[] path, String extension) throws Exception{ packet.reset(); int len = 9+path.length; if(extension == null) { putHEAD(fxp, len); buf.putInt(seq++); } else { len+=(4+extension.length()); putHEAD(SSH_FXP_EXTENDED, len); buf.putInt(seq++); buf.putString(Util.str2byte(extension)); } buf.putString(path); // path getSession().write(packet, this, len+4); } private void sendPacketPath(byte fxp, byte[] p1, byte[] p2) throws Exception{ sendPacketPath(fxp, p1, p2, null); } private void sendPacketPath(byte fxp, byte[] p1, byte[] p2, String extension) throws Exception{ packet.reset(); int len = 13+p1.length+p2.length; if(extension==null){ putHEAD(fxp, len); buf.putInt(seq++); } else { len+=(4+extension.length()); putHEAD(SSH_FXP_EXTENDED, len); buf.putInt(seq++); buf.putString(Util.str2byte(extension)); } buf.putString(p1); buf.putString(p2); getSession().write(packet, this, len+4); } private int sendWRITE(byte[] handle, long offset, byte[] data, int start, int length) throws Exception{ int _length=length; opacket.reset(); if(obuf.buffer.length0){ if(length>0){ buf.shift(); int j=(buf.buffer.length>(buf.index+length)) ? length : (buf.buffer.length-buf.index); i=io_in.read(buf.buffer, buf.index, j); if(i<=0)break; buf.index+=i; length-=i; } byte[] filename=buf.getString(); //System.err.println("filename: "+new String(filename)); if(server_version<=3){ str=buf.getString(); // longname } SftpATTRS attrs=SftpATTRS.getATTR(buf); byte[] _filename=filename; String f=null; boolean found=false; if(!fEncoding_is_utf8){ f=Util.byte2str(filename, fEncoding); _filename=Util.str2byte(f, UTF8); } found=Util.glob(pattern, _filename); if(found){ if(f==null){ f=Util.byte2str(filename, fEncoding); } if(pdir==null){ pdir=dir; if(!pdir.endsWith("/")){ pdir+="/"; } } v.addElement(pdir+f); } count--; } } if(_sendCLOSE(handle, header)) return v; return null; } private boolean isPattern(byte[] path){ int length=path.length; int i=0; while(i=0){ if(path[i]!='*' && path[i]!='?'){ i--; continue; } if(!fs_is_bs && i>0 && path[i-1]=='\\'){ i--; if(i>0 && path[i-1]=='\\'){ i--; i--; continue; } } break; } if(i<0){ v.addElement(fs_is_bs ? _path : Util.unquote(_path)); return v;} while(i>=0){ if(path[i]==file_separatorc || (fs_is_bs && path[i]=='/')){ // On Windows, '/' is also the separator. break; } i--; } if(i<0){ v.addElement(fs_is_bs ? _path : Util.unquote(_path)); return v;} byte[] dir; if(i==0){dir=new byte[]{(byte)file_separatorc};} else{ dir=new byte[i]; System.arraycopy(path, 0, dir, 0, i); } byte[] pattern=new byte[path.length-i-1]; System.arraycopy(path, i+1, pattern, 0, pattern.length); //System.err.println("dir: "+new String(dir)+" pattern: "+new String(pattern)); try{ String[] children=(new File(Util.byte2str(dir, UTF8))).list(); String pdir=Util.byte2str(dir)+file_separator; for(int j=0; j=3 && // WindRiver's sftp will send invalid buf.getLength()>=4){ // SSH_FXP_STATUS packet. byte[] str=buf.getString(); //byte[] tag=buf.getString(); throw new SftpException(i, Util.byte2str(str, UTF8)); } else{ throw new SftpException(i, "Failure"); } } private static boolean isLocalAbsolutePath(String path){ return (new File(path)).isAbsolute(); } public void disconnect(){ super.disconnect(); } private boolean isPattern(String path, byte[][] utf8){ byte[] _path=Util.str2byte(path, UTF8); if(utf8!=null) utf8[0]=_path; return isPattern(_path); } private boolean isPattern(String path){ return isPattern(path, null); } private void fill(Buffer buf, int len) throws IOException{ buf.reset(); fill(buf.buffer, 0, len); buf.skip(len); } private int fill(byte[] buf, int s, int len) throws IOException{ int i=0; int foo=s; while(len>0){ i=io_in.read(buf, s, len); if(i<=0){ throw new IOException("inputstream is closed"); //return (s-foo)==0 ? i : s-foo; } s+=i; len-=i; } return s-foo; } private void skip(long foo) throws IOException{ while(foo>0){ long bar=io_in.skip(foo); if(bar<=0) break; foo-=bar; } } class Header{ int length; int type; int rid; } private Header header(Buffer buf, Header header) throws IOException{ buf.rewind(); int i=fill(buf.buffer, 0, 9); header.length=buf.getInt()-5; header.type=buf.getByte()&0xff; header.rid=buf.getInt(); return header; } private String remoteAbsolutePath(String path) throws SftpException{ if(path.charAt(0)=='/') return path; String cwd=getCwd(); // if(cwd.equals(getHome())) return path; if(cwd.endsWith("/")) return cwd+path; return cwd+"/"+path; } private String localAbsolutePath(String path){ if(isLocalAbsolutePath(path)) return path; if(lcwd.endsWith(file_separator)) return lcwd+path; return lcwd+file_separator+path; } /** * This method will check if the given string can be expanded to the * unique string. If it can be expanded to mutiple files, SftpException * will be thrown. * @return the returned string is unquoted. */ private String isUnique(String path) throws SftpException, Exception{ Vector v=glob_remote(path); if(v.size()!=1){ throw new SftpException(SSH_FX_FAILURE, path+" is not unique: "+v.toString()); } return (String)(v.elementAt(0)); } public int getServerVersion() throws SftpException{ if(!isConnected()){ throw new SftpException(SSH_FX_FAILURE, "The channel is not connected."); } return server_version; } public void setFilenameEncoding(String encoding) throws SftpException{ int sversion=getServerVersion(); if(3 <= sversion && sversion <= 5 && !encoding.equals(UTF8)){ throw new SftpException(SSH_FX_FAILURE, "The encoding can not be changed for this sftp server."); } if(encoding.equals(UTF8)){ encoding=UTF8; } fEncoding=encoding; fEncoding_is_utf8=fEncoding.equals(UTF8); } public String getExtension(String key){ if(extensions==null) return null; return (String)extensions.get(key); } public String realpath(String path) throws SftpException{ try{ byte[] _path=_realpath(remoteAbsolutePath(path)); return Util.byte2str(_path, fEncoding); } catch(Exception e){ if(e instanceof SftpException) throw (SftpException)e; if(e instanceof Throwable) throw new SftpException(SSH_FX_FAILURE, "", (Throwable)e); throw new SftpException(SSH_FX_FAILURE, ""); } } public class LsEntry implements Comparable{ private String filename; private String longname; private SftpATTRS attrs; LsEntry(String filename, String longname, SftpATTRS attrs){ setFilename(filename); setLongname(longname); setAttrs(attrs); } public String getFilename(){return filename;}; void setFilename(String filename){this.filename = filename;}; public String getLongname(){return longname;}; void setLongname(String longname){this.longname = longname;}; public SftpATTRS getAttrs(){return attrs;}; void setAttrs(SftpATTRS attrs) {this.attrs = attrs;}; public String toString(){ return longname; } public int compareTo(Object o) throws ClassCastException{ if(o instanceof LsEntry){ return filename.compareTo(((LsEntry)o).getFilename()); } throw new ClassCastException("a decendent of LsEntry must be given."); } } /** * This interface will be passed as an argument for ls method. * * @see ChannelSftp.LsEntry * @see #ls(String, ChannelSftp.LsEntrySelector) * @since 0.1.47 */ public interface LsEntrySelector { public final int CONTINUE = 0; public final int BREAK = 1; /** *

    The select method will be invoked in ls * method for each file entry. If this method returns BREAK, * ls will be canceled. * * @param entry one of entry from ls * @return if BREAK is returned, the 'ls' operation will be canceled. */ public int select(LsEntry entry); } } jsch-0.1.53/src/main/java/com/jcraft/jsch/Buffer.java0000644000000000000000000001661112500204653020715 0ustar rootroot/* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ /* Copyright (c) 2002-2015 ymnk, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ package com.jcraft.jsch; public class Buffer{ final byte[] tmp=new byte[4]; byte[] buffer; int index; int s; public Buffer(int size){ buffer=new byte[size]; index=0; s=0; } public Buffer(byte[] buffer){ this.buffer=buffer; index=0; s=0; } public Buffer(){ this(1024*10*2); } public void putByte(byte foo){ buffer[index++]=foo; } public void putByte(byte[] foo) { putByte(foo, 0, foo.length); } public void putByte(byte[] foo, int begin, int length) { System.arraycopy(foo, begin, buffer, index, length); index+=length; } public void putString(byte[] foo){ putString(foo, 0, foo.length); } public void putString(byte[] foo, int begin, int length) { putInt(length); putByte(foo, begin, length); } public void putInt(int val) { tmp[0]=(byte)(val >>> 24); tmp[1]=(byte)(val >>> 16); tmp[2]=(byte)(val >>> 8); tmp[3]=(byte)(val); System.arraycopy(tmp, 0, buffer, index, 4); index+=4; } public void putLong(long val) { tmp[0]=(byte)(val >>> 56); tmp[1]=(byte)(val >>> 48); tmp[2]=(byte)(val >>> 40); tmp[3]=(byte)(val >>> 32); System.arraycopy(tmp, 0, buffer, index, 4); tmp[0]=(byte)(val >>> 24); tmp[1]=(byte)(val >>> 16); tmp[2]=(byte)(val >>> 8); tmp[3]=(byte)(val); System.arraycopy(tmp, 0, buffer, index+4, 4); index+=8; } void skip(int n) { index+=n; } void putPad(int n) { while(n>0){ buffer[index++]=(byte)0; n--; } } public void putMPInt(byte[] foo){ int i=foo.length; if((foo[0]&0x80)!=0){ i++; putInt(i); putByte((byte)0); } else{ putInt(i); } putByte(foo); } public int getLength(){ return index-s; } public int getOffSet(){ return s; } public void setOffSet(int s){ this.s=s; } public long getLong(){ long foo = getInt()&0xffffffffL; foo = ((foo<<32)) | (getInt()&0xffffffffL); return foo; } public int getInt(){ int foo = getShort(); foo = ((foo<<16)&0xffff0000) | (getShort()&0xffff); return foo; } public long getUInt(){ long foo = 0L; long bar = 0L; foo = getByte(); foo = ((foo<<8)&0xff00)|(getByte()&0xff); bar = getByte(); bar = ((bar<<8)&0xff00)|(getByte()&0xff); foo = ((foo<<16)&0xffff0000) | (bar&0xffff); return foo; } int getShort() { int foo = getByte(); foo = ((foo<<8)&0xff00)|(getByte()&0xff); return foo; } public int getByte() { return (buffer[s++]&0xff); } public void getByte(byte[] foo) { getByte(foo, 0, foo.length); } void getByte(byte[] foo, int start, int len) { System.arraycopy(buffer, s, foo, start, len); s+=len; } public int getByte(int len) { int foo=s; s+=len; return foo; } public byte[] getMPInt() { int i=getInt(); // uint32 if(i<0 || // bigger than 0x7fffffff i>8*1024){ // TODO: an exception should be thrown. i = 8*1024; // the session will be broken, but working around OOME. } byte[] foo=new byte[i]; getByte(foo, 0, i); return foo; } public byte[] getMPIntBits() { int bits=getInt(); int bytes=(bits+7)/8; byte[] foo=new byte[bytes]; getByte(foo, 0, bytes); if((foo[0]&0x80)!=0){ byte[] bar=new byte[foo.length+1]; bar[0]=0; // ?? System.arraycopy(foo, 0, bar, 1, foo.length); foo=bar; } return foo; } public byte[] getString() { int i = getInt(); // uint32 if(i<0 || // bigger than 0x7fffffff i>256*1024){ // TODO: an exception should be thrown. i = 256*1024; // the session will be broken, but working around OOME. } byte[] foo=new byte[i]; getByte(foo, 0, i); return foo; } byte[] getString(int[]start, int[]len) { int i=getInt(); start[0]=getByte(i); len[0]=i; return buffer; } public void reset(){ index=0; s=0; } public void shift(){ if(s==0)return; System.arraycopy(buffer, s, buffer, 0, index-s); index=index-s; s=0; } void rewind(){ s=0; } byte getCommand(){ return buffer[5]; } void checkFreeSize(int n){ int size = index+n+Session.buffer_margin; if(buffer.length>>4)&0xf]); System.err.print(chars[foo&0xf]); if(i%16==15){ System.err.println(""); continue; } if(i>0 && i%2==1){ System.err.print(" "); } } System.err.println(""); } static void dump(byte[] b){ dump(b, 0, b.length); } static void dump(byte[] b, int s, int l){ for(int i=s; i 0){ Object[] identities = cache.toArray(); for(int i = 0; i < identities.length; i++){ Identity identity = (Identity)(identities[i]); cache.removeElement(identity); add(identity); } } } } } jsch-0.1.53/src/test/0000755000000000000000000000000012231443417012774 5ustar rootrootjsch-0.1.53/src/test/resources/0000755000000000000000000000000012534212266015010 5ustar rootrootjsch-0.1.53/src/test/scala/0000755000000000000000000000000012534212272014056 5ustar rootrootjsch-0.1.53/pom.xml0000644000000000000000000000625412531410622012545 0ustar rootroot 4.0.0 com.jcraft jsch jar 0.1.53 JSch http://www.jcraft.com/jsch/ JSch is a pure Java implementation of SSH2 JCraft,Inc. http://www.jcraft.com/ scm:git:http://git.jcraft.com/jsch.git scm:git:http://git.jcraft.com/jsch.git http://git.jcraft.com/jsch.git ymnk Atsuhiko Yamanaka ymnk at jcraft D0t com http://github.com/ymnk JCraft,Inc. http://www.jcraft.com/ architect developer +9 Revised BSD http://www.jcraft.com/jsch/LICENSE.txt com.jcraft jzlib 1.0.7 true org.apache.maven.plugins maven-source-plugin attach-sources jar org.apache.maven.plugins maven-compiler-plugin 1.5 org.apache.maven.plugins maven-javadoc-plugin attach-javadocs jar org.apache.maven.wagon wagon-ssh-external 1.0-alpha-5 org.sonatype.oss oss-parent 6 jsch-0.1.53/LICENSE.txt0000644000000000000000000000316312534213123013047 0ustar rootrootJSch 0.0.* was released under the GNU LGPL license. Later, we have switched over to a BSD-style license. ------------------------------------------------------------------------------ Copyright (c) 2002-2015 Atsuhiko Yamanaka, JCraft,Inc. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of the authors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. jsch-0.1.53/build.xml0000644000000000000000000000670112531410632013047 0ustar rootroot JSch is a pure Java implementation of SSH2. JSch allows you to connect to an sshd server and use port forwarding, X11 forwarding, file transfer, etc., and you can integrate its functionality into your own Java programs jsch-0.1.53/build.bat0000644000000000000000000000042607662347645013041 0ustar rootroot@echo off echo. echo JSch Build System echo ----------------- set OLD_ANT_HOME=%ANT_HOME% set ANT_HOME=tools set OLD_CLASSPATH=%CLASSPATH% %ANT_HOME%\bin\ant.bat -emacs %1 %2 %3 %4 %5 %6 %7 %8 goto cleanup :cleanup set ANT_HOME=%OLD_ANT_HOME% set CLASSPATH=%OLD_CLASSPATH%