📄 sshinteractiveclient.java
字号:
/****************************************************************************** * * Copyright (c) 1999-2003 AppGate Network Security AB. All Rights Reserved. * * This file contains Original Code and/or Modifications of Original Code as * defined in and that are subject to the MindTerm Public Source License, * Version 2.0, (the 'License'). You may not use this file except in compliance * with the License. * * You should have received a copy of the MindTerm Public Source License * along with this software; see the file LICENSE. If not, write to * AppGate Network Security AB, Otterhallegatan 2, SE-41118 Goteborg, SWEDEN * *****************************************************************************/package com.mindbright.ssh;import java.io.File;import java.io.InputStream;import java.io.ByteArrayOutputStream;import java.io.IOException;import java.io.FileNotFoundException;import java.net.UnknownHostException;import java.util.Properties;import java.util.Vector;import java.util.Enumeration;import java.applet.AppletContext;import java.awt.Frame;import java.awt.Image;import java.awt.Toolkit;import com.mindbright.ssh2.*;import com.mindbright.terminal.*;import com.mindbright.net.*;import com.mindbright.gui.Logo;import com.mindbright.application.MindTermApp;import com.mindbright.application.ModuleTerminalImpl;import com.mindbright.sshcommon.SSHConsoleRemote;import com.mindbright.util.RandomSeed;public final class SSHInteractiveClient extends SSHClient implements Runnable, SSHInteractor, SSH2Interactor, MindTermApp, TerminalInputListener { public boolean isSSH2 = false; public SSH2Transport transport; SSH2Connection connection; SSH2TerminalAdapter termAdapter; public static boolean wantHelpInfo = true; public static String customStartMessage = null; SSHMenuHandler menus; SSHStdIO sshStdIO; SSHPropertyHandler propsHandler; public boolean quiet; public boolean exitOnLogout; boolean initQuiet; public SSHInteractiveClient(boolean quiet, boolean exitOnLogout, SSHPropertyHandler propsHandler) { super(propsHandler, propsHandler); this.propsHandler = propsHandler; this.interactor = this; // !!! OUCH propsHandler.setInteractor(this); propsHandler.setClient(this); this.quiet = quiet; this.exitOnLogout = exitOnLogout; this.initQuiet = quiet; setConsole(new SSHStdIO()); sshStdIO = (SSHStdIO)console; sshStdIO.setClient(this); } public SSHInteractiveClient(SSHInteractiveClient clone) { this(true, true, new SSHPropertyHandler(clone.propsHandler)); this.activateTunnels = false; this.wantHelpInfo = clone.wantHelpInfo; this.customStartMessage = clone.customStartMessage; } public void setMenus(SSHMenuHandler menus) { this.menus = menus; } public SSHPropertyHandler getPropertyHandler() { return propsHandler; } public void updateMenus() { if(menus != null) menus.update(); } public void splashScreen() { TerminalWin t = getTerminalWin(); if(t != null) { t.clearScreen(); t.cursorSetPos(0, 0, false); } console.println("MindTerm version " + Version.version); console.println(Version.copyright); console.println(Version.licenseMessage); /* !!! REMOVE int col = (t.cols() / 2) - (copyright.length() / 2) - 1; t.cursorSetPos(t.rows() - 5, col, false); */ showLogo(); if((menus != null) && menus.havePopupMenu) { if(t != null) { t.cursorSetPos(t.rows() - 3, 0, false); } console.println("\r\33[2Kpress <ctrl> + <mouse-" + menus.getPopupButton() + "> for Menu"); } if(propsHandler.getSSHHomeDir() != null) { if(t != null) { t.cursorSetPos(t.rows() - 2, 0, false); } console.println("\r\33[2KMindTerm home: " + propsHandler.getSSHHomeDir()); } if(t != null) { t.cursorSetPos(t.rows() - 1, 0, false); } } public boolean installLogo() { boolean isPresent = false; TerminalWin t = getTerminalWin(); if(t != null) { ByteArrayOutputStream baos = readResource("/defaults/logo.gif"); if(baos != null) { byte[] img = baos.toByteArray(); Image logo = Toolkit.getDefaultToolkit().createImage(img); int width = -1; int height = -1; boolean ready = false; while (!ready) { width = logo.getWidth(null); height = logo.getHeight(null); if(width != -1 && height != -1) { ready = true; } Thread.yield(); } t.setLogo(logo, -1, -1, width, height); isPresent = true; } } return isPresent; } public ByteArrayOutputStream readResource(String name) { InputStream in = getClass().getResourceAsStream(name); ByteArrayOutputStream baos = null; if(in != null) { baos = new ByteArrayOutputStream(); try { int c; while((c = in.read()) >= 0) baos.write(c); } catch(IOException e) { // !!! System.err.println("ERROR reading resource " + name + " : " + e); } } return baos; } void initRandomSeed() { if(!SSH.haveSecureRandom()) { console.print("Initializing random generator, please wait..."); SSH.initSeedGenerator(); console.print("done"); } } public void doSingleCommand(String commandLine) throws Exception { this.commandLine = commandLine; if (com.mindbright.util.Util.isNetscapeJava()) { try { netscape.security.PrivilegeManager.enablePrivilege("TerminalEmulator"); } catch (netscape.security.ForbiddenTargetException e) { // !!! REMOVE console.println("Unsigned applet, can only connect to www host, tunneling can't be used"); console.println(""); } } installLogo(); splashScreen(); initRandomSeed(); startSSHClient(false); } public void run() { boolean gotExtMsg; if (com.mindbright.util.Util.isNetscapeJava()) { try { netscape.security.PrivilegeManager.enablePrivilege("TerminalEmulator"); } catch (netscape.security.ForbiddenTargetException e) { // !!! REMOVE console.println("Unsigned applet, can only connect to www host, tunneling can't be used"); console.println(""); } } installLogo(); boolean keepRunning = true; while(keepRunning) { gotExtMsg = false; try { splashScreen(); initRandomSeed(); startSSHClient(true); if(sshStdIO.isConnected()) { // Server died on us without sending disconnect sshStdIO.serverDisconnect("\n\r\n\rServer died or connection lost"); disconnect(false); propsHandler.clearServerSetting(); } // !!! Wait for last session to close down entirely (i.e. so // disconnected gets a chance to be called...) // Thread.sleep(1000); try { propsHandler.checkSave(); } catch (IOException e) { alert("Error saving settings!"); } } catch(SSHClient.AuthFailException e) { alert("Authentication failed, " + e.getMessage()); propsHandler.clearPasswords(); } catch(WebProxyException e) { alert(e.getMessage()); propsHandler.clearPasswords(); } catch(SSHStdIO.SSHExternalMessage e) { gotExtMsg = true; String msg = e.getMessage(); // !!! REMOVE if(msg != null && msg.trim().length() > 0) { alert(e.getMessage()); } } catch(UnknownHostException e) { String host = e.getMessage(); if(propsHandler.getProperty("proxytype").equals("none")) { alert("Unknown host: " + host); } else { alert("Unknown proxy host: " + host); } propsHandler.clearServerSetting(); } catch(FileNotFoundException e) { alert("File not found: " + e.getMessage()); } catch(Exception e) { String msg = e.getMessage(); if(msg == null || msg.trim().length() == 0) msg = e.toString(); msg = "Error connecting to " + propsHandler.getProperty("server") + ", reason:\n" + "-> " + msg; alert(msg); if(SSH.DEBUGMORE) { System.err.println("If an error occured, please send the below stacktrace to mt-support@appgate.com"); e.printStackTrace(); } } catch(ThreadDeath death) { if(controller != null) controller.killAll(); controller = null; throw death; } propsHandler.passivateProperties(); activateTunnels = true; if(!gotExtMsg) { if(!propsHandler.savePasswords || usedOTP) { propsHandler.clearPasswords(); } propsHandler.currentPropsFile = null; if(!propsHandler.autoLoadProps) { propsHandler.clearPasswords(); initQuiet = false; } quiet = false; } controller = null; TerminalWin t = getTerminalWin(); if(t != null) t.setTitle(null); keepRunning = !exitOnLogout; } } private void startSSHClient(boolean shell) throws Exception { // This starts a connection to the sshd and all the related stuff... // bootSSH(shell, true); int major = 2; String proto = propsHandler.getProperty("protocol"); if("auto".equals(proto)) { sshSocket = new SSHVersionSpySocket(sshSocket); major = ((SSHVersionSpySocket)sshSocket).getMajorVersion(); } else if("ssh1".equals(proto)) { major = 1; } if(major == 1) { console.println("Warning connecting using ssh1, consider upgrading server!"); console.println(""); boot(shell, sshSocket); // !!! REMOVE if(isDumb()) System.out.println("No console..."); // Join main receiver channel thread and wait for session to end // controller.waitForExit(); } else { runSSH2Client(); } } public boolean isDumb() { return (console.getTerminal() == null); } public TerminalWin getTerminalWin() { Terminal term = console.getTerminal(); if(term != null && term instanceof TerminalWin) return (TerminalWin)term; return null; } public void showLogo() { TerminalWin t = getTerminalWin(); if(t != null) { t.showLogo(); } } public void hideLogo() { TerminalWin t = getTerminalWin(); if(t != null) { t.hideLogo(); } } public Logo getLogo() { Logo logo = null; TerminalWin t = getTerminalWin(); if(t != null) { Image img = t.getLogo(); logo = new Logo(img); } return logo; } public void updateTitle() { sshStdIO.updateTitle(); } // // SSH2Interactor interface // public String promptLine(String prompt, boolean echo) throws SSH2UserCancelException { try { if(echo) { return promptLine(prompt, ""); } else { return promptPassword(prompt); } } catch (IOException e) { throw new SSH2UserCancelException(e.getMessage()); } } public String[] promptMulti(String[] prompts, boolean[] echos) throws SSH2UserCancelException { return promptMultiFull(null, null, prompts, echos); } public String[] promptMultiFull(String name, String instruction, String[] prompts, boolean[] echos) throws SSH2UserCancelException { try { console.println(name); console.println(instruction); String[] resp = new String[prompts.length]; for(int i = 0; i < prompts.length; i++) { if(echos[i]) { resp[i] = promptLine(prompts[i], ""); } else { resp[i] = promptPassword(prompts[i]); } } return resp; } catch (IOException e) { throw new SSH2UserCancelException(e.getMessage()); } } public int promptList(String name, String instruction, String[] choices) throws SSH2UserCancelException { try { console.println(name); console.println(instruction); for(int i = 0; i < choices.length; i++) { console.println(i + ") " + choices[i]); } String choice = promptLine("Choice", "0"); return Integer.parseInt(choice); } catch (Exception e) { throw new SSH2UserCancelException(e.getMessage()); } } // // SSHInteractor interface // public void propsStateChanged(SSHPropertyHandler props) { updateMenus(); } public void startNewSession(SSHClient client) { // !!! REMOVE // Here we can have a login-dialog with proxy-info also (or configurable more than one method) // !!! } public void sessionStarted(SSHClient client) { quiet = initQuiet; } public boolean quietPrompts() { return (commandLine != null || quiet); } public boolean isVerbose() { return wantHelpInfo; } public String promptLine(String prompt, String defaultVal) throws IOException { return sshStdIO.promptLine(prompt, defaultVal, false); } public String promptPassword(String prompt) throws IOException { return sshStdIO.promptLine(prompt, "", true); } public boolean askConfirmation(String message, boolean defAnswer) { boolean confirm = false; try { confirm = askConfirmation(message, true, defAnswer); } catch (IOException e) { // !!! } return confirm; } public boolean askConfirmation(String message, boolean preferDialog, boolean defAnswer) throws IOException { boolean confirm = false; if(menus != null && preferDialog) { confirm = menus.confirmDialog(message, defAnswer); } else { String answer = promptLine(message + (defAnswer ? " ([yes]/no) " : "(yes/[no]) "), ""); if(answer.equalsIgnoreCase("yes") || answer.equals("y")) { confirm = true; } else if(answer.equals("")) { confirm = defAnswer; } } return confirm; } public boolean licenseDialog(String license) { if(license != null && menus instanceof SSHMenuHandlerFull) { return SSHMiscDialogs.confirm("MindTerm - License agreeement", license, 24, 100, "Accept", "Decline", false, ((SSHMenuHandlerFull)menus).parent, true); } return false; } public void connected(SSHClient client) { updateMenus(); console.println("Connected to server running " + srvVersionStr); } public void open(SSHClient client) { updateMenus(); updateTitle();
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -