/* most interesting part: openpty, forkpty */
static void fill_termios(struct termios *tp);
static void fill_winsize(struct winsize *wp);
JNIEXPORT jint JNICALL
Java_de_mud_jta_plugin_HandlerPTY_start
(JNIEnv *env, jobject this, jstring jcmd)
{
jclass cls = (*env)->GetObjectClass(env, this);
jfieldID fid_good, fid_fd;
const char *scmd;
char *ncmd;
jboolean good;
jint fd;
int fd_buf; /* different type from fd */
struct termios tiob;
struct winsize winb;
int rc;
scmd = (*env)->GetStringUTFChars(env, jcmd, 0);
ncmd = strdup(scmd); // We are more comfortable with free()
(*env)->ReleaseStringUTFChars(env, jcmd, scmd);
if (ncmd == NULL) {
return -1;
}
fid_good = (*env)->GetFieldID(env, cls, "good", "Z");
if (fid_good == 0) {
fprintf(stderr, "HandlerPTY.start: null FID for \"good\"\n");
free(ncmd);
return -1;
}
fid_fd = (*env)->GetFieldID(env, cls, "fd", "I");
if (fid_fd == 0) {
fprintf(stderr, "HandlerPTY.start: null FID for \"fd\"\n");
free(ncmd);
return -1;
}
good = (*env)->GetBooleanField(env, this, fid_good);
fd = (*env)->GetIntField(env, this, fid_fd);
if (good) {
/* P3 remove later */ fprintf(stderr,
"HandlerPTY.start: PTY is already open\n");
free(ncmd);
return -1;
}
/*
* At least on my system NULL is legal as PTY name.
* We use it because we do not want to use a buffer of unknown size.
*/
fill_termios(&tiob);
fill_winsize(&winb);
if ((rc = forkpty(&fd_buf, NULL, &tiob, &winb)) < 0) {
fprintf(stderr, "HandlerPTY.start: forkpty() failed\n");
free(ncmd);
return -1;
}
if (rc == 0) { /* child */
char *eargv[] = { NULL, NULL };
char *eenvp[] = { NULL };
eargv[0] = ncmd;
execve(ncmd, eargv, eenvp);
fprintf(stderr, "HandlerPTY.start: execve(%s) failed: %s\n",
ncmd, strerror(errno));
exit(1);
}
fd = fd_buf;
good = JNI_TRUE;
/* Would be nice to linger here until the child is known to be good. */
(*env)->SetBooleanField(env, this, fid_good, good);
(*env)->SetIntField(env, this, fid_fd, fd);
free(ncmd);
return 0;
}
JNIEXPORT void JNICALL
Java_de_mud_jta_plugin_HandlerPTY_close
(JNIEnv *env, jobject this)
{
jclass cls = (*env)->GetObjectClass(env, this);
jfieldID fid_good, fid_fd;
jboolean good;
jint fd;
if ((fid_good = (*env)->GetFieldID(env, cls, "good", "Z")) == 0) {
fprintf(stderr, "HandlerPTY.close: null FID for \"good\"\n");
return;
}
if ((fid_fd = (*env)->GetFieldID(env, cls, "fd", "I")) == 0) {
fprintf(stderr, "HandlerPTY.close: null FID for \"fd\"\n");
return;
}
good = (*env)->GetBooleanField(env, this, fid_good);
fd = (*env)->GetIntField(env, this, fid_fd);
if (good) {
close(fd);
good = JNI_FALSE;
}
(*env)->SetBooleanField(env, this, fid_good, good);
(*env)->SetIntField(env, this, fid_fd, fd);
}
JNIEXPORT jint JNICALL Java_de_mud_jta_plugin_HandlerPTY_read
(JNIEnv *env, jobject this, jbyteArray b)
{
jclass cls = (*env)->GetObjectClass(env, this);
jfieldID fid_good, fid_fd;
jboolean good;
jint fd;
jsize blen;
jbyte *buf;
int rc;
if ((fid_good = (*env)->GetFieldID(env, cls, "good", "Z")) == 0) {
fprintf(stderr, "HandlerPTY.read: null FID for \"good\"\n");
return -1;
}
if ((fid_fd = (*env)->GetFieldID(env, cls, "fd", "I")) == 0) {
fprintf(stderr, "HandlerPTY.read: null FID for \"fd\"\n");
return -1;
}
good = (*env)->GetBooleanField(env, this, fid_good);
fd = (*env)->GetIntField(env, this, fid_fd);
if (!good) {
printf("HandlerPTY.read: no good\n");
return -1;
}
blen = (*env)->GetArrayLength(env, b);
buf = (*env)->GetByteArrayElements(env, b, 0);
if (blen > 0) {
rc = read(fd, buf, blen);
} else {
rc = 0;
}
(*env)->ReleaseByteArrayElements(env, b, buf, 0);
if (rc < 0) {
// Dunno if we want this printout... xterm is silent here.
fprintf(stderr, "HandlerPTY.read: %s\n", strerror(errno));
return -1;
}
return rc;
}
JNIEXPORT jint JNICALL Java_de_mud_jta_plugin_HandlerPTY_write
(JNIEnv *env, jobject this, jbyteArray b)
{
jclass cls = (*env)->GetObjectClass(env, this);
jfieldID fid_good, fid_fd;
jboolean good;
jint fd;
jsize blen;
jbyte *buf;
int rc;
if ((fid_good = (*env)->GetFieldID(env, cls, "good", "Z")) == 0) {
fprintf(stderr, "HandlerPTY.write: null FID for \"good\"\n");
return -1;
}
if ((fid_fd = (*env)->GetFieldID(env, cls, "fd", "I")) == 0) {
fprintf(stderr, "HandlerPTY.write: null FID for \"fd\"\n");
return -1;
}
good = (*env)->GetBooleanField(env, this, fid_good);
fd = (*env)->GetIntField(env, this, fid_fd);
if (!good) {
printf("HandlerPTY.write: no good\n");
return -1;
}
blen = (*env)->GetArrayLength(env, b);
buf = (*env)->GetByteArrayElements(env, b, 0);
if (blen > 0) {
rc = write(fd, buf, blen);
} else {
rc = 0;
}
(*env)->ReleaseByteArrayElements(env, b, buf, 0);
if (rc < 0) {
fprintf(stderr, "HandlerPTY.write: %s\n", strerror(errno));
return -1;
}
return rc;
}
static void
fill_termios(struct termios *tp)
{
memset(tp, 0, sizeof(struct termios));
tp->c_iflag = IXON | IXOFF; /* ICRNL? */
tp->c_oflag = OPOST | ONLCR;
tp->c_cflag = CS8 | CREAD | CLOCAL | B9600; /* HUPCL? CRTSCTS? */
tp->c_lflag = ICANON | ISIG | ECHO | ECHOE | ECHOK | ECHOKE | ECHOCTL;
tp->c_cc[VSTART] = 'Q' & 0x1F;
tp->c_cc[VSTOP] = 'S' & 0x1F;
tp->c_cc[VERASE] = 0x7F;
tp->c_cc[VKILL] = 'U' & 0x1F;
tp->c_cc[VINTR] = 'C' & 0x1F;
tp->c_cc[VQUIT] = '\\' & 0x1F;
tp->c_cc[VEOF] = 'D' & 0x1F;
tp->c_cc[VSUSP] = 'Z' & 0x1F;
tp->c_cc[VWERASE] = 'W' & 0x1F;
tp->c_cc[VREPRINT] = 'R' & 0x1F;
}
static void
fill_winsize(struct winsize *wp)
{
memset(wp, 0, sizeof(struct winsize));
wp->ws_row = 24;
wp->ws_col = 80;
}
jta_2.6+dfsg.orig/jni/Makefile 0000644 0001750 0001750 00000000354 10610772601 015005 0 ustar paul paul SUBDIRS = win32 linux solaris
ARCH = linux
all:
cd $(ARCH) && $(MAKE)
clean:
set -e ; for i in $(SUBDIRS) ; do (cd $$i && $(MAKE) clean) ; done
realclean:
set -e ; for i in $(SUBDIRS) ; do (cd $$i && $(MAKE) realclean) ; done
jta_2.6+dfsg.orig/jni/win32/ 0000755 0001750 0001750 00000000000 10610772601 014305 5 ustar paul paul jta_2.6+dfsg.orig/jni/win32/Makefile 0000644 0001750 0001750 00000003157 10610772601 015753 0 ustar paul paul # This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
#
# (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
#
# Please visit http://javatelnet.org/ for updates and contact.
#
# --LICENSE NOTICE--
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
# --LICENSE NOTICE--
#
#### This makefile is incomplete! Someone please finish it.
JAVAH = /q/opt/jdk1.2.2/bin/javah
TOPDIR = ../..
SRCDIR = ../../de
CDIR = ../src
JNI_INCLUDE = -Ic:\java\include -Ic:\java\include\win32
CC = gcc
SOCFLAGS = -fPIC -c -Wall -I. $(JNI_INCLUDE)
SOLFLAGS = -shared -lutil
all: jtapty.dll
#
# On Win32, the following command builds a dynamic link library hello.dll using Microsoft Visual C++ 4.0:
#
# cl -Ic:\java\include -Ic:\java\include\win32
# -LD HelloWorldImp.c -Fehello.dll
#
# On Linux libutil contains forkpty()
#
#
# This will most likely not be easily portable to Win32, except probably
# using cygwin. Do not expect it to work.
clean:
realclean: clean
# EOF
jta_2.6+dfsg.orig/jni/solaris/ 0000755 0001750 0001750 00000000000 10610772601 015017 5 ustar paul paul jta_2.6+dfsg.orig/jni/solaris/Makefile 0000644 0001750 0001750 00000003230 10610772601 016455 0 ustar paul paul # This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
#
# (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
#
# Please visit http://javatelnet.org/ for updates and contact.
#
# --LICENSE NOTICE--
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
# --LICENSE NOTICE--
#
### This makefile is incomplete. Please adjust it to your environment.
JAVAH = /usr/java/bin/javah
TOPDIR = ../..
SRCDIR = ../../de
CDIR = ../src
JNI_INCLUDE = -I/usr/java/include -I/usr/java/include/linux
CC = /opt/SUNWspro/SC5.0/bin/cc
SOCFLAGS = -c -I. $(JNI_INCLUDE) -G
SOLFLAGS = -G
#
# major rules to create files
#
all: libjtapty.so
HandlerPTY.h: $(SRCDIR)/mud/jta/plugin/HandlerPTY.class
$(JAVAH) -force -classpath $(TOPDIR) -o $@ de.mud.jta.plugin.HandlerPTY
libjtapty.so: HandlerPTY.lo
$(CC) $(SOLFLAGS) -o $@ HandlerPTY.lo
HandlerPTY.lo: $(CDIR)/HandlerPTY.c HandlerPTY.h
$(CC) $(SOCFLAGS) -o $@ $(CDIR)/HandlerPTY.c
clean:
-find . -name \*~ -print | xargs rm -f
-rm -f HandlerPTY.h libjtapty.so
realclean: clean
# EOF
jta_2.6+dfsg.orig/jni/linux/ 0000755 0001750 0001750 00000000000 10610772601 014502 5 ustar paul paul jta_2.6+dfsg.orig/jni/linux/Makefile 0000644 0001750 0001750 00000003244 10610772601 016145 0 ustar paul paul # This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
#
# (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
#
# Please visit http://javatelnet.org/ for updates and contact.
#
# --LICENSE NOTICE--
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
# --LICENSE NOTICE--
#
JAVAH = javah
TOPDIR = ../..
SRCDIR = ../../de
CDIR = ../src
JNI_INCLUDE = -I/usr/lib/j2sdk1.3/include -I/usr/lib/j2sdk1.3/include/linux
# Linux (glibc 2.1.3)
# libutil contains forkpty()
CC = gcc
SOCFLAGS = -fPIC -c -Wall -I. $(JNI_INCLUDE)
SOLFLAGS = -shared -lutil
#
# major rules to create files
#
all: libjtapty.so
HandlerPTY.h: $(SRCDIR)/mud/jta/plugin/HandlerPTY.class
$(JAVAH) -classpath /usr/java/lib/classes.zip:$(TOPDIR) -o $@ de.mud.jta.plugin.HandlerPTY
libjtapty.so: HandlerPTY.lo
$(CC) $(SOLFLAGS) -o $@ HandlerPTY.lo
HandlerPTY.lo: $(CDIR)/HandlerPTY.c HandlerPTY.h
$(CC) $(SOCFLAGS) -o $@ $(CDIR)/HandlerPTY.c
clean:
-find . -name \*~ -print | xargs rm -f
-rm -f HandlerPTY.h HandlerPTY.lo libjtapty.so
realclean: clean
# EOF
jta_2.6+dfsg.orig/de/ 0000755 0001750 0001750 00000000000 10610772601 013153 5 ustar paul paul jta_2.6+dfsg.orig/de/mud/ 0000755 0001750 0001750 00000000000 10610772601 013740 5 ustar paul paul jta_2.6+dfsg.orig/de/mud/telnet/ 0000755 0001750 0001750 00000000000 10610772601 015233 5 ustar paul paul jta_2.6+dfsg.orig/de/mud/telnet/ScriptHandler.java 0000644 0001750 0001750 00000004676 10610772601 020655 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.telnet;
import java.util.Vector;
/**
* A script handler, that tries to match strings and returns true when
* it found the string it searched for.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: ScriptHandler.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class ScriptHandler {
/** debugging level */
private final static int debug = 0;
private int matchPos; // current position in the match
private byte[] match; // the current bytes to look for
private boolean done = true; // nothing to look for!
/**
* Setup the parser using the passed string.
* @param match the string to look for
*/
public void setup(String match) {
if(match == null) return;
this.match = match.getBytes();
matchPos = 0;
done = false;
}
/**
* Try to match the byte array s against the match string.
* @param s the array of bytes to match against
* @param length the amount of bytes in the array
* @return true if the string was found, else false
*/
public boolean match(byte[] s, int length) {
if(done) return true;
for(int i = 0; !done && i < length; i++) {
if(s[i] == match[matchPos]) {
// the whole thing matched so, return the match answer
// and reset to use the next match
if(++matchPos >= match.length) {
done = true;
return true;
}
} else
matchPos = 0; // get back to the beginning
}
return false;
}
}
jta_2.6+dfsg.orig/de/mud/telnet/TelnetWrapper.java 0000644 0001750 0001750 00000010404 10610772601 020671 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.telnet;
import java.io.InputStream;
import java.io.OutputStream;
import java.io.IOException;
import java.net.Socket;
import java.util.Vector;
import java.util.Properties;
import java.awt.Dimension;
import de.mud.jta.Wrapper;
/**
* The telnet wrapper is a sample class for how to use the telnet protocol
* handler of the JTA source package. To write a program using the wrapper
* you may use the following piece of code as an example:
*
* TelnetWrapper telnet = new TelnetWrapper();
* try {
* telnet.connect(args[0], 23);
* telnet.login("user", "password");
* telnet.setPrompt("user@host");
* telnet.waitfor("Terminal type?");
* telnet.send("dumb");
* System.out.println(telnet.send("ls -l"));
* } catch(java.io.IOException e) {
* e.printStackTrace();
* }
*
* Please keep in mind that the password is visible for anyone who can
* download the class file. So use this only for public accounts or if
* you are absolutely sure nobody can see the file.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: TelnetWrapper.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class TelnetWrapper extends Wrapper {
protected TelnetProtocolHandler handler;
/** debugging level */
private final static int debug = 0;
public TelnetWrapper() {
handler = new TelnetProtocolHandler() {
/** get the current terminal type */
public String getTerminalType() {
return "vt320";
}
/** get the current window size */
public Dimension getWindowSize() {
return new Dimension(80, 25);
}
/** notify about local echo */
public void setLocalEcho(boolean echo) {
/* EMPTY */
}
/** write data to our back end */
public void write(byte[] b) throws IOException {
out.write(b);
}
/** sent on IAC EOR (prompt terminator for remote access systems). */
public void notifyEndOfRecord() {
}
};
}
public TelnetProtocolHandler getHandler() {
return handler;
}
public void connect(String host, int port) throws IOException {
super.connect(host, port);
handler.reset();
}
/**
* Send a command to the remote host. A newline is appended and if
* a prompt is set it will return the resulting data until the prompt
* is encountered.
* @param cmd the command
* @return output of the command or null if no prompt is set
*/
public String send(String cmd) throws IOException {
byte arr[];
arr = (cmd + "\n").getBytes();
handler.transpose(arr);
if (getPrompt() != null)
return waitfor(getPrompt());
return null;
}
/**
* Read data from the socket and use telnet negotiation before returning
* the data read.
* @param b the input buffer to read in
* @return the amount of bytes read
*/
public int read(byte[] b) throws IOException {
/* process all already read bytes */
int n;
do {
n = handler.negotiate(b);
if (n>0)
return n;
} while (n==0);
while (n <= 0) {
do {
n = handler.negotiate(b);
if (n > 0)
return n;
} while (n == 0);
n = in.read(b);
if (n < 0)
return n;
handler.inputfeed(b, n);
n = handler.negotiate(b);
}
return n;
}
}
jta_2.6+dfsg.orig/de/mud/telnet/TelnetProtocolHandler.java 0000644 0001750 0001750 00000046556 10610772601 022371 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.telnet;
import java.io.IOException;
import java.awt.Dimension;
import java.lang.Byte;
/**
* This is a telnet protocol handler. The handler needs implementations
* for several methods to handle the telnet options and to be able to
* read and write the buffer.
*
* Maintainer: Marcus Meissner
*
* @version $Id: TelnetProtocolHandler.java 503 2005-10-24 07:34:13Z marcus $
* @author Matthias L. Jugel, Marcus Meissner
*/
public abstract class TelnetProtocolHandler {
/** contains the current revision id */
public final static String ID = "$Id: TelnetProtocolHandler.java 503 2005-10-24 07:34:13Z marcus $";
/** debug level */
private final static int debug = 0;
/** temporary buffer for data-telnetstuff-data transformation */
private byte[] tempbuf = new byte[0];
/** the data sent on pressing \n */
private byte[] crlf = new byte[2];
/** the data sent on pressing \r */
private byte[] cr = new byte[2];
/**
* Create a new telnet protocol handler.
*/
public TelnetProtocolHandler() {
reset();
crlf[0] = 13; crlf[1] = 10;
cr[0] = 13; cr[1] = 0;
}
/**
* Get the current terminal type for TTYPE telnet option.
* @return the string id of the terminal
*/
protected abstract String getTerminalType();
/**
* Get the current window size of the terminal for the
* NAWS telnet option.
* @return the size of the terminal as Dimension
*/
protected abstract Dimension getWindowSize();
/**
* Set the local echo option of telnet.
* @param echo true for local echo, false for no local echo
*/
protected abstract void setLocalEcho(boolean echo);
/**
* Generate an EOR (end of record) request. For use by prompt displaying.
*/
protected abstract void notifyEndOfRecord();
/**
* Send data to the remote host.
* @param b array of bytes to send
*/
protected abstract void write(byte[] b) throws IOException;
/**
* Send one byte to the remote host.
* @param b the byte to be sent
* @see #write(byte[] b)
*/
private static byte[] one = new byte[1];
private void write(byte b) throws IOException {
one[0] = b;
write(one);
}
/**
* Reset the protocol handler. This may be necessary after the
* connection was closed or some other problem occured.
*/
public void reset() {
neg_state = 0;
receivedDX = new byte[256];
sentDX = new byte[256];
receivedWX = new byte[256];
sentWX = new byte[256];
}
// ===================================================================
// the actual negotiation handling for the telnet protocol follows:
// ===================================================================
/** state variable for telnet negotiation reader */
private byte neg_state = 0;
/** constants for the negotiation state */
private final static byte STATE_DATA = 0;
private final static byte STATE_IAC = 1;
private final static byte STATE_IACSB = 2;
private final static byte STATE_IACWILL = 3;
private final static byte STATE_IACDO = 4;
private final static byte STATE_IACWONT = 5;
private final static byte STATE_IACDONT = 6;
private final static byte STATE_IACSBIAC = 7;
private final static byte STATE_IACSBDATA = 8;
private final static byte STATE_IACSBDATAIAC = 9;
/** What IAC SB we are handling right now */
private byte current_sb;
/** current SB negotiation buffer */
private byte[] sbbuf;
/** IAC - init sequence for telnet negotiation. */
private final static byte IAC = (byte)255;
/** [IAC] End Of Record */
private final static byte EOR = (byte)239;
/** [IAC] WILL */
private final static byte WILL = (byte)251;
/** [IAC] WONT */
private final static byte WONT = (byte)252;
/** [IAC] DO */
private final static byte DO = (byte)253;
/** [IAC] DONT */
private final static byte DONT = (byte)254;
/** [IAC] Sub Begin */
private final static byte SB = (byte)250;
/** [IAC] Sub End */
private final static byte SE = (byte)240;
/** Telnet option: binary mode */
private final static byte TELOPT_BINARY= (byte)0; /* binary mode */
/** Telnet option: echo text */
private final static byte TELOPT_ECHO = (byte)1; /* echo on/off */
/** Telnet option: sga */
private final static byte TELOPT_SGA = (byte)3; /* supress go ahead */
/** Telnet option: End Of Record */
private final static byte TELOPT_EOR = (byte)25; /* end of record */
/** Telnet option: Negotiate About Window Size */
private final static byte TELOPT_NAWS = (byte)31; /* NA-WindowSize*/
/** Telnet option: Terminal Type */
private final static byte TELOPT_TTYPE = (byte)24; /* terminal type */
private final static byte[] IACWILL = { IAC, WILL };
private final static byte[] IACWONT = { IAC, WONT };
private final static byte[] IACDO = { IAC, DO };
private final static byte[] IACDONT = { IAC, DONT };
private final static byte[] IACSB = { IAC, SB };
private final static byte[] IACSE = { IAC, SE };
/** Telnet option qualifier 'IS' */
private final static byte TELQUAL_IS = (byte)0;
/** Telnet option qualifier 'SEND' */
private final static byte TELQUAL_SEND = (byte)1;
/** What IAC DO(NT) request do we have received already ? */
private byte[] receivedDX;
/** What IAC WILL/WONT request do we have received already ? */
private byte[] receivedWX;
/** What IAC DO/DONT request do we have sent already ? */
private byte[] sentDX;
/** What IAC WILL/WONT request do we have sent already ? */
private byte[] sentWX;
/**
* Send a Telnet Escape character (IAC )
*/
public void sendTelnetControl(byte code)
throws IOException {
byte[] b = new byte[2];
b[0] = IAC;
b[1] = code;
write(b);
}
/**
* Send the new Window Size (via NAWS)
*/
public void setWindowSize(int columns,int rows)
throws IOException {
if(debug > 2) System.err.println("sending NAWS");
if (receivedDX[TELOPT_NAWS] != DO) {
System.err.println("not allowed to send NAWS? (DONT NAWS)");
return;
}
write(IAC);write(SB);write(TELOPT_NAWS);
write((byte) (columns >> 8));
write((byte) (columns & 0xff));
write((byte) (rows >> 8));
write((byte) (rows & 0xff));
write(IAC);write(SE);
}
/**
* Handle an incoming IAC SB <type> <bytes> IAC SE
* @param type type of SB
* @param sbata byte array as <bytes>
*/
private void handle_sb(byte type, byte[] sbdata)
throws IOException {
if(debug > 1)
System.err.println("TelnetIO.handle_sb("+type+")");
switch (type) {
case TELOPT_TTYPE:
if (sbdata.length>0 && sbdata[0]==TELQUAL_SEND) {
write(IACSB);write(TELOPT_TTYPE);write(TELQUAL_IS);
/* FIXME: need more logic here if we use
* more than one terminal type
*/
String ttype = getTerminalType();
if(ttype == null) ttype = "dumb";
write(ttype.getBytes());
write(IACSE);
}
}
}
/**
* Do not send any notifications at startup. We do not know,
* whether the remote client understands telnet protocol handling,
* so we are silent.
* (This used to send IAC WILL SGA, but this is false for a compliant
* client.)
*/
public void startup() throws IOException {
}
/**
* Transpose special telnet codes like 0xff or newlines to values
* that are compliant to the protocol. This method will also send
* the buffer immediately after transposing the data.
* @param buf the data buffer to be sent
*/
public void transpose(byte[] buf) throws IOException {
int i;
byte[] nbuf,xbuf;
int nbufptr=0;
nbuf = new byte[buf.length*2]; // FIXME: buffer overflows possible
for (i = 0; i < buf.length ; i++) {
switch (buf[i]) {
// Escape IAC twice in stream ... to be telnet protocol compliant
// this is there in binary and non-binary mode.
case IAC:
nbuf[nbufptr++]=IAC;
nbuf[nbufptr++]=IAC;
break;
// We need to heed RFC 854. LF (\n) is 10, CR (\r) is 13
// we assume that the Terminal sends \n for lf+cr and \r for just cr
// linefeed+carriage return is CR LF */
case 10: // \n
if (receivedDX[TELOPT_BINARY + 128 ] != DO) {
while (nbuf.length - nbufptr < crlf.length) {
xbuf = new byte[nbuf.length*2];
System.arraycopy(nbuf,0,xbuf,0,nbufptr);
nbuf = xbuf;
}
for (int j=0;jRFC-Telnet
* @param nbuf the byte buffer put out after negotiation
* @return number of bytes processed, 0 for none, and -1 for end of buffer.
*/
public int negotiate(byte nbuf[])
throws IOException
{
int count = tempbuf.length;
byte[] buf = tempbuf;
byte sendbuf[] = new byte[3];
byte b,reply;
int boffset = 0, noffset = 0;
boolean dobreak = false;
if (count == 0) // buffer is empty.
return -1;
while(!dobreak && (boffset < count) && (noffset < nbuf.length)) {
b=buf[boffset++];
// of course, byte is a signed entity (-128 -> 127)
// but apparently the SGI Netscape 3.0 doesn't seem
// to care and provides happily values up to 255
if (b>=128)
b=(byte)((int)b-256);
if(debug > 2) {
Byte B = new Byte(b);
System.err.print("byte: " + B.intValue()+ " ");
}
switch (neg_state) {
case STATE_DATA:
if (b==IAC) {
neg_state = STATE_IAC;
dobreak = true; // leave the loop so we can sync.
} else
nbuf[noffset++]=b;
break;
case STATE_IAC:
switch (b) {
case IAC:
if(debug > 2) System.err.print("IAC ");
neg_state = STATE_DATA;
nbuf[noffset++]=IAC;
break;
case WILL:
if(debug > 2) System.err.print("WILL ");
neg_state = STATE_IACWILL;
break;
case WONT:
if(debug > 2) System.err.print("WONT ");
neg_state = STATE_IACWONT;
break;
case DONT:
if(debug > 2) System.err.print("DONT ");
neg_state = STATE_IACDONT;
break;
case DO:
if(debug > 2) System.err.print("DO ");
neg_state = STATE_IACDO;
break;
case EOR:
if(debug > 1) System.err.print("EOR ");
notifyEndOfRecord();
dobreak = true; // leave the loop so we can sync.
neg_state = STATE_DATA;
break;
case SB:
if(debug > 2) System.err.print("SB ");
neg_state = STATE_IACSB;
break;
default:
if(debug > 2) System.err.print(" ");
neg_state = STATE_DATA;
break;
}
break;
case STATE_IACWILL:
switch(b) {
case TELOPT_ECHO:
if(debug > 2) System.err.println("ECHO");
reply = DO;
setLocalEcho(false);
break;
case TELOPT_SGA:
if(debug > 2) System.err.println("SGA");
reply = DO;
break;
case TELOPT_EOR:
if(debug > 2) System.err.println("EOR");
reply = DO;
break;
case TELOPT_BINARY:
if(debug > 2) System.err.println("BINARY");
reply = DO;
break;
default:
if(debug > 2) System.err.println("");
reply = DONT;
break;
}
if(debug > 1) System.err.println("<"+b+", WILL ="+WILL+">");
if (reply != sentDX[b+128] || WILL != receivedWX[b+128]) {
sendbuf[0]=IAC;
sendbuf[1]=reply;
sendbuf[2]=b;
write(sendbuf);
sentDX[b+128] = reply;
receivedWX[b+128] = WILL;
}
neg_state = STATE_DATA;
break;
case STATE_IACWONT:
switch(b) {
case TELOPT_ECHO:
if(debug > 2) System.err.println("ECHO");
setLocalEcho(true);
reply = DONT;
break;
case TELOPT_SGA:
if(debug > 2) System.err.println("SGA");
reply = DONT;
break;
case TELOPT_EOR:
if(debug > 2) System.err.println("EOR");
reply = DONT;
break;
case TELOPT_BINARY:
if(debug > 2) System.err.println("BINARY");
reply = DONT;
break;
default:
if(debug > 2) System.err.println("");
reply = DONT;
break;
}
if(reply != sentDX[b+128] || WONT != receivedWX[b+128]) {
sendbuf[0]=IAC;
sendbuf[1]=reply;
sendbuf[2]=b;
write(sendbuf);
sentDX[b+128] = reply;
receivedWX[b+128] = WILL;
}
neg_state = STATE_DATA;
break;
case STATE_IACDO:
switch (b) {
case TELOPT_ECHO:
if(debug > 2) System.err.println("ECHO");
reply = WILL;
setLocalEcho(true);
break;
case TELOPT_SGA:
if(debug > 2) System.err.println("SGA");
reply = WILL;
break;
case TELOPT_TTYPE:
if(debug > 2) System.err.println("TTYPE");
reply = WILL;
break;
case TELOPT_BINARY:
if(debug > 2) System.err.println("BINARY");
reply = WILL;
break;
case TELOPT_NAWS:
if(debug > 2) System.err.println("NAWS");
Dimension size = getWindowSize();
receivedDX[b] = DO;
if(size == null) {
// this shouldn't happen
write(IAC);
write(WONT);
write(TELOPT_NAWS);
reply = WONT;
sentWX[b] = WONT;
break;
}
reply = WILL;
sentWX[b] = WILL;
sendbuf[0]=IAC;
sendbuf[1]=WILL;
sendbuf[2]=TELOPT_NAWS;
write(sendbuf);
write(IAC);write(SB);write(TELOPT_NAWS);
write((byte) (size.width >> 8));
write((byte) (size.width & 0xff));
write((byte) (size.height >> 8));
write((byte) (size.height & 0xff));
write(IAC);write(SE);
break;
default:
if(debug > 2) System.err.println("");
reply = WONT;
break;
}
if(reply != sentWX[128+b] || DO != receivedDX[128+b]) {
sendbuf[0]=IAC;
sendbuf[1]=reply;
sendbuf[2]=b;
write(sendbuf);
sentWX[b+128] = reply;
receivedDX[b+128] = DO;
}
neg_state = STATE_DATA;
break;
case STATE_IACDONT:
switch (b) {
case TELOPT_ECHO:
if(debug > 2) System.err.println("ECHO");
reply = WONT;
setLocalEcho(false);
break;
case TELOPT_SGA:
if(debug > 2) System.err.println("SGA");
reply = WONT;
break;
case TELOPT_NAWS:
if(debug > 2) System.err.println("NAWS");
reply = WONT;
break;
case TELOPT_BINARY:
if(debug > 2) System.err.println("BINARY");
reply = WONT;
break;
default:
if(debug > 2) System.err.println("");
reply = WONT;
break;
}
if(reply != sentWX[b+128] || DONT != receivedDX[b+128]) {
write(IAC);write(reply);write(b);
sentWX[b+128] = reply;
receivedDX[b+128] = DONT;
}
neg_state = STATE_DATA;
break;
case STATE_IACSBIAC:
if(debug > 2) System.err.println(""+b+" ");
if (b == IAC) {
sbbuf = new byte[0];
current_sb = b;
neg_state = STATE_IACSBDATA;
} else {
System.err.println("(bad) "+b+" ");
neg_state = STATE_DATA;
}
break;
case STATE_IACSB:
if(debug > 2) System.err.println(""+b+" ");
switch (b) {
case IAC:
neg_state = STATE_IACSBIAC;
break;
default:
current_sb = b;
sbbuf = new byte[0];
neg_state = STATE_IACSBDATA;
break;
}
break;
case STATE_IACSBDATA:
if (debug > 2) System.err.println(""+b+" ");
switch (b) {
case IAC:
neg_state = STATE_IACSBDATAIAC;
break;
default:
byte[] xsb = new byte[sbbuf.length+1];
System.arraycopy(sbbuf,0,xsb,0,sbbuf.length);
sbbuf = xsb;
sbbuf[sbbuf.length-1] = b;
break;
}
break;
case STATE_IACSBDATAIAC:
if (debug > 2) System.err.println(""+b+" ");
switch (b) {
case IAC:
neg_state = STATE_IACSBDATA;
byte[] xsb = new byte[sbbuf.length+1];
System.arraycopy(sbbuf,0,xsb,0,sbbuf.length);
sbbuf = xsb;
sbbuf[sbbuf.length-1] = IAC;
break;
case SE:
handle_sb(current_sb,sbbuf);
current_sb = 0;
neg_state = STATE_DATA;
break;
case SB:
handle_sb(current_sb,sbbuf);
neg_state = STATE_IACSB;
break;
default:
neg_state = STATE_DATA;
break;
}
break;
default:
if (debug > 1)
System.err.println("This should not happen: "+neg_state+" ");
neg_state = STATE_DATA;
break;
}
}
// shrink tempbuf to new processed size.
byte[] xb = new byte[count-boffset];
System.arraycopy(tempbuf,boffset,xb,0,count-boffset);
tempbuf = xb;
return noffset;
}
public void inputfeed(byte[] b, int len) {
byte[] xb = new byte[tempbuf.length+len];
System.arraycopy(tempbuf,0,xb,0,tempbuf.length);
System.arraycopy(b,0,xb,tempbuf.length,len);
tempbuf = xb;
}
}
jta_2.6+dfsg.orig/de/mud/ssh/ 0000755 0001750 0001750 00000000000 10610772601 014535 5 ustar paul paul jta_2.6+dfsg.orig/de/mud/ssh/SshWrapper.java 0000644 0001750 0001750 00000012064 10610772601 017501 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.ssh;
import de.mud.telnet.ScriptHandler;
import de.mud.jta.Wrapper;
import java.io.InputStream;
import java.io.OutputStream;
import java.io.IOException;
import java.net.Socket;
import java.util.Vector;
import java.util.Properties;
import java.awt.Dimension;
/**
* The telnet ssh is a sample class for how to use the SSH protocol
* handler of the JTA source package. To write a program using the wrapper
* you may use the following piece of code as an example:
*
* SshWrapper telnet = new SshWrapper();
* try {
* ssh.connect(args[0], 23);
* ssh.login("user", "password");
* ssh.setPrompt("user@host");
* ssh.waitfor("Terminal type?");
* ssh.send("dumb");
* System.out.println(ssh.send("ls -l"));
* } catch(java.io.IOException e) {
* e.printStackTrace();
* }
*
* Please keep in mind that the password is visible for anyone who can
* download the class file. So use this only for public accounts or if
* you are absolutely sure nobody can see the file.
*
* Maintainer:Marcus Mei�ner
*
* @version $Id: SshWrapper.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class SshWrapper extends Wrapper {
protected SshIO handler;
/** debugging level */
private final static int debug = 0;
public SshWrapper() {
handler = new SshIO() {
/** get the current terminal type */
public String getTerminalType() {
return "vt320";
}
/** get the current window size */
public Dimension getWindowSize() {
return new Dimension(80,25);
}
/** notify about local echo */
public void setLocalEcho(boolean echo) {
/* EMPTY */
}
/** write data to our back end */
public void write(byte[] b) throws IOException {
out.write(b);
}
};
}
/**
* Send a command to the remote host. A newline is appended and if
* a prompt is set it will return the resulting data until the prompt
* is encountered.
* @param cmd the command
* @return output of the command or null if no prompt is set
*/
public String send(String cmd) throws IOException {
byte arr[];
arr = (cmd+"\n").getBytes();
// no write until authorization is done
for (int i=0;i \r */
arr[i] = 13;
break;
}
}
handler.sendData(new String(arr));
if(getPrompt() != null)
return waitfor(getPrompt());
return null;
}
/** Buffer for SSH input */
private byte[] buffer;
/** Position in SSH input buffer */
private int pos;
/**
* Read data from the backend and decrypt it. This is a buffering read
* as the encrypted information is usually smaller than its decrypted
* pendant. So it will not read from the backend as long as there is
* data in the buffer.
* @param b the buffer where to read the decrypted data in
* @return the amount of bytes actually read.
*/
public int read(byte[] b) throws IOException {
// Empty the buffer before we do anything else
if(buffer != null) {
int amount = ((buffer.length - pos) <= b.length) ?
buffer.length - pos : b.length;
System.arraycopy(buffer, pos, b, 0, amount);
if(pos + amount < buffer.length) {
pos += amount;
} else
buffer = null;
return amount;
}
// now that the buffer is empty let's read more data and decrypt it
int n = in.read(b);
if(n > 0) {
byte[] tmp = new byte[n];
System.arraycopy(b, 0, tmp, 0, n);
pos = 0;
buffer = handler.handleSSH(tmp);
if(debug > 0 && buffer != null && buffer.length > 0)
System.err.println("ssh: "+buffer);
if(buffer != null && buffer.length > 0) {
if(debug > 0)
System.err.println("ssh: incoming="+n+" now="+buffer.length);
int amount = buffer.length <= b.length ? buffer.length : b.length;
System.arraycopy(buffer, 0, b, 0, amount);
pos = n = amount;
if(amount == buffer.length) {
buffer = null;
pos = 0;
}
} else
return 0;
}
return n;
}
}
jta_2.6+dfsg.orig/de/mud/ssh/Cipher.java 0000644 0001750 0001750 00000004430 10610772601 016613 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.ssh;
/**
* Cipher class is the type for all other ciphers.
* @author Marcus Meissner
* @version $Id: Cipher.java 499 2005-09-29 08:24:54Z leo $
*/
public abstract class Cipher {
public static Cipher getInstance(String algorithm) {
Class c;
try {
c = Class.forName("de.mud.ssh." + algorithm);
return (Cipher) c.newInstance();
} catch (Throwable t) {
System.err.println("Cipher: unable to load instance of '" + algorithm + "'");
return null;
}
}
/**
* Encrypt source byte array using the instantiated algorithm.
*/
public byte[] encrypt(byte[] src) {
byte[] dest = new byte[src.length];
encrypt(src, 0, dest, 0, src.length);
return dest;
}
/**
* The actual encryption takes place here.
*/
public abstract void encrypt(byte[] src, int srcOff, byte[] dest, int destOff, int len);
/**
* Decrypt source byte array using the instantiated algorithm.
*/
public byte[] decrypt(byte[] src) {
byte[] dest = new byte[src.length];
decrypt(src, 0, dest, 0, src.length);
return dest;
}
/**
* The actual decryption takes place here.
*/
public abstract void decrypt(byte[] src, int srcOff, byte[] dest, int destOff, int len);
public abstract void setKey(byte[] key);
public void setKey(String key) {
setKey(key.getBytes());
}
}
jta_2.6+dfsg.orig/de/mud/ssh/SshPacket1.java 0000644 0001750 0001750 00000020330 10610772601 017344 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.ssh;
import java.math.BigInteger;
/**
* @author Marcus Meissner
* @version $Id: SshPacket1.java 499 2005-09-29 08:24:54Z leo $
*/
public class SshPacket1 extends SshPacket {
private final static boolean debug = false;
//SSH_RECEIVE_PACKET
private byte[] packet_length_array = new byte[4];
private int packet_length = 0;
private byte[] padding = null;
private byte[] crc_array = new byte[4];
private byte[] block = null;
private byte[] encryptedBlock = null; // encrypted part (Padding + Type + Data + Check)
private byte[] decryptedBlock = null; // decrypted part (Padding + Type + Data + Check)
private SshCrypto crypto = null;
public SshPacket1(SshCrypto _crypto) {
/* receiving packet */
position = 0;
phase_packet = PHASE_packet_length;
crypto = _crypto;
}
public SshPacket1(byte newType) {
setType(newType);
}
/**
* Return the mp-int at the position offset in the data
* First 2 bytes are the number of bits in the integer, msb first
* (for example, the value 0x00012345 would have 17 bits). The
* value zero has zero bits. It is permissible that the number of
* bits be larger than the real number of bits.
* The number of bits is followed by (bits + 7) / 8 bytes of binary
* data, msb first, giving the value of the integer.
*/
public byte[] getMpInt() {
return getBytes((getInt16() + 7) / 8);
}
public void putMpInt(BigInteger bi) {
byte[] mpbytes = bi.toByteArray(), xbytes;
int i;
for (i = 0; (i < mpbytes.length) && (mpbytes[i] == 0); i++) /* EMPTY */ ;
xbytes = new byte[mpbytes.length - i];
System.arraycopy(mpbytes, i, xbytes, 0, mpbytes.length - i);
putInt16(xbytes.length * 8);
putBytes(xbytes);
}
byte[] getPayLoad(SshCrypto crypto) {
byte[] data = getData();
//packet length
if (data != null)
packet_length = data.length + 5;
else
packet_length = 5;
packet_length_array[3] = (byte) (packet_length & 0xff);
packet_length_array[2] = (byte) ((packet_length >> 8) & 0xff);
packet_length_array[1] = (byte) ((packet_length >> 16) & 0xff);
packet_length_array[0] = (byte) ((packet_length >> 24) & 0xff);
//padding
padding = new byte[(8 - (packet_length % 8))];
if (crypto == null) {
for (int i = 0; i < padding.length; i++)
padding[i] = 0;
} else {
for (int i = 0; i < padding.length; i++)
padding[i] = SshMisc.getNotZeroRandomByte();
}
//Compute the crc of [ Padding, Packet type, Data ]
block = new byte[packet_length + padding.length];
System.arraycopy(padding, 0, block, 0, padding.length);
int offset = padding.length;
block[offset++] = getType();
if (packet_length > 5) {
System.arraycopy(data, 0, block, offset, data.length);
offset += data.length;
}
long crc = SshMisc.crc32(block, offset);
crc_array[3] = (byte) (crc & 0xff);
crc_array[2] = (byte) ((crc >> 8) & 0xff);
crc_array[1] = (byte) ((crc >> 16) & 0xff);
crc_array[0] = (byte) ((crc >> 24) & 0xff);
System.arraycopy(crc_array, 0, block, offset, 4);
//encrypt
if (crypto != null)
block = crypto.encrypt(block);
byte[] full = new byte[block.length + 4];
System.arraycopy(packet_length_array, 0, full, 0, 4);
System.arraycopy(block, 0, full, 4, block.length);
return full;
};
private int position = 0;
private int phase_packet = 0;
private final int PHASE_packet_length = 0;
private final int PHASE_block = 1;
public byte[] addPayload(byte[] buff) {
int boffset = 0;
byte newbuf[] = null;
while (boffset < buff.length) {
switch (phase_packet) {
// 4 bytes
// Packet length: 32 bit unsigned integer
// gives the length of the packet, not including the length field
// and padding. maximum is 262144 bytes.
case PHASE_packet_length:
packet_length_array[position++] = buff[boffset++];
if (position >= 4) {
packet_length =
(packet_length_array[3] & 0xff) +
((packet_length_array[2] & 0xff) << 8) +
((packet_length_array[1] & 0xff) << 16) +
((packet_length_array[0] & 0xff) << 24);
position = 0;
phase_packet++;
block = new byte[8 * (packet_length / 8 + 1)];
}
break; //switch (phase_packet)
//8*(packet_length/8 +1) bytes
case PHASE_block:
if (block.length > position) {
if (boffset < buff.length) {
int amount = buff.length - boffset;
if (amount > block.length - position)
amount = block.length - position;
System.arraycopy(buff, boffset, block, position, amount);
boffset += amount;
position += amount;
}
}
if (position == block.length) { //the block is complete
if (buff.length > boffset) { //there is more than 1 packet in buff
newbuf = new byte[buff.length - boffset];
System.arraycopy(buff, boffset, newbuf, 0, buff.length - boffset);
}
int blockOffset = 0;
//padding
int padding_length = (int) (8 - (packet_length % 8));
padding = new byte[padding_length];
if (crypto != null)
decryptedBlock = crypto.decrypt(block);
else
decryptedBlock = block;
if (decryptedBlock.length != padding_length + packet_length)
System.out.println("???");
for (int i = 0; i < padding.length; i++)
padding[i] = decryptedBlock[blockOffset++];
//packet type
setType(decryptedBlock[blockOffset++]);
byte[] data;
//data
if (packet_length > 5) {
data = new byte[packet_length - 5];
System.arraycopy(decryptedBlock, blockOffset, data, 0, packet_length - 5);
blockOffset += packet_length - 5;
} else
data = null;
putData(data);
//crc
for (int i = 0; i < crc_array.length; i++)
crc_array[i] = decryptedBlock[blockOffset++];
if (!checkCrc())
System.err.println("SshPacket1: CRC wrong in received packet!");
return newbuf;
}
break;
}
}
return null;
};
private boolean checkCrc() {
byte[] crc_arrayCheck = new byte[4];
long crcCheck;
crcCheck = SshMisc.crc32(decryptedBlock, decryptedBlock.length - 4);
crc_arrayCheck[3] = (byte) (crcCheck & 0xff);
crc_arrayCheck[2] = (byte) ((crcCheck >> 8) & 0xff);
crc_arrayCheck[1] = (byte) ((crcCheck >> 16) & 0xff);
crc_arrayCheck[0] = (byte) ((crcCheck >> 24) & 0xff);
if (debug) {
System.err.println(crc_arrayCheck[3] + " == " + crc_array[3]);
System.err.println(crc_arrayCheck[2] + " == " + crc_array[2]);
System.err.println(crc_arrayCheck[1] + " == " + crc_array[1]);
System.err.println(crc_arrayCheck[0] + " == " + crc_array[0]);
}
if (crc_arrayCheck[3] != crc_array[3]) return false;
if (crc_arrayCheck[2] != crc_array[2]) return false;
if (crc_arrayCheck[1] != crc_array[1]) return false;
if (crc_arrayCheck[0] != crc_array[0]) return false;
return true;
}
} //class
jta_2.6+dfsg.orig/de/mud/ssh/SshPacket.java 0000644 0001750 0001750 00000007721 10610772601 017274 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.ssh;
import java.math.BigInteger;
abstract class SshPacket {
public SshPacket() { /* nothing */
}
// Data management
protected byte[] byteArray = new byte[0];
protected int offset;
private boolean finished = false;
public byte[] getData() {
return byteArray;
}
public void putData(byte[] data) {
byteArray = data;
offset = 0;
finished = true;
}
public boolean isFinished() {
return finished;
}
abstract public byte[] addPayload(byte[] buff);
// Type
private byte packet_type;
public byte getType() {
return packet_type;
}
public void setType(byte ntype) {
packet_type = ntype;
}
public abstract void putMpInt(BigInteger bi);
public int getInt32() {
short d0 = byteArray[offset++];
short d1 = byteArray[offset++];
short d2 = byteArray[offset++];
short d3 = byteArray[offset++];
if (d0 < 0) d0 = (short) (256 + d0);
if (d1 < 0) d1 = (short) (256 + d1);
if (d2 < 0) d2 = (short) (256 + d2);
if (d3 < 0) d3 = (short) (256 + d3);
return (d0 << 24) + (d1 << 16) + (d2 << 8) + d3;
}
public int getInt16() {
short d0 = byteArray[offset++];
short d1 = byteArray[offset++];
if (d0 < 0) d0 = (short) (256 + d0);
if (d1 < 0) d1 = (short) (256 + d1);
return (d0 << 8) + d1;
}
public String getString() {
int length = getInt32();
String str = "";
for (int i = 0; i < length; i++) {
if (byteArray[offset] >= 0)
str += (char) (byteArray[offset++]);
else
str += (char) (256 + byteArray[offset++]);
}
return str;
}
public byte getByte() {
return byteArray[offset++];
}
public byte[] getBytes(int cnt) {
byte[] bytes = new byte[cnt];
System.arraycopy(byteArray, offset, bytes, 0, cnt);
offset += cnt;
return bytes;
}
private void grow(int howmuch) {
byte[] value = new byte[byteArray.length + howmuch];
System.arraycopy(byteArray, 0, value, 0, byteArray.length);
byteArray = value;
}
public void putInt16(int xint) {
int boffset = byteArray.length;
grow(2);
byteArray[boffset + 1] = (byte) ((xint) & 0xff);
byteArray[boffset] = (byte) ((xint >> 8) & 0xff);
}
public void putInt32(int xint) {
int boffset = byteArray.length;
grow(4);
byteArray[boffset + 3] = (byte) ((xint) & 0xff);
byteArray[boffset + 2] = (byte) ((xint >> 8) & 0xff);
byteArray[boffset + 1] = (byte) ((xint >> 16) & 0xff);
byteArray[boffset + 0] = (byte) ((xint >> 24) & 0xff);
}
public void putByte(byte xbyte) {
grow(1);
byteArray[byteArray.length - 1] = xbyte;
}
public void putBytes(byte[] bytes) {
int oldlen = byteArray.length;
grow(bytes.length);
System.arraycopy(bytes, 0, byteArray, oldlen, bytes.length);
}
/**
* Add a SSH String to a packet. The incore representation is a
* INT32 length
* BYTE[length] data
* @param str: The string to be added.
*/
public void putString(String str) {
putInt32(str.length());
putBytes(str.getBytes());
}
}
jta_2.6+dfsg.orig/de/mud/ssh/SshWrapperExample.java 0000644 0001750 0001750 00000003434 10610772601 021016 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.ssh;
/**
* This is an example for using the SshWrapper class. Note that the
* password here is in plaintext, so do not make this .class file
* available with your password inside it.
*
*
* Maintainer:Marcus Meissner
*
* @version $Id: SshWrapperExample.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class SshWrapperExample {
public static void main(String args[]) {
SshWrapper ssh = new SshWrapper();
try {
byte[] buffer = new byte[256];
ssh.connect(args[0], 22);
ssh.login("marcus", "xxxxx");
ssh.setPrompt("marcus");
System.out.println("after login");
ssh.send("ls -l");
ssh.read(buffer);
System.out.println(new String(buffer));
} catch (java.io.IOException e) {
e.printStackTrace();
}
}
}
jta_2.6+dfsg.orig/de/mud/ssh/NONE.java 0000644 0001750 0001750 00000002746 10610772601 016150 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.ssh;
/**
* @author Marcus Meissner
* @version $Id: NONE.java 499 2005-09-29 08:24:54Z leo $
*/
public final class NONE extends Cipher {
public void setKey(String skey) {
}
public void setKey(byte[] key) {
}
public synchronized void encrypt(byte[] src, int srcOff, byte[] dest, int destOff, int len) {
System.arraycopy(src,srcOff,dest,destOff,len);
}
public synchronized void decrypt(byte[] src, int srcOff, byte[] dest, int destOff, int len) {
System.arraycopy(src,srcOff,dest,destOff,len);
}
}
jta_2.6+dfsg.orig/de/mud/ssh/SshCrypto.java 0000644 0001750 0001750 00000013376 10610772601 017350 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.ssh;
import java.math.BigInteger;
/**
* @author Marcus Meissner
* @version $Id: SshCrypto.java 499 2005-09-29 08:24:54Z leo $
*/
public class SshCrypto {
private Cipher sndCipher,rcvCipher;
public SshCrypto(String type, final byte[] key) {
sndCipher = Cipher.getInstance(type);
rcvCipher = Cipher.getInstance(type);
// must be async for RC4. But we currently don't.
sndCipher.setKey(key);
rcvCipher.setKey(key);
}
public byte[] encrypt(byte[] block) {
return sndCipher.encrypt(block);
}
public byte[] decrypt(byte[] block) {
return rcvCipher.decrypt(block);
};
//-------------------------------------------------------------------------
static public byte[] encrypteRSAPkcs1Twice(byte[] clearData,
byte[] server_key_public_exponent,
byte[] server_key_public_modulus,
byte[] host_key_public_exponent,
byte[] host_key_public_modulus) {
// At each encryption step, a multiple-precision integer is constructed
//
// the integer is interpreted as a sequence of bytes, msb first;
// the number of bytes is the number of bytes needed to represent the modulus.
//
// cf PKCS #1: RSA Encryption Standard. Available for anonymous ftp at ftp.rsa.com.
// The sequence of byte is as follows:
// The most significant byte is zero.
// The next byte contains the value 2 (stands for public-key encrypted data)
// Then, there are non zero random bytes to fill any unused space
// a zero byte,
// and the data to be encrypted
byte[] key1exp, key1mod, key2exp, key2mod;
if (server_key_public_modulus.length < host_key_public_modulus.length) {
key1exp = server_key_public_exponent;
key1mod = server_key_public_modulus;
key2exp = host_key_public_exponent;
key2mod = host_key_public_modulus;
} else {
key1exp = host_key_public_exponent;
key1mod = host_key_public_modulus;
key2exp = server_key_public_exponent;
key2mod = server_key_public_modulus;
}
byte[] EncryptionBlock; //what will be encrypted
int offset = 0;
EncryptionBlock = new byte[key1mod.length];
EncryptionBlock[0] = 0;
EncryptionBlock[1] = 2;
offset = 2;
for (int i = 2; i < (EncryptionBlock.length - clearData.length - 1); i++)
EncryptionBlock[offset++] = SshMisc.getNotZeroRandomByte();
EncryptionBlock[offset++] = 0;
for (int i = 0; i < clearData.length; i++)
EncryptionBlock[offset++] = clearData[i];
//EncryptionBlock can be encrypted now !
BigInteger m, e, message;
byte[] messageByte;
m = new BigInteger(1, key1mod);
e = new BigInteger(1, key1exp);
message = new BigInteger(1, EncryptionBlock);
message = message.modPow(e, m); //RSA Encryption !!
byte[] messageByteTemp = message.toByteArray();
//there should be no zeroes a the begining but we have to fix it (JDK bug !!)
messageByte = new byte[key1mod.length];
int tempOffset = 0;
while (messageByteTemp[tempOffset] == 0)
tempOffset++;
for (int i = messageByte.length - messageByteTemp.length + tempOffset;
i < messageByte.length; i++)
messageByte[i] = messageByteTemp[tempOffset++];
clearData = messageByte;
//SECOND ROUND !!
offset = 0;
EncryptionBlock = new byte[key2mod.length];
EncryptionBlock[0] = 0;
EncryptionBlock[1] = 2;
offset = 2;
for (int i = 2; i < (EncryptionBlock.length - clearData.length - 1); i++)
EncryptionBlock[offset++] = SshMisc.getNotZeroRandomByte(); //random !=0
EncryptionBlock[offset++] = 0;
for (int i = 0; (i < clearData.length ) ; i++)
EncryptionBlock[offset++] = clearData[i];
//EncryptionBlock can be encrypted now !
m = new BigInteger(1, key2mod);
e = new BigInteger(1, key2exp);
message = new BigInteger(1, EncryptionBlock);
message = message.modPow(e, m);
messageByteTemp = message.toByteArray();
//there should be no zeroes a the begining but we have to fix it (JDK bug !!)
messageByte = new byte[key2mod.length];
tempOffset = 0;
while (messageByteTemp[tempOffset] == 0)
tempOffset++;
for (int i = messageByte.length - messageByteTemp.length + tempOffset;
i < messageByte.length; i++)
messageByte[i] = messageByteTemp[tempOffset++];
//Second encrypted key : encrypted_session_key //mp-int
byte[] encrypted_session_key = new byte[key2mod.length + 2];
//the lengh of the mp-int.
encrypted_session_key[1] = (byte) ((8 * key2mod.length) & 0xff);
encrypted_session_key[0] = (byte) (((8 * key2mod.length) >> 8) & 0xff);
//the mp-int
for (int i = 0; i < key2mod.length; i++)
encrypted_session_key[i + 2] = messageByte[i];
return encrypted_session_key;
};
}
jta_2.6+dfsg.orig/de/mud/ssh/SshMisc.java 0000644 0001750 0001750 00000022662 10610772601 016761 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.ssh;
import java.io.IOException;
import java.security.SecureRandom;
/**
* @author Marcus Meissner
* @version $Id: SshMisc.java 499 2005-09-29 08:24:54Z leo $
*/
public class SshMisc {
/**
* return the strint at the position offset in the data
* First 4 bytes are the length of the string, msb first (not
* including the length itself). The following "length" bytes are
* the string value. There are no terminating null characters.
*/
static public String getString(int offset, byte[] byteArray) throws IOException {
short d0 = byteArray[offset++];
short d1 = byteArray[offset++];
short d2 = byteArray[offset++];
short d3 = byteArray[offset++];
if (d0 < 0) d0 = (short) (256 + d0);
if (d1 < 0) d1 = (short) (256 + d1);
if (d2 < 0) d2 = (short) (256 + d2);
if (d3 < 0) d3 = (short) (256 + d3);
int length = d0 * 16777216 //to be checked
+ d1 * 65536
+ d2 * 256
+ d3;
String str = ""; //new String(byteArray,0);
for (int i = 0; i < length; i++) {
if (byteArray[offset] >= 0)
str += (char) (byteArray[offset++]);
else
str += (char) (256 + byteArray[offset++]);
}
return str;
}
static public byte getNotZeroRandomByte() {
byte[] randomBytes = new byte[32];
SecureRandom random = new java.security.SecureRandom(randomBytes);
while (true) {
random.nextBytes(randomBytes);
for (int i = 0; i < randomBytes.length; i++)
if (randomBytes[i] != 0)
return randomBytes[i];
}
}
static public byte[] addArrayOfBytes(byte[] a, byte[] b) {
if (a == null) return b;
if (b == null) return a;
byte[] temp = new byte[a.length + b.length];
for (int i = 0; i < a.length; i++) temp[i] = a[i];
for (int i = 0; i < b.length; i++) temp[i + a.length] = b[i];
return temp;
}
static public byte[] XORArrayOfBytes(byte[] a, byte[] b) {
if (a == null) return null;
if (b == null) return null;
if (a.length != b.length) return null;
byte[] result = new byte[a.length];
for (int i = 0; i < result.length; i++) result[i] = (byte) (((a[i] & 0xff) ^ (b[i] & 0xff)) & 0xff);// ^ xor operator
return result;
}
/**
* Return the mp-int at the position offset in the data
* First 2 bytes are the number of bits in the integer, msb first
* (for example, the value 0x00012345 would have 17 bits). The
* value zero has zero bits. It is permissible that the number of
* bits be larger than the real number of bits.
* The number of bits is followed by (bits + 7) / 8 bytes of binary
* data, msb first, giving the value of the integer.
*/
static public byte[] getMpInt(int offset, byte[] byteArray) throws IOException {
byte[] MpInt;
short d0 = byteArray[offset++];
short d1 = byteArray[offset++];
if (d0 < 0) d0 = (short) (256 + d0);
if (d1 < 0) d1 = (short) (256 + d1);
int byteLength = (d0 * 256 + d1 + 7) / 8;
MpInt = new byte[byteLength];
for (int i = 0; i < byteLength; i++) MpInt[i] = byteArray[offset++];
return MpInt;
} //getMpInt
/**
* Return a Arbitrary length binary string
* First 4 bytes are the length of the string, msb first (not
* including the length itself). The following "length" bytes are
* the string value. There are no terminating null characters.
*/
static public byte[] createString(String str) throws IOException {
int length = str.length();
byte[] value = new byte[4 + length];
value[3] = (byte) ((length) & 0xff);
value[2] = (byte) ((length >> 8) & 0xff);
value[1] = (byte) ((length >> 16) & 0xff);
value[0] = (byte) ((length >> 24) & 0xff);
byte[] strByte = str.getBytes();
for (int i = 0; i < length; i++) value[i + 4] = strByte[i];
return value;
} //createString
/**
* This table simply represent the results of eight shift/xor operations for
* all combinations of data and CRC register values. In other words, it caches
* all the possible resulting values such that they won't need to be computed.
*/
static private long crc32_tab[] = {
0x00000000L, 0x77073096L, 0xee0e612cL, 0x990951baL, 0x076dc419L,
0x706af48fL, 0xe963a535L, 0x9e6495a3L, 0x0edb8832L, 0x79dcb8a4L,
0xe0d5e91eL, 0x97d2d988L, 0x09b64c2bL, 0x7eb17cbdL, 0xe7b82d07L,
0x90bf1d91L, 0x1db71064L, 0x6ab020f2L, 0xf3b97148L, 0x84be41deL,
0x1adad47dL, 0x6ddde4ebL, 0xf4d4b551L, 0x83d385c7L, 0x136c9856L,
0x646ba8c0L, 0xfd62f97aL, 0x8a65c9ecL, 0x14015c4fL, 0x63066cd9L,
0xfa0f3d63L, 0x8d080df5L, 0x3b6e20c8L, 0x4c69105eL, 0xd56041e4L,
0xa2677172L, 0x3c03e4d1L, 0x4b04d447L, 0xd20d85fdL, 0xa50ab56bL,
0x35b5a8faL, 0x42b2986cL, 0xdbbbc9d6L, 0xacbcf940L, 0x32d86ce3L,
0x45df5c75L, 0xdcd60dcfL, 0xabd13d59L, 0x26d930acL, 0x51de003aL,
0xc8d75180L, 0xbfd06116L, 0x21b4f4b5L, 0x56b3c423L, 0xcfba9599L,
0xb8bda50fL, 0x2802b89eL, 0x5f058808L, 0xc60cd9b2L, 0xb10be924L,
0x2f6f7c87L, 0x58684c11L, 0xc1611dabL, 0xb6662d3dL, 0x76dc4190L,
0x01db7106L, 0x98d220bcL, 0xefd5102aL, 0x71b18589L, 0x06b6b51fL,
0x9fbfe4a5L, 0xe8b8d433L, 0x7807c9a2L, 0x0f00f934L, 0x9609a88eL,
0xe10e9818L, 0x7f6a0dbbL, 0x086d3d2dL, 0x91646c97L, 0xe6635c01L,
0x6b6b51f4L, 0x1c6c6162L, 0x856530d8L, 0xf262004eL, 0x6c0695edL,
0x1b01a57bL, 0x8208f4c1L, 0xf50fc457L, 0x65b0d9c6L, 0x12b7e950L,
0x8bbeb8eaL, 0xfcb9887cL, 0x62dd1ddfL, 0x15da2d49L, 0x8cd37cf3L,
0xfbd44c65L, 0x4db26158L, 0x3ab551ceL, 0xa3bc0074L, 0xd4bb30e2L,
0x4adfa541L, 0x3dd895d7L, 0xa4d1c46dL, 0xd3d6f4fbL, 0x4369e96aL,
0x346ed9fcL, 0xad678846L, 0xda60b8d0L, 0x44042d73L, 0x33031de5L,
0xaa0a4c5fL, 0xdd0d7cc9L, 0x5005713cL, 0x270241aaL, 0xbe0b1010L,
0xc90c2086L, 0x5768b525L, 0x206f85b3L, 0xb966d409L, 0xce61e49fL,
0x5edef90eL, 0x29d9c998L, 0xb0d09822L, 0xc7d7a8b4L, 0x59b33d17L,
0x2eb40d81L, 0xb7bd5c3bL, 0xc0ba6cadL, 0xedb88320L, 0x9abfb3b6L,
0x03b6e20cL, 0x74b1d29aL, 0xead54739L, 0x9dd277afL, 0x04db2615L,
0x73dc1683L, 0xe3630b12L, 0x94643b84L, 0x0d6d6a3eL, 0x7a6a5aa8L,
0xe40ecf0bL, 0x9309ff9dL, 0x0a00ae27L, 0x7d079eb1L, 0xf00f9344L,
0x8708a3d2L, 0x1e01f268L, 0x6906c2feL, 0xf762575dL, 0x806567cbL,
0x196c3671L, 0x6e6b06e7L, 0xfed41b76L, 0x89d32be0L, 0x10da7a5aL,
0x67dd4accL, 0xf9b9df6fL, 0x8ebeeff9L, 0x17b7be43L, 0x60b08ed5L,
0xd6d6a3e8L, 0xa1d1937eL, 0x38d8c2c4L, 0x4fdff252L, 0xd1bb67f1L,
0xa6bc5767L, 0x3fb506ddL, 0x48b2364bL, 0xd80d2bdaL, 0xaf0a1b4cL,
0x36034af6L, 0x41047a60L, 0xdf60efc3L, 0xa867df55L, 0x316e8eefL,
0x4669be79L, 0xcb61b38cL, 0xbc66831aL, 0x256fd2a0L, 0x5268e236L,
0xcc0c7795L, 0xbb0b4703L, 0x220216b9L, 0x5505262fL, 0xc5ba3bbeL,
0xb2bd0b28L, 0x2bb45a92L, 0x5cb36a04L, 0xc2d7ffa7L, 0xb5d0cf31L,
0x2cd99e8bL, 0x5bdeae1dL, 0x9b64c2b0L, 0xec63f226L, 0x756aa39cL,
0x026d930aL, 0x9c0906a9L, 0xeb0e363fL, 0x72076785L, 0x05005713L,
0x95bf4a82L, 0xe2b87a14L, 0x7bb12baeL, 0x0cb61b38L, 0x92d28e9bL,
0xe5d5be0dL, 0x7cdcefb7L, 0x0bdbdf21L, 0x86d3d2d4L, 0xf1d4e242L,
0x68ddb3f8L, 0x1fda836eL, 0x81be16cdL, 0xf6b9265bL, 0x6fb077e1L,
0x18b74777L, 0x88085ae6L, 0xff0f6a70L, 0x66063bcaL, 0x11010b5cL,
0x8f659effL, 0xf862ae69L, 0x616bffd3L, 0x166ccf45L, 0xa00ae278L,
0xd70dd2eeL, 0x4e048354L, 0x3903b3c2L, 0xa7672661L, 0xd06016f7L,
0x4969474dL, 0x3e6e77dbL, 0xaed16a4aL, 0xd9d65adcL, 0x40df0b66L,
0x37d83bf0L, 0xa9bcae53L, 0xdebb9ec5L, 0x47b2cf7fL, 0x30b5ffe9L,
0xbdbdf21cL, 0xcabac28aL, 0x53b39330L, 0x24b4a3a6L, 0xbad03605L,
0xcdd70693L, 0x54de5729L, 0x23d967bfL, 0xb3667a2eL, 0xc4614ab8L,
0x5d681b02L, 0x2a6f2b94L, 0xb40bbe37L, 0xc30c8ea1L, 0x5a05df1bL,
0x2d02ef8dL
};
/**
* Compute the crc Cyclic Redundancy Check, with the polynomial 0xedb88320,
* The polynomial is X^32+X^26+X^23+X^22+X^16+X^12+X^11+X^10+X^8+X^7+X^5+X^4+X^2+X^1+X^0
* We take it "backwards" and put the highest-order term in the lowest-order bit.
* The X^32 term is "implied"; the LSB is the X^31 term, etc.
* The X^0 term (usually shown as "+1") results in the MSB being 1.
* so the poly is 0x04c11db7 (used for Ethernet)
* The buf will be the Padding, Packet type, and Data fields.
* The crc is computed before any encryption.
* R =X^n * M rem P M message P polynomial crc R : crc calculated.
* T(x) = x^n * M(x) + R(x) property: T rem P = 0
*/
// Return a 32-bit CRC of the byte using the feedback terms table
static public long crc32(byte[] s, int len) {
int i;
long crc32val = 0;
for (i = 0; i < len; i++) {
crc32val =
crc32_tab[(int) ((crc32val ^ s[i]) & 0xff)] ^ (crc32val >> 8);
}
return crc32val;
}
}
jta_2.6+dfsg.orig/de/mud/ssh/SshIO.java 0000644 0001750 0001750 00000073666 10610772601 016407 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.ssh;
import java.io.IOException;
import java.math.BigInteger;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.security.SecureRandom;
/**
* Secure Shell IO
* @author Marcus Meissner
* @version $Id: SshIO.java 506 2005-10-25 10:07:21Z marcus $
*/
public abstract class SshIO {
private static MessageDigest md5;
static {
try {
md5 = MessageDigest.getInstance("MD5");
} catch (NoSuchAlgorithmException e) {
System.err.println("SshIO: unable to load message digest algorithm: "+e);
e.printStackTrace();
}
}
/**
* variables for the connection
*/
private String idstr = ""; //("SSH-.-\n")
private String idstr_sent = "SSH/JTA (c) Marcus Meissner, Matthias L. Jugel\n";
/**
* Debug level. This results in additional diagnostic messages on the
* java console.
*/
private static int debug = 0;
/**
* State variable for Ssh negotiation reader
*/
private SshCrypto crypto = null;
String cipher_type = "IDEA";
private int remotemajor, remoteminor;
private int mymajor, myminor;
private int useprotocol;
private String login = "", password = "";
//nobody is to access those fields : better to use pivate, nobody knows :-)
public String dataToSend = null;
public String hashHostKey = null; // equals to the applet parameter if any
byte lastPacketSentType;
// phase : handleBytes
private int phase = 0;
private final int PHASE_INIT = 0;
private final int PHASE_SSH_RECEIVE_PACKET = 1;
// SSH v2 RSA
BigInteger rsa_e, rsa_n;
//handlePacket
//messages
// The supported packet types and the corresponding message numbers are
// given in the following table. Messages with _MSG_ in their name may
// be sent by either side. Messages with _CMSG_ are only sent by the
// client, and messages with _SMSG_ only by the server.
//
private final byte SSH_MSG_DISCONNECT = 1;
private final byte SSH_SMSG_PUBLIC_KEY = 2;
private final byte SSH_CMSG_SESSION_KEY = 3;
private final byte SSH_CMSG_USER = 4;
private final byte SSH_CMSG_AUTH_PASSWORD = 9;
private final byte SSH_CMSG_REQUEST_PTY = 10;
private final byte SSH_CMSG_WINDOW_SIZE = 11;
private final byte SSH_CMSG_EXEC_SHELL = 12;
private final byte SSH_SMSG_SUCCESS = 14;
private final byte SSH_SMSG_FAILURE = 15;
private final byte SSH_CMSG_STDIN_DATA = 16;
private final byte SSH_SMSG_STDOUT_DATA = 17;
private final byte SSH_SMSG_STDERR_DATA = 18;
private final byte SSH_SMSG_EXITSTATUS = 20;
private final byte SSH_MSG_IGNORE = 32;
private final byte SSH_CMSG_EXIT_CONFIRMATION = 33;
private final byte SSH_MSG_DEBUG = 36;
/* SSH v2 stuff */
private final byte SSH2_MSG_DISCONNECT = 1;
private final byte SSH2_MSG_IGNORE = 2;
private final byte SSH2_MSG_SERVICE_REQUEST = 5;
private final byte SSH2_MSG_SERVICE_ACCEPT = 6;
private final byte SSH2_MSG_KEXINIT = 20;
private final byte SSH2_MSG_NEWKEYS = 21;
private final byte SSH2_MSG_KEXDH_INIT = 30;
private final byte SSH2_MSG_KEXDH_REPLY = 31;
private String kexalgs, hostkeyalgs, encalgs2c, encalgc2s, macalgs2c, macalgc2s, compalgc2s, compalgs2c, langc2s, langs2;
private int outgoingseq = 0, incomingseq = 0;
//
// encryption types
//
private int SSH_CIPHER_NONE = 0; // No encryption
private int SSH_CIPHER_IDEA = 1; // IDEA in CFB mode (patented)
private int SSH_CIPHER_DES = 2; // DES in CBC mode
private int SSH_CIPHER_3DES = 3; // Triple-DES in CBC mode
private int SSH_CIPHER_TSS = 4; // An experimental stream cipher
private int SSH_CIPHER_RC4 = 5; // RC4 (patented)
private int SSH_CIPHER_BLOWFISH = 6; // Bruce Scheiers blowfish (public d)
//
// authentication methods
//
private final int SSH_AUTH_RHOSTS = 1; //.rhosts or /etc/hosts.equiv
private final int SSH_AUTH_RSA = 2; //pure RSA authentication
private final int SSH_AUTH_PASSWORD = 3; //password authentication, implemented !
private final int SSH_AUTH_RHOSTS_RSA = 4; //.rhosts with RSA host authentication
private boolean cansenddata = false;
/**
* Initialise SshIO
*/
public SshIO() {
crypto = null;
}
public void setLogin(String user) {
if (user == null) user = "";
login = user;
}
public void setPassword(String password) {
if (password == null) password = "";
this.password = password;
}
SshPacket currentpacket;
protected abstract void write(byte[] buf) throws IOException;
public abstract String getTerminalType();
byte[] one = new byte[1];
private void write(byte b) throws IOException {
one[0] = b;
write(one);
}
public void disconnect() {
// System.err.println("In Disconnect");
idstr = "";
login = "";
password = "";
phase = 0;
crypto = null;
}
public void setWindowSize(int columns,int rows)
throws IOException {
if (phase == PHASE_INIT) {
System.err.println("sshio:setWindowSize(), sizing in init phase not supported.\n");
}
if (debug>1) System.err.println("SSHIO:setWindowSize("+columns+","+rows+")");
Send_SSH_CMSG_WINDOW_SIZE(columns,rows);
}
synchronized public void sendData(String str) throws IOException {
if (debug > 1) System.out.println("SshIO.send(" + str + ")");
if (dataToSend == null)
dataToSend = str;
else
dataToSend += str;
if (cansenddata) {
Send_SSH_CMSG_STDIN_DATA(dataToSend);
dataToSend = null;
}
}
/**
* Read data from the remote host. Blocks until data is available.
*
* Returns an array of bytes that will be displayed.
*
*/
public byte[] handleSSH(byte buff[])
throws IOException {
byte[] rest;
String result;
if (debug > 1)
System.out.println("SshIO.getPacket(" + buff + "," + buff.length + ")");
if (phase == PHASE_INIT) {
byte b; // of course, byte is a signed entity (-128 -> 127)
int boffset = 0; // offset into the buffer received
while (boffset < buff.length) {
b = buff[boffset++];
// both sides MUST send an identification string of the form
// "SSH-protoversion-softwareversion comments",
// followed by newline character(ascii 10 = '\n' or '\r')
idstr += (char) b;
if (b == '\n') {
if (!idstr.substring(0, 4).equals("SSH-")) {
// we need to ignore lines of data that precede the idstr
if (debug > 0)
System.out.print("Received data line: " + idstr);
idstr = "";
continue;
}
phase++;
remotemajor = Integer.parseInt(idstr.substring(4, 5));
String minorverstr = idstr.substring(6, 8);
if (!Character.isDigit(minorverstr.charAt(1)))
minorverstr = minorverstr.substring(0, 1);
remoteminor = Integer.parseInt(minorverstr);
System.out.println("remotemajor " + remotemajor);
System.out.println("remoteminor " + remoteminor);
if (remotemajor == 2) {
mymajor = 2;
myminor = 0;
useprotocol = 2;
} else {
if (false && (remoteminor == 99)) {
mymajor = 2;
myminor = 0;
useprotocol = 2;
} else {
mymajor = 1;
myminor = 5;
useprotocol = 1;
}
}
// this is how we tell the remote server what protocol we use.
idstr_sent = "SSH-" + mymajor + "." + myminor + "-" + idstr_sent;
write(idstr_sent.getBytes());
if (useprotocol == 2)
currentpacket = new SshPacket2(null);
else
currentpacket = new SshPacket1(null);
}
}
if (boffset == buff.length)
return "".getBytes();
return "Must not have left over data after PHASE_INIT!\n".getBytes();
}
result = "";
rest = currentpacket.addPayload(buff);
if (currentpacket.isFinished()) {
if (useprotocol == 1) {
result = result + handlePacket1((SshPacket1) currentpacket);
currentpacket = new SshPacket1(crypto);
} else {
result = result + handlePacket2((SshPacket2) currentpacket);
currentpacket = new SshPacket2(crypto);
}
}
while (rest != null) {
rest = currentpacket.addPayload(rest);
if (currentpacket.isFinished()) {
// the packet is finished, otherwise we would not have got a rest
if (useprotocol == 1) {
result = result + handlePacket1((SshPacket1) currentpacket);
currentpacket = new SshPacket1(crypto);
} else {
result = result + handlePacket2((SshPacket2) currentpacket);
currentpacket = new SshPacket2(crypto);
}
}
}
return result.getBytes();
}
/**
* Handle SSH protocol Version 2
*
* @param p the packet we will process here.
* @return a array of bytes
*/
private String handlePacket2(SshPacket2 p)
throws IOException {
switch (p.getType()) {
case SSH2_MSG_IGNORE:
System.out.println("SSH2: SSH2_MSG_IGNORE");
break;
case SSH2_MSG_DISCONNECT:
int discreason = p.getInt32();
String discreason1 = p.getString();
/*String discreason2 = p.getString();*/
System.out.println("SSH2: SSH2_MSG_DISCONNECT(" + discreason + "," + discreason1 + "," + /*discreason2+*/")");
return "\nSSH2 disconnect: " + discreason1 + "\n";
case SSH2_MSG_NEWKEYS:
{
System.out.println("SSH2: SSH2_MSG_NEWKEYS");
sendPacket2(new SshPacket2(SSH2_MSG_NEWKEYS));
byte[] session_key = new byte[16];
crypto = new SshCrypto(cipher_type, session_key);
SshPacket2 pn = new SshPacket2(SSH2_MSG_SERVICE_REQUEST);
pn.putString("ssh-userauth");
sendPacket2(pn);
break;
}
case SSH2_MSG_SERVICE_ACCEPT:
{
System.out.println("Service Accept: " + p.getString());
break;
}
case SSH2_MSG_KEXINIT:
{
byte[] fupp;
System.out.println("SSH2: SSH2_MSG_KEXINIT");
byte kexcookie[] = p.getBytes(16); // unused.
String kexalgs = p.getString();
System.out.println("- " + kexalgs);
String hostkeyalgs = p.getString();
System.out.println("- " + hostkeyalgs);
String encalgc2s = p.getString();
System.out.println("- " + encalgc2s);
String encalgs2c = p.getString();
System.out.println("- " + encalgs2c);
String macalgc2s = p.getString();
System.out.println("- " + macalgc2s);
String macalgs2c = p.getString();
System.out.println("- " + macalgs2c);
String compalgc2s = p.getString();
System.out.println("- " + compalgc2s);
String compalgs2c = p.getString();
System.out.println("- " + compalgs2c);
String langc2s = p.getString();
System.out.println("- " + langc2s);
String langs2c = p.getString();
System.out.println("- " + langs2c);
fupp = p.getBytes(1);
System.out.println("- first_kex_follows: " + fupp[0]);
/* int32 reserved (0) */
SshPacket2 pn = new SshPacket2(SSH2_MSG_KEXINIT);
byte[] kexsend = new byte[16];
String ciphername;
pn.putBytes(kexsend);
pn.putString("diffie-hellman-group1-sha1");
pn.putString("ssh-rsa");
/* FIXME: check if it really is in the encalgc2s */
cipher_type = "NONE";
ciphername = "none";
/* FIXME: dito for HMAC */
pn.putString("none");
pn.putString("none");
pn.putString("hmac-md5");
pn.putString("hmac-md5");
pn.putString("none");
pn.putString("none");
pn.putString("");
pn.putString("");
pn.putByte((byte) 0);
pn.putInt32(0);
sendPacket2(pn);
pn = new SshPacket2(SSH2_MSG_KEXDH_INIT);
pn.putMpInt(BigInteger.valueOf(0xdeadbeef));
sendPacket2(pn);
break;
}
case SSH2_MSG_KEXDH_REPLY:
{
String result;
System.out.println("SSH2_MSG_KEXDH_REPLY");
int bloblen = p.getInt32();
System.out.println("bloblen is " + bloblen);
/* the blob has a substructure:
* String type
* if RSA:
* bignum1
* bignum2
* if DSA:
* bignum1,2,3,4
*/
String keytype = p.getString();
System.out.println("KEXDH: " + keytype);
if (keytype.equals("ssh-rsa")) {
rsa_e = p.getMpInt();
rsa_n = p.getMpInt();
result = "\n\rSSH-RSA (" + rsa_n + "," + rsa_e + ")\n\r";
} else {
return "\n\rUnsupported kexdh algorithm " + keytype + "!\n\r";
}
BigInteger dhserverpub = p.getMpInt();
result += "DH Server Pub: " + dhserverpub + "\n\r";
/* signature is a new blob, length is Int32. */
/*
* RSA:
* String type (ssh-rsa)
* Int32/byte[] signed signature
*/
int siglen = p.getInt32();
String sigstr = p.getString();
result += "Signature: ktype is " + sigstr + "\r\n";
byte sigdata[] = p.getBytes(p.getInt32());
return result;
}
default:
return "SSH2: handlePacket2 Unknown type " + p.getType();
}
return "";
}
private String handlePacket1(SshPacket1 p)
throws IOException { //the message to handle is data and its length is
byte b; // of course, byte is a signed entity (-128 -> 127)
//we have to deal with data....
if (debug > 0)
System.out.println("1 packet to handle, type " + p.getType());
switch (p.getType()) {
case SSH_MSG_IGNORE:
return "";
case SSH_MSG_DISCONNECT:
String str = p.getString();
disconnect();
return str;
case SSH_SMSG_PUBLIC_KEY:
byte[] anti_spoofing_cookie; //8 bytes
byte[] server_key_bits; //32-bit int
byte[] server_key_public_exponent; //mp-int
byte[] server_key_public_modulus; //mp-int
byte[] host_key_bits; //32-bit int
byte[] host_key_public_exponent; //mp-int
byte[] host_key_public_modulus; //mp-int
byte[] protocol_flags; //32-bit int
byte[] supported_ciphers_mask; //32-bit int
byte[] supported_authentications_mask; //32-bit int
anti_spoofing_cookie = p.getBytes(8);
server_key_bits = p.getBytes(4);
server_key_public_exponent = p.getMpInt();
server_key_public_modulus = p.getMpInt();
host_key_bits = p.getBytes(4);
host_key_public_exponent = p.getMpInt();
host_key_public_modulus = p.getMpInt();
protocol_flags = p.getBytes(4);
supported_ciphers_mask = p.getBytes(4);
supported_authentications_mask = p.getBytes(4);
// We have completely received the PUBLIC_KEY
// We prepare the answer ...
String ret = Send_SSH_CMSG_SESSION_KEY(
anti_spoofing_cookie, server_key_public_modulus,
host_key_public_modulus, supported_ciphers_mask,
server_key_public_exponent, host_key_public_exponent
);
if (ret != null)
return ret;
// we check if MD5(server_key_public_exponent) is equals to the
// applet parameter if any .
if (hashHostKey != null && hashHostKey.compareTo("") != 0) {
// we compute hashHostKeyBis the hash value in hexa of
// host_key_public_modulus
byte[] Md5_hostKey = md5.digest(host_key_public_modulus);
String hashHostKeyBis = "";
for (int i = 0; i < Md5_hostKey.length; i++) {
String hex = "";
int[] v = new int[2];
v[0] = (Md5_hostKey[i] & 240) >> 4;
v[1] = (Md5_hostKey[i] & 15);
for (int j = 0; j < 1; j++)
switch (v[j]) {
case 10:
hex += "a";
break;
case 11:
hex += "b";
break;
case 12:
hex += "c";
break;
case 13:
hex += "d";
break;
case 14:
hex += "e";
break;
case 15:
hex += "f";
break;
default :
hex += String.valueOf(v[j]);
break;
}
hashHostKeyBis = hashHostKeyBis + hex;
}
//we compare the 2 values
if (hashHostKeyBis.compareTo(hashHostKey) != 0) {
login = password = "";
return "\nHash value of the host key not correct \r\n"
+ "login & password have been reset \r\n"
+ "- erase the 'hashHostKey' parameter in the Html\r\n"
+ "(it is used for auhentificating the server and "
+ "prevent you from connecting \r\n"
+ "to any other)\r\n";
}
}
break;
case SSH_SMSG_SUCCESS:
if (debug > 0)
System.out.println("SSH_SMSG_SUCCESS (last packet was " + lastPacketSentType + ")");
if (lastPacketSentType == SSH_CMSG_SESSION_KEY) {
//we have succefully sent the session key !! (at last :-) )
Send_SSH_CMSG_USER();
break;
}
if (lastPacketSentType == SSH_CMSG_USER) {
// authentication is NOT needed for this user
Send_SSH_CMSG_REQUEST_PTY(); //request a pseudo-terminal
return "\nEmpty password login.\r\n";
}
if (lastPacketSentType == SSH_CMSG_AUTH_PASSWORD) {// password correct !!!
//yahoo
if (debug > 0)
System.out.println("login succesful");
//now we have to start the interactive session ...
Send_SSH_CMSG_REQUEST_PTY(); //request a pseudo-terminal
return "\nLogin & password accepted\r\n";
}
if (lastPacketSentType == SSH_CMSG_REQUEST_PTY) {// pty accepted !!
/* we can send data with a pty accepted ... no need for a shell. */
cansenddata = true;
if (dataToSend != null) {
Send_SSH_CMSG_STDIN_DATA(dataToSend);
dataToSend = null;
}
Send_SSH_CMSG_EXEC_SHELL(); //we start a shell
break;
}
if (lastPacketSentType == SSH_CMSG_EXEC_SHELL) {// shell is running ...
/* empty */
}
break;
case SSH_SMSG_FAILURE:
if (debug > 1) System.err.println("SSH_SMSG_FAILURE");
if (lastPacketSentType == SSH_CMSG_AUTH_PASSWORD) {// password incorrect ???
System.out.println("failed to log in");
Send_SSH_MSG_DISCONNECT("Failed to log in.");
disconnect();
return "\nLogin & password not accepted\r\n";
}
if (lastPacketSentType == SSH_CMSG_USER) {
// authentication is needed for the given user
// (in most cases that's true)
Send_SSH_CMSG_AUTH_PASSWORD();
break;
}
if (lastPacketSentType == SSH_CMSG_REQUEST_PTY) {// pty not accepted !!
break;
}
break;
case SSH_SMSG_STDOUT_DATA: //receive some data from the server
return p.getString();
case SSH_SMSG_STDERR_DATA: //receive some error data from the server
// if(debug > 1)
str = "Error : " + p.getString();
System.out.println("SshIO.handlePacket : " + "STDERR_DATA " + str);
return str;
case SSH_SMSG_EXITSTATUS: //sent by the server to indicate that
// the client program has terminated.
//32-bit int exit status of the command
int value = p.getInt32();
Send_SSH_CMSG_EXIT_CONFIRMATION();
System.out.println("SshIO : Exit status " + value);
disconnect();
break;
case SSH_MSG_DEBUG:
str = p.getString();
if (debug > 0) {
System.out.println("SshIO.handlePacket : " + " DEBUG " + str);
// bad bad bad bad bad. We should not do actions in DEBUG messages,
// but apparently some SSH demons does not send SSH_SMSG_FAILURE for
// just USER CMS.
/*
if(lastPacketSentType==SSH_CMSG_USER) {
Send_SSH_CMSG_AUTH_PASSWORD();
break;
}
*/
return str;
}
return "";
default:
System.err.print("SshIO.handlePacket1: Packet Type unknown: " + p.getType());
break;
}// switch(b)
return "";
} // handlePacket
private void sendPacket1(SshPacket1 packet) throws IOException {
write(packet.getPayLoad(crypto));
lastPacketSentType = packet.getType();
}
private void sendPacket2(SshPacket2 packet) throws IOException {
write(packet.getPayLoad(crypto, outgoingseq));
outgoingseq++;
lastPacketSentType = packet.getType();
}
//
// Send_SSH_CMSG_SESSION_KEY
// Create :
// the session_id,
// the session_key,
// the Xored session_key,
// the double_encrypted session key
// send SSH_CMSG_SESSION_KEY
// Turn the encryption on (initialise the block cipher)
//
private String Send_SSH_CMSG_SESSION_KEY(byte[] anti_spoofing_cookie,
byte[] server_key_public_modulus,
byte[] host_key_public_modulus,
byte[] supported_ciphers_mask,
byte[] server_key_public_exponent,
byte[] host_key_public_exponent)
throws IOException {
String str;
int boffset;
byte cipher_types; //encryption types
byte[] session_key; //mp-int
// create the session id
// session_id = md5(hostkey->n || servkey->n || cookie) //protocol V 1.5. (we use this one)
// session_id = md5(servkey->n || hostkey->n || cookie) //protocol V 1.1.(Why is it different ??)
//
byte[] session_id_byte = new byte[host_key_public_modulus.length + server_key_public_modulus.length + anti_spoofing_cookie.length];
System.arraycopy(host_key_public_modulus, 0, session_id_byte, 0, host_key_public_modulus.length);
System.arraycopy(server_key_public_modulus, 0, session_id_byte, host_key_public_modulus.length, server_key_public_modulus.length);
System.arraycopy(anti_spoofing_cookie, 0, session_id_byte, host_key_public_modulus.length + server_key_public_modulus.length, anti_spoofing_cookie.length);
byte[] hash_md5 = md5.digest(session_id_byte);
// SSH_CMSG_SESSION_KEY : Sent by the client
// 1 byte cipher_type (must be one of the supported values)
// 8 bytes anti_spoofing_cookie (must match data sent by the server)
// mp-int double-encrypted session key (uses the session-id)
// 32-bit int protocol_flags
//
if ((supported_ciphers_mask[3] & (byte) (1 << SSH_CIPHER_BLOWFISH)) != 0) {
cipher_types = (byte) SSH_CIPHER_BLOWFISH;
cipher_type = "Blowfish";
} else {
if ((supported_ciphers_mask[3] & (1 << SSH_CIPHER_IDEA)) != 0) {
cipher_types = (byte) SSH_CIPHER_IDEA;
cipher_type = "IDEA";
} else {
if ((supported_ciphers_mask[3] & (1 << SSH_CIPHER_3DES)) != 0) {
cipher_types = (byte) SSH_CIPHER_3DES;
cipher_type = "DES3";
} else {
if ((supported_ciphers_mask[3] & (1 << SSH_CIPHER_DES)) != 0) {
cipher_types = (byte) SSH_CIPHER_DES;
cipher_type = "DES";
} else {
System.err.println("SshIO: remote server does not supported IDEA, BlowFish or 3DES, support cypher mask is " + supported_ciphers_mask[3] + ".\n");
Send_SSH_MSG_DISCONNECT("No more auth methods available.");
disconnect();
return "\rRemote server does not support IDEA/Blowfish/3DES blockcipher, closing connection.\r\n";
}
}
}
}
if (debug > 0)
System.out.println("SshIO: Using " + cipher_type + " blockcipher.\n");
// anti_spoofing_cookie : the same
// double_encrypted_session_key :
// 32 bytes of random bits
// Xor the 16 first bytes with the session-id
// encrypt with the server_key_public (small) then the host_key_public(big) using RSA.
//
//32 bytes of random bits
byte[] random_bits1 = new byte[16], random_bits2 = new byte[16];
/// java.util.Date date = new java.util.Date(); ////the number of milliseconds since January 1, 1970, 00:00:00 GMT.
//Math.random() a pseudorandom double between 0.0 and 1.0.
// random_bits2 = random_bits1 =
// md5.hash("" + Math.random() * (new java.util.Date()).getDate());
// md5.digest(("" + Math.random() * (new java.util.Date()).getTime()).getBytes());
//random_bits1 = md5.digest(SshMisc.addArrayOfBytes(md5.digest((password + login).getBytes()), random_bits1));
//random_bits2 = md5.digest(SshMisc.addArrayOfBytes(md5.digest((password + login).getBytes()), random_bits2));
SecureRandom random = new java.security.SecureRandom(random_bits1); //no supported by netscape :-(
random.nextBytes(random_bits1);
random.nextBytes(random_bits2);
session_key = SshMisc.addArrayOfBytes(random_bits1, random_bits2);
//Xor the 16 first bytes with the session-id
byte[] session_keyXored = SshMisc.XORArrayOfBytes(random_bits1, hash_md5);
session_keyXored = SshMisc.addArrayOfBytes(session_keyXored, random_bits2);
//We encrypt now!!
byte[] encrypted_session_key =
SshCrypto.encrypteRSAPkcs1Twice(session_keyXored,
server_key_public_exponent,
server_key_public_modulus,
host_key_public_exponent,
host_key_public_modulus);
// protocol_flags :protocol extension cf. page 18
int protocol_flags = 0; /* currently 0 */
SshPacket1 packet = new SshPacket1(SSH_CMSG_SESSION_KEY);
packet.putByte((byte) cipher_types);
packet.putBytes(anti_spoofing_cookie);
packet.putBytes(encrypted_session_key);
packet.putInt32(protocol_flags);
sendPacket1(packet);
crypto = new SshCrypto(cipher_type, session_key);
return "";
}
/**
* SSH_MSG_DISCONNECT
* string disconnect reason
*/
private String Send_SSH_MSG_DISCONNECT(String reason) throws IOException {
SshPacket1 p = new SshPacket1(SSH_MSG_DISCONNECT);
p.putString(reason); // String Disconnect reason
sendPacket1(p);
return "";
}
/**
* SSH_CMSG_USER
* string user login name on server
*/
private String Send_SSH_CMSG_USER() throws IOException {
if (debug > 0) System.err.println("Send_SSH_CMSG_USER(" + login + ")");
SshPacket1 p = new SshPacket1(SSH_CMSG_USER);
p.putString(login);
sendPacket1(p);
return "";
}
/**
* Send_SSH_CMSG_AUTH_PASSWORD
* string user password
*/
private String Send_SSH_CMSG_AUTH_PASSWORD() throws IOException {
SshPacket1 p = new SshPacket1(SSH_CMSG_AUTH_PASSWORD);
p.putString(password);
sendPacket1(p);
return "";
}
/**
* Send_SSH_CMSG_EXEC_SHELL
* (no arguments)
* Starts a shell (command interpreter), and enters interactive
* session mode.
*/
private String Send_SSH_CMSG_EXEC_SHELL() throws IOException {
SshPacket1 packet = new SshPacket1(SSH_CMSG_EXEC_SHELL);
sendPacket1(packet);
return "";
}
/**
* Send_SSH_CMSG_STDIN_DATA
*
*/
private String Send_SSH_CMSG_STDIN_DATA(String str) throws IOException {
SshPacket1 packet = new SshPacket1(SSH_CMSG_STDIN_DATA);
packet.putString(str);
sendPacket1(packet);
return "";
}
/**
* Send_SSH_CMSG_WINDOW_SIZE
* string TERM environment variable value (e.g. vt100)
* 32-bit int terminal height, rows (e.g., 24)
* 32-bit int terminal width, columns (e.g., 80)
* 32-bit int terminal width, pixels (0 if no graphics) (e.g., 480)
*/
private String Send_SSH_CMSG_WINDOW_SIZE(int c, int r) throws IOException {
SshPacket1 p = new SshPacket1(SSH_CMSG_WINDOW_SIZE);
p.putInt32(r); // Int32 rows
p.putInt32(c); // Int32 columns
p.putInt32(0); // Int32 x pixels
p.putInt32(0); // Int32 y pixels
sendPacket1(p);
return "";
}
/**
* Send_SSH_CMSG_REQUEST_PTY
* string TERM environment variable value (e.g. vt100)
* 32-bit int terminal height, rows (e.g., 24)
* 32-bit int terminal width, columns (e.g., 80)
* 32-bit int terminal width, pixels (0 if no graphics) (e.g., 480)
*/
private String Send_SSH_CMSG_REQUEST_PTY() throws IOException {
SshPacket1 p = new SshPacket1(SSH_CMSG_REQUEST_PTY);
p.putString(getTerminalType());
p.putInt32(24); // Int32 rows
p.putInt32(80); // Int32 columns
p.putInt32(0); // Int32 x pixels
p.putInt32(0); // Int32 y pixels
p.putByte((byte) 0); // Int8 terminal modes
sendPacket1(p);
return "";
}
private String Send_SSH_CMSG_EXIT_CONFIRMATION() throws IOException {
SshPacket1 packet = new SshPacket1(SSH_CMSG_EXIT_CONFIRMATION);
sendPacket1(packet);
return "";
}
}
jta_2.6+dfsg.orig/de/mud/ssh/Blowfish.java 0000644 0001750 0001750 00000063752 10610772601 017172 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.ssh;
/**
* @author Marcus Meissner
* @version $Id: Blowfish.java 499 2005-09-29 08:24:54Z leo $
*/
public final class Blowfish extends Cipher {
protected int[] S0 = new int[256];
protected int[] S1 = new int[256];
protected int[] S2 = new int[256];
protected int[] S3 = new int[256];
protected int[] P = new int[18];
private int IV0;
private int IV1;
public Blowfish() {
}
// Set key of this Blowfish from a String
public void setKey(String skey) {
byte[] key = skey.getBytes();
setKey(key);
}
// Set key of this Blowfish from a bytearray
public void setKey(byte[] key) {
int i, j, k, len = key.length;
int temp;
int L, R;
int[] output = new int[2];
System.arraycopy(blowfish_pbox, 0, P, 0, 18);
System.arraycopy(blowfish_sbox, 0, S0, 0, 256);
System.arraycopy(blowfish_sbox, 256, S1, 0, 256);
System.arraycopy(blowfish_sbox, 512, S2, 0, 256);
System.arraycopy(blowfish_sbox, 768, S3, 0, 256);
// Actual subkey generation
//
for (j = 0, i = 0; i < 16 + 2; i++) {
temp = (((key[j] & 0xff) << 24) |
((key[(j + 1) % len] & 0xff) << 16) |
((key[(j + 2) % len] & 0xff) << 8) |
((key[(j + 3) % len] & 0xff)));
P[i] = P[i] ^ temp;
j = (j + 4) % len;
}
L = 0;
R = 0;
for (i = 0; i < 16 + 2; i += 2) {
encrypt(L, R, output);
L = output[0];
R = output[1];
P[i] = L;
P[i + 1] = R;
}
for (j = 0; j < 256; j += 2) {
encrypt(L, R, output);
L = output[0];
R = output[1];
S0[j] = L;
S0[j + 1] = R;
}
for (j = 0; j < 256; j += 2) {
encrypt(L, R, output);
L = output[0];
R = output[1];
S1[j] = L;
S1[j + 1] = R;
}
for (j = 0; j < 256; j += 2) {
encrypt(L, R, output);
L = output[0];
R = output[1];
S2[j] = L;
S2[j + 1] = R;
}
for (j = 0; j < 256; j += 2) {
encrypt(L, R, output);
L = output[0];
R = output[1];
S3[j] = L;
S3[j + 1] = R;
}
IV0 = 0;
IV1 = 0;
}
public synchronized void encrypt(byte[] src, int srcOff, byte[] dest, int destOff, int len) {
int[] out = new int[2];
int iv0 = IV0;
int iv1 = IV1;
int end = srcOff + len;
for (int si = srcOff, di = destOff; si < end; si += 8, di += 8) {
iv0 ^= ((src[si] & 0xff) | ((src[si + 1] & 0xff) << 8) |
((src[si + 2] & 0xff) << 16) | ((src[si + 3] & 0xff) << 24));
iv1 ^= ((src[si + 4] & 0xff) | ((src[si + 5] & 0xff) << 8) |
((src[si + 6] & 0xff) << 16) | ((src[si + 7] & 0xff) << 24));
encrypt(iv0, iv1, out);
iv0 = out[0];
iv1 = out[1];
dest[di] = (byte) (iv0 & 0xff);
dest[di + 1] = (byte) ((iv0 >>> 8) & 0xff);
dest[di + 2] = (byte) ((iv0 >>> 16) & 0xff);
dest[di + 3] = (byte) ((iv0 >>> 24) & 0xff);
dest[di + 4] = (byte) (iv1 & 0xff);
dest[di + 5] = (byte) ((iv1 >>> 8) & 0xff);
dest[di + 6] = (byte) ((iv1 >>> 16) & 0xff);
dest[di + 7] = (byte) ((iv1 >>> 24) & 0xff);
}
IV0 = iv0;
IV1 = iv1;
}
public void encrypt(int xL, int xR, int[] out) {
int L, R;
L = xL;
R = xR;
L ^= P[0];
R ^= ((((S0[(int) ((L >>> 24) & 0xff)] + S1[(int) ((L >>> 16) & 0xff)]) ^
S2[(int) ((L >>> 8) & 0xff)]) + S3[(int) (L & 0xff)]) ^ P[1]);
L ^= ((((S0[(int) ((R >>> 24) & 0xff)] + S1[(int) ((R >>> 16) & 0xff)]) ^
S2[(int) ((R >>> 8) & 0xff)]) + S3[(int) (R & 0xff)]) ^ P[2]);
R ^= ((((S0[(int) ((L >>> 24) & 0xff)] + S1[(int) ((L >>> 16) & 0xff)]) ^
S2[(int) ((L >>> 8) & 0xff)]) + S3[(int) (L & 0xff)]) ^ P[3]);
L ^= ((((S0[(int) ((R >>> 24) & 0xff)] + S1[(int) ((R >>> 16) & 0xff)]) ^
S2[(int) ((R >>> 8) & 0xff)]) + S3[(int) (R & 0xff)]) ^ P[4]);
R ^= ((((S0[(int) ((L >>> 24) & 0xff)] + S1[(int) ((L >>> 16) & 0xff)]) ^
S2[(int) ((L >>> 8) & 0xff)]) + S3[(int) (L & 0xff)]) ^ P[5]);
L ^= ((((S0[(int) ((R >>> 24) & 0xff)] + S1[(int) ((R >>> 16) & 0xff)]) ^
S2[(int) ((R >>> 8) & 0xff)]) + S3[(int) (R & 0xff)]) ^ P[6]);
R ^= ((((S0[(int) ((L >>> 24) & 0xff)] + S1[(int) ((L >>> 16) & 0xff)]) ^
S2[(int) ((L >>> 8) & 0xff)]) + S3[(int) (L & 0xff)]) ^ P[7]);
L ^= ((((S0[(int) ((R >>> 24) & 0xff)] + S1[(int) ((R >>> 16) & 0xff)]) ^
S2[(int) ((R >>> 8) & 0xff)]) + S3[(int) (R & 0xff)]) ^ P[8]);
R ^= ((((S0[(int) ((L >>> 24) & 0xff)] + S1[(int) ((L >>> 16) & 0xff)]) ^
S2[(int) ((L >>> 8) & 0xff)]) + S3[(int) (L & 0xff)]) ^ P[9]);
L ^= ((((S0[(int) ((R >>> 24) & 0xff)] + S1[(int) ((R >>> 16) & 0xff)]) ^
S2[(int) ((R >>> 8) & 0xff)]) + S3[(int) (R & 0xff)]) ^ P[10]);
R ^= ((((S0[(int) ((L >>> 24) & 0xff)] + S1[(int) ((L >>> 16) & 0xff)]) ^
S2[(int) ((L >>> 8) & 0xff)]) + S3[(int) (L & 0xff)]) ^ P[11]);
L ^= ((((S0[(int) ((R >>> 24) & 0xff)] + S1[(int) ((R >>> 16) & 0xff)]) ^
S2[(int) ((R >>> 8) & 0xff)]) + S3[(int) (R & 0xff)]) ^ P[12]);
R ^= ((((S0[(int) ((L >>> 24) & 0xff)] + S1[(int) ((L >>> 16) & 0xff)]) ^
S2[(int) ((L >>> 8) & 0xff)]) + S3[(int) (L & 0xff)]) ^ P[13]);
L ^= ((((S0[(int) ((R >>> 24) & 0xff)] + S1[(int) ((R >>> 16) & 0xff)]) ^
S2[(int) ((R >>> 8) & 0xff)]) + S3[(int) (R & 0xff)]) ^ P[14]);
R ^= ((((S0[(int) ((L >>> 24) & 0xff)] + S1[(int) ((L >>> 16) & 0xff)]) ^
S2[(int) ((L >>> 8) & 0xff)]) + S3[(int) (L & 0xff)]) ^ P[15]);
L ^= ((((S0[(int) ((R >>> 24) & 0xff)] + S1[(int) ((R >>> 16) & 0xff)]) ^
S2[(int) ((R >>> 8) & 0xff)]) + S3[(int) (R & 0xff)]) ^ P[16]);
R ^= P[17];
out[0] = R;
out[1] = L;
}
public synchronized void decrypt(byte[] src, int srcOff, byte[] dest, int destOff, int len) {
int[] out = new int[2];
int iv0 = IV0;
int iv1 = IV1;
int d0;
int d1;
int end = srcOff + len;
for (int si = srcOff, di = destOff; si < end; si += 8, di += 8) {
d0 = ((src[si] & 0xff) | ((src[si + 1] & 0xff) << 8) |
((src[si + 2] & 0xff) << 16) | ((src[si + 3] & 0xff) << 24));
d1 = ((src[si + 4] & 0xff) | ((src[si + 5] & 0xff) << 8) |
((src[si + 6] & 0xff) << 16) | ((src[si + 7] & 0xff) << 24));
decrypt(d0, d1, out);
iv0 ^= out[0];
iv1 ^= out[1];
dest[di] = (byte) (iv0 & 0xff);
dest[di + 1] = (byte) ((iv0 >>> 8) & 0xff);
dest[di + 2] = (byte) ((iv0 >>> 16) & 0xff);
dest[di + 3] = (byte) ((iv0 >>> 24) & 0xff);
dest[di + 4] = (byte) (iv1 & 0xff);
dest[di + 5] = (byte) ((iv1 >>> 8) & 0xff);
dest[di + 6] = (byte) ((iv1 >>> 16) & 0xff);
dest[di + 7] = (byte) ((iv1 >>> 24) & 0xff);
iv0 = d0;
iv1 = d1;
}
IV0 = iv0;
IV1 = iv1;
}
public int[] decrypt(int xL, int xR, int[] out) {
int L, R;
L = xL;
R = xR;
L ^= P[17];
R ^= ((((S0[(int) ((L >>> 24) & 0xff)] + S1[(int) ((L >>> 16) & 0xff)]) ^
S2[(int) ((L >>> 8) & 0xff)]) + S3[(int) (L & 0xff)]) ^ P[16]);
L ^= ((((S0[(int) ((R >>> 24) & 0xff)] + S1[(int) ((R >>> 16) & 0xff)]) ^
S2[(int) ((R >>> 8) & 0xff)]) + S3[(int) (R & 0xff)]) ^ P[15]);
R ^= ((((S0[(int) ((L >>> 24) & 0xff)] + S1[(int) ((L >>> 16) & 0xff)]) ^
S2[(int) ((L >>> 8) & 0xff)]) + S3[(int) (L & 0xff)]) ^ P[14]);
L ^= ((((S0[(int) ((R >>> 24) & 0xff)] + S1[(int) ((R >>> 16) & 0xff)]) ^
S2[(int) ((R >>> 8) & 0xff)]) + S3[(int) (R & 0xff)]) ^ P[13]);
R ^= ((((S0[(int) ((L >>> 24) & 0xff)] + S1[(int) ((L >>> 16) & 0xff)]) ^
S2[(int) ((L >>> 8) & 0xff)]) + S3[(int) (L & 0xff)]) ^ P[12]);
L ^= ((((S0[(int) ((R >>> 24) & 0xff)] + S1[(int) ((R >>> 16) & 0xff)]) ^
S2[(int) ((R >>> 8) & 0xff)]) + S3[(int) (R & 0xff)]) ^ P[11]);
R ^= ((((S0[(int) ((L >>> 24) & 0xff)] + S1[(int) ((L >>> 16) & 0xff)]) ^
S2[(int) ((L >>> 8) & 0xff)]) + S3[(int) (L & 0xff)]) ^ P[10]);
L ^= ((((S0[(int) ((R >>> 24) & 0xff)] + S1[(int) ((R >>> 16) & 0xff)]) ^
S2[(int) ((R >>> 8) & 0xff)]) + S3[(int) (R & 0xff)]) ^ P[9]);
R ^= ((((S0[(int) ((L >>> 24) & 0xff)] + S1[(int) ((L >>> 16) & 0xff)]) ^
S2[(int) ((L >>> 8) & 0xff)]) + S3[(int) (L & 0xff)]) ^ P[8]);
L ^= ((((S0[(int) ((R >>> 24) & 0xff)] + S1[(int) ((R >>> 16) & 0xff)]) ^
S2[(int) ((R >>> 8) & 0xff)]) + S3[(int) (R & 0xff)]) ^ P[7]);
R ^= ((((S0[(int) ((L >>> 24) & 0xff)] + S1[(int) ((L >>> 16) & 0xff)]) ^
S2[(int) ((L >>> 8) & 0xff)]) + S3[(int) (L & 0xff)]) ^ P[6]);
L ^= ((((S0[(int) ((R >>> 24) & 0xff)] + S1[(int) ((R >>> 16) & 0xff)]) ^
S2[(int) ((R >>> 8) & 0xff)]) + S3[(int) (R & 0xff)]) ^ P[5]);
R ^= ((((S0[(int) ((L >>> 24) & 0xff)] + S1[(int) ((L >>> 16) & 0xff)]) ^
S2[(int) ((L >>> 8) & 0xff)]) + S3[(int) (L & 0xff)]) ^ P[4]);
L ^= ((((S0[(int) ((R >>> 24) & 0xff)] + S1[(int) ((R >>> 16) & 0xff)]) ^
S2[(int) ((R >>> 8) & 0xff)]) + S3[(int) (R & 0xff)]) ^ P[3]);
R ^= ((((S0[(int) ((L >>> 24) & 0xff)] + S1[(int) ((L >>> 16) & 0xff)]) ^
S2[(int) ((L >>> 8) & 0xff)]) + S3[(int) (L & 0xff)]) ^ P[2]);
L ^= ((((S0[(int) ((R >>> 24) & 0xff)] + S1[(int) ((R >>> 16) & 0xff)]) ^
S2[(int) ((R >>> 8) & 0xff)]) + S3[(int) (R & 0xff)]) ^ P[1]);
R ^= P[0];
out[0] = R;
out[1] = L;
return out;
}
/* Blowfish's P and S -boxes, respectively. These were taken
from Bruce Schneier's public-domain implementation. */
final static int[] blowfish_pbox =
{
0x243f6a88, 0x85a308d3, 0x13198a2e, 0x03707344,
0xa4093822, 0x299f31d0, 0x082efa98, 0xec4e6c89,
0x452821e6, 0x38d01377, 0xbe5466cf, 0x34e90c6c,
0xc0ac29b7, 0xc97c50dd, 0x3f84d5b5, 0xb5470917,
0x9216d5d9, 0x8979fb1b
};
final static int[] blowfish_sbox =
{
0xd1310ba6, 0x98dfb5ac, 0x2ffd72db, 0xd01adfb7,
0xb8e1afed, 0x6a267e96, 0xba7c9045, 0xf12c7f99,
0x24a19947, 0xb3916cf7, 0x0801f2e2, 0x858efc16,
0x636920d8, 0x71574e69, 0xa458fea3, 0xf4933d7e,
0x0d95748f, 0x728eb658, 0x718bcd58, 0x82154aee,
0x7b54a41d, 0xc25a59b5, 0x9c30d539, 0x2af26013,
0xc5d1b023, 0x286085f0, 0xca417918, 0xb8db38ef,
0x8e79dcb0, 0x603a180e, 0x6c9e0e8b, 0xb01e8a3e,
0xd71577c1, 0xbd314b27, 0x78af2fda, 0x55605c60,
0xe65525f3, 0xaa55ab94, 0x57489862, 0x63e81440,
0x55ca396a, 0x2aab10b6, 0xb4cc5c34, 0x1141e8ce,
0xa15486af, 0x7c72e993, 0xb3ee1411, 0x636fbc2a,
0x2ba9c55d, 0x741831f6, 0xce5c3e16, 0x9b87931e,
0xafd6ba33, 0x6c24cf5c, 0x7a325381, 0x28958677,
0x3b8f4898, 0x6b4bb9af, 0xc4bfe81b, 0x66282193,
0x61d809cc, 0xfb21a991, 0x487cac60, 0x5dec8032,
0xef845d5d, 0xe98575b1, 0xdc262302, 0xeb651b88,
0x23893e81, 0xd396acc5, 0x0f6d6ff3, 0x83f44239,
0x2e0b4482, 0xa4842004, 0x69c8f04a, 0x9e1f9b5e,
0x21c66842, 0xf6e96c9a, 0x670c9c61, 0xabd388f0,
0x6a51a0d2, 0xd8542f68, 0x960fa728, 0xab5133a3,
0x6eef0b6c, 0x137a3be4, 0xba3bf050, 0x7efb2a98,
0xa1f1651d, 0x39af0176, 0x66ca593e, 0x82430e88,
0x8cee8619, 0x456f9fb4, 0x7d84a5c3, 0x3b8b5ebe,
0xe06f75d8, 0x85c12073, 0x401a449f, 0x56c16aa6,
0x4ed3aa62, 0x363f7706, 0x1bfedf72, 0x429b023d,
0x37d0d724, 0xd00a1248, 0xdb0fead3, 0x49f1c09b,
0x075372c9, 0x80991b7b, 0x25d479d8, 0xf6e8def7,
0xe3fe501a, 0xb6794c3b, 0x976ce0bd, 0x04c006ba,
0xc1a94fb6, 0x409f60c4, 0x5e5c9ec2, 0x196a2463,
0x68fb6faf, 0x3e6c53b5, 0x1339b2eb, 0x3b52ec6f,
0x6dfc511f, 0x9b30952c, 0xcc814544, 0xaf5ebd09,
0xbee3d004, 0xde334afd, 0x660f2807, 0x192e4bb3,
0xc0cba857, 0x45c8740f, 0xd20b5f39, 0xb9d3fbdb,
0x5579c0bd, 0x1a60320a, 0xd6a100c6, 0x402c7279,
0x679f25fe, 0xfb1fa3cc, 0x8ea5e9f8, 0xdb3222f8,
0x3c7516df, 0xfd616b15, 0x2f501ec8, 0xad0552ab,
0x323db5fa, 0xfd238760, 0x53317b48, 0x3e00df82,
0x9e5c57bb, 0xca6f8ca0, 0x1a87562e, 0xdf1769db,
0xd542a8f6, 0x287effc3, 0xac6732c6, 0x8c4f5573,
0x695b27b0, 0xbbca58c8, 0xe1ffa35d, 0xb8f011a0,
0x10fa3d98, 0xfd2183b8, 0x4afcb56c, 0x2dd1d35b,
0x9a53e479, 0xb6f84565, 0xd28e49bc, 0x4bfb9790,
0xe1ddf2da, 0xa4cb7e33, 0x62fb1341, 0xcee4c6e8,
0xef20cada, 0x36774c01, 0xd07e9efe, 0x2bf11fb4,
0x95dbda4d, 0xae909198, 0xeaad8e71, 0x6b93d5a0,
0xd08ed1d0, 0xafc725e0, 0x8e3c5b2f, 0x8e7594b7,
0x8ff6e2fb, 0xf2122b64, 0x8888b812, 0x900df01c,
0x4fad5ea0, 0x688fc31c, 0xd1cff191, 0xb3a8c1ad,
0x2f2f2218, 0xbe0e1777, 0xea752dfe, 0x8b021fa1,
0xe5a0cc0f, 0xb56f74e8, 0x18acf3d6, 0xce89e299,
0xb4a84fe0, 0xfd13e0b7, 0x7cc43b81, 0xd2ada8d9,
0x165fa266, 0x80957705, 0x93cc7314, 0x211a1477,
0xe6ad2065, 0x77b5fa86, 0xc75442f5, 0xfb9d35cf,
0xebcdaf0c, 0x7b3e89a0, 0xd6411bd3, 0xae1e7e49,
0x00250e2d, 0x2071b35e, 0x226800bb, 0x57b8e0af,
0x2464369b, 0xf009b91e, 0x5563911d, 0x59dfa6aa,
0x78c14389, 0xd95a537f, 0x207d5ba2, 0x02e5b9c5,
0x83260376, 0x6295cfa9, 0x11c81968, 0x4e734a41,
0xb3472dca, 0x7b14a94a, 0x1b510052, 0x9a532915,
0xd60f573f, 0xbc9bc6e4, 0x2b60a476, 0x81e67400,
0x08ba6fb5, 0x571be91f, 0xf296ec6b, 0x2a0dd915,
0xb6636521, 0xe7b9f9b6, 0xff34052e, 0xc5855664,
0x53b02d5d, 0xa99f8fa1, 0x08ba4799, 0x6e85076a,
0x4b7a70e9, 0xb5b32944, 0xdb75092e, 0xc4192623,
0xad6ea6b0, 0x49a7df7d, 0x9cee60b8, 0x8fedb266,
0xecaa8c71, 0x699a17ff, 0x5664526c, 0xc2b19ee1,
0x193602a5, 0x75094c29, 0xa0591340, 0xe4183a3e,
0x3f54989a, 0x5b429d65, 0x6b8fe4d6, 0x99f73fd6,
0xa1d29c07, 0xefe830f5, 0x4d2d38e6, 0xf0255dc1,
0x4cdd2086, 0x8470eb26, 0x6382e9c6, 0x021ecc5e,
0x09686b3f, 0x3ebaefc9, 0x3c971814, 0x6b6a70a1,
0x687f3584, 0x52a0e286, 0xb79c5305, 0xaa500737,
0x3e07841c, 0x7fdeae5c, 0x8e7d44ec, 0x5716f2b8,
0xb03ada37, 0xf0500c0d, 0xf01c1f04, 0x0200b3ff,
0xae0cf51a, 0x3cb574b2, 0x25837a58, 0xdc0921bd,
0xd19113f9, 0x7ca92ff6, 0x94324773, 0x22f54701,
0x3ae5e581, 0x37c2dadc, 0xc8b57634, 0x9af3dda7,
0xa9446146, 0x0fd0030e, 0xecc8c73e, 0xa4751e41,
0xe238cd99, 0x3bea0e2f, 0x3280bba1, 0x183eb331,
0x4e548b38, 0x4f6db908, 0x6f420d03, 0xf60a04bf,
0x2cb81290, 0x24977c79, 0x5679b072, 0xbcaf89af,
0xde9a771f, 0xd9930810, 0xb38bae12, 0xdccf3f2e,
0x5512721f, 0x2e6b7124, 0x501adde6, 0x9f84cd87,
0x7a584718, 0x7408da17, 0xbc9f9abc, 0xe94b7d8c,
0xec7aec3a, 0xdb851dfa, 0x63094366, 0xc464c3d2,
0xef1c1847, 0x3215d908, 0xdd433b37, 0x24c2ba16,
0x12a14d43, 0x2a65c451, 0x50940002, 0x133ae4dd,
0x71dff89e, 0x10314e55, 0x81ac77d6, 0x5f11199b,
0x043556f1, 0xd7a3c76b, 0x3c11183b, 0x5924a509,
0xf28fe6ed, 0x97f1fbfa, 0x9ebabf2c, 0x1e153c6e,
0x86e34570, 0xeae96fb1, 0x860e5e0a, 0x5a3e2ab3,
0x771fe71c, 0x4e3d06fa, 0x2965dcb9, 0x99e71d0f,
0x803e89d6, 0x5266c825, 0x2e4cc978, 0x9c10b36a,
0xc6150eba, 0x94e2ea78, 0xa5fc3c53, 0x1e0a2df4,
0xf2f74ea7, 0x361d2b3d, 0x1939260f, 0x19c27960,
0x5223a708, 0xf71312b6, 0xebadfe6e, 0xeac31f66,
0xe3bc4595, 0xa67bc883, 0xb17f37d1, 0x018cff28,
0xc332ddef, 0xbe6c5aa5, 0x65582185, 0x68ab9802,
0xeecea50f, 0xdb2f953b, 0x2aef7dad, 0x5b6e2f84,
0x1521b628, 0x29076170, 0xecdd4775, 0x619f1510,
0x13cca830, 0xeb61bd96, 0x0334fe1e, 0xaa0363cf,
0xb5735c90, 0x4c70a239, 0xd59e9e0b, 0xcbaade14,
0xeecc86bc, 0x60622ca7, 0x9cab5cab, 0xb2f3846e,
0x648b1eaf, 0x19bdf0ca, 0xa02369b9, 0x655abb50,
0x40685a32, 0x3c2ab4b3, 0x319ee9d5, 0xc021b8f7,
0x9b540b19, 0x875fa099, 0x95f7997e, 0x623d7da8,
0xf837889a, 0x97e32d77, 0x11ed935f, 0x16681281,
0x0e358829, 0xc7e61fd6, 0x96dedfa1, 0x7858ba99,
0x57f584a5, 0x1b227263, 0x9b83c3ff, 0x1ac24696,
0xcdb30aeb, 0x532e3054, 0x8fd948e4, 0x6dbc3128,
0x58ebf2ef, 0x34c6ffea, 0xfe28ed61, 0xee7c3c73,
0x5d4a14d9, 0xe864b7e3, 0x42105d14, 0x203e13e0,
0x45eee2b6, 0xa3aaabea, 0xdb6c4f15, 0xfacb4fd0,
0xc742f442, 0xef6abbb5, 0x654f3b1d, 0x41cd2105,
0xd81e799e, 0x86854dc7, 0xe44b476a, 0x3d816250,
0xcf62a1f2, 0x5b8d2646, 0xfc8883a0, 0xc1c7b6a3,
0x7f1524c3, 0x69cb7492, 0x47848a0b, 0x5692b285,
0x095bbf00, 0xad19489d, 0x1462b174, 0x23820e00,
0x58428d2a, 0x0c55f5ea, 0x1dadf43e, 0x233f7061,
0x3372f092, 0x8d937e41, 0xd65fecf1, 0x6c223bdb,
0x7cde3759, 0xcbee7460, 0x4085f2a7, 0xce77326e,
0xa6078084, 0x19f8509e, 0xe8efd855, 0x61d99735,
0xa969a7aa, 0xc50c06c2, 0x5a04abfc, 0x800bcadc,
0x9e447a2e, 0xc3453484, 0xfdd56705, 0x0e1e9ec9,
0xdb73dbd3, 0x105588cd, 0x675fda79, 0xe3674340,
0xc5c43465, 0x713e38d8, 0x3d28f89e, 0xf16dff20,
0x153e21e7, 0x8fb03d4a, 0xe6e39f2b, 0xdb83adf7,
0xe93d5a68, 0x948140f7, 0xf64c261c, 0x94692934,
0x411520f7, 0x7602d4f7, 0xbcf46b2e, 0xd4a20068,
0xd4082471, 0x3320f46a, 0x43b7d4b7, 0x500061af,
0x1e39f62e, 0x97244546, 0x14214f74, 0xbf8b8840,
0x4d95fc1d, 0x96b591af, 0x70f4ddd3, 0x66a02f45,
0xbfbc09ec, 0x03bd9785, 0x7fac6dd0, 0x31cb8504,
0x96eb27b3, 0x55fd3941, 0xda2547e6, 0xabca0a9a,
0x28507825, 0x530429f4, 0x0a2c86da, 0xe9b66dfb,
0x68dc1462, 0xd7486900, 0x680ec0a4, 0x27a18dee,
0x4f3ffea2, 0xe887ad8c, 0xb58ce006, 0x7af4d6b6,
0xaace1e7c, 0xd3375fec, 0xce78a399, 0x406b2a42,
0x20fe9e35, 0xd9f385b9, 0xee39d7ab, 0x3b124e8b,
0x1dc9faf7, 0x4b6d1856, 0x26a36631, 0xeae397b2,
0x3a6efa74, 0xdd5b4332, 0x6841e7f7, 0xca7820fb,
0xfb0af54e, 0xd8feb397, 0x454056ac, 0xba489527,
0x55533a3a, 0x20838d87, 0xfe6ba9b7, 0xd096954b,
0x55a867bc, 0xa1159a58, 0xcca92963, 0x99e1db33,
0xa62a4a56, 0x3f3125f9, 0x5ef47e1c, 0x9029317c,
0xfdf8e802, 0x04272f70, 0x80bb155c, 0x05282ce3,
0x95c11548, 0xe4c66d22, 0x48c1133f, 0xc70f86dc,
0x07f9c9ee, 0x41041f0f, 0x404779a4, 0x5d886e17,
0x325f51eb, 0xd59bc0d1, 0xf2bcc18f, 0x41113564,
0x257b7834, 0x602a9c60, 0xdff8e8a3, 0x1f636c1b,
0x0e12b4c2, 0x02e1329e, 0xaf664fd1, 0xcad18115,
0x6b2395e0, 0x333e92e1, 0x3b240b62, 0xeebeb922,
0x85b2a20e, 0xe6ba0d99, 0xde720c8c, 0x2da2f728,
0xd0127845, 0x95b794fd, 0x647d0862, 0xe7ccf5f0,
0x5449a36f, 0x877d48fa, 0xc39dfd27, 0xf33e8d1e,
0x0a476341, 0x992eff74, 0x3a6f6eab, 0xf4f8fd37,
0xa812dc60, 0xa1ebddf8, 0x991be14c, 0xdb6e6b0d,
0xc67b5510, 0x6d672c37, 0x2765d43b, 0xdcd0e804,
0xf1290dc7, 0xcc00ffa3, 0xb5390f92, 0x690fed0b,
0x667b9ffb, 0xcedb7d9c, 0xa091cf0b, 0xd9155ea3,
0xbb132f88, 0x515bad24, 0x7b9479bf, 0x763bd6eb,
0x37392eb3, 0xcc115979, 0x8026e297, 0xf42e312d,
0x6842ada7, 0xc66a2b3b, 0x12754ccc, 0x782ef11c,
0x6a124237, 0xb79251e7, 0x06a1bbe6, 0x4bfb6350,
0x1a6b1018, 0x11caedfa, 0x3d25bdd8, 0xe2e1c3c9,
0x44421659, 0x0a121386, 0xd90cec6e, 0xd5abea2a,
0x64af674e, 0xda86a85f, 0xbebfe988, 0x64e4c3fe,
0x9dbc8057, 0xf0f7c086, 0x60787bf8, 0x6003604d,
0xd1fd8346, 0xf6381fb0, 0x7745ae04, 0xd736fccc,
0x83426b33, 0xf01eab71, 0xb0804187, 0x3c005e5f,
0x77a057be, 0xbde8ae24, 0x55464299, 0xbf582e61,
0x4e58f48f, 0xf2ddfda2, 0xf474ef38, 0x8789bdc2,
0x5366f9c3, 0xc8b38e74, 0xb475f255, 0x46fcd9b9,
0x7aeb2661, 0x8b1ddf84, 0x846a0e79, 0x915f95e2,
0x466e598e, 0x20b45770, 0x8cd55591, 0xc902de4c,
0xb90bace1, 0xbb8205d0, 0x11a86248, 0x7574a99e,
0xb77f19b6, 0xe0a9dc09, 0x662d09a1, 0xc4324633,
0xe85a1f02, 0x09f0be8c, 0x4a99a025, 0x1d6efe10,
0x1ab93d1d, 0x0ba5a4df, 0xa186f20f, 0x2868f169,
0xdcb7da83, 0x573906fe, 0xa1e2ce9b, 0x4fcd7f52,
0x50115e01, 0xa70683fa, 0xa002b5c4, 0x0de6d027,
0x9af88c27, 0x773f8641, 0xc3604c06, 0x61a806b5,
0xf0177a28, 0xc0f586e0, 0x006058aa, 0x30dc7d62,
0x11e69ed7, 0x2338ea63, 0x53c2dd94, 0xc2c21634,
0xbbcbee56, 0x90bcb6de, 0xebfc7da1, 0xce591d76,
0x6f05e409, 0x4b7c0188, 0x39720a3d, 0x7c927c24,
0x86e3725f, 0x724d9db9, 0x1ac15bb4, 0xd39eb8fc,
0xed545578, 0x08fca5b5, 0xd83d7cd3, 0x4dad0fc4,
0x1e50ef5e, 0xb161e6f8, 0xa28514d9, 0x6c51133c,
0x6fd5c7e7, 0x56e14ec4, 0x362abfce, 0xddc6c837,
0xd79a3234, 0x92638212, 0x670efa8e, 0x406000e0,
0x3a39ce37, 0xd3faf5cf, 0xabc27737, 0x5ac52d1b,
0x5cb0679e, 0x4fa33742, 0xd3822740, 0x99bc9bbe,
0xd5118e9d, 0xbf0f7315, 0xd62d1c7e, 0xc700c47b,
0xb78c1b6b, 0x21a19045, 0xb26eb1be, 0x6a366eb4,
0x5748ab2f, 0xbc946e79, 0xc6a376d2, 0x6549c2c8,
0x530ff8ee, 0x468dde7d, 0xd5730a1d, 0x4cd04dc6,
0x2939bbdb, 0xa9ba4650, 0xac9526e8, 0xbe5ee304,
0xa1fad5f0, 0x6a2d519a, 0x63ef8ce2, 0x9a86ee22,
0xc089c2b8, 0x43242ef6, 0xa51e03aa, 0x9cf2d0a4,
0x83c061ba, 0x9be96a4d, 0x8fe51550, 0xba645bd6,
0x2826a2f9, 0xa73a3ae1, 0x4ba99586, 0xef5562e9,
0xc72fefd3, 0xf752f7da, 0x3f046f69, 0x77fa0a59,
0x80e4a915, 0x87b08601, 0x9b09e6ad, 0x3b3ee593,
0xe990fd5a, 0x9e34d797, 0x2cf0b7d9, 0x022b8b51,
0x96d5ac3a, 0x017da67d, 0xd1cf3ed6, 0x7c7d2d28,
0x1f9f25cf, 0xadf2b89b, 0x5ad6b472, 0x5a88f54c,
0xe029ac71, 0xe019a5e6, 0x47b0acfd, 0xed93fa9b,
0xe8d3c48d, 0x283b57cc, 0xf8d56629, 0x79132e28,
0x785f0191, 0xed756055, 0xf7960e44, 0xe3d35e8c,
0x15056dd4, 0x88f46dba, 0x03a16125, 0x0564f0bd,
0xc3eb9e15, 0x3c9057a2, 0x97271aec, 0xa93a072a,
0x1b3f6d9b, 0x1e6321f5, 0xf59c66fb, 0x26dcf319,
0x7533d928, 0xb155fdf5, 0x03563482, 0x8aba3cbb,
0x28517711, 0xc20ad9f8, 0xabcc5167, 0xccad925f,
0x4de81751, 0x3830dc8e, 0x379d5862, 0x9320f991,
0xea7a90c2, 0xfb3e7bce, 0x5121ce64, 0x774fbe32,
0xa8b6e37e, 0xc3293d46, 0x48de5369, 0x6413e680,
0xa2ae0810, 0xdd6db224, 0x69852dfd, 0x09072166,
0xb39a460a, 0x6445c0dd, 0x586cdecf, 0x1c20c8ae,
0x5bbef7dd, 0x1b588d40, 0xccd2017f, 0x6bb4e3bb,
0xdda26a7e, 0x3a59ff45, 0x3e350a44, 0xbcb4cdd5,
0x72eacea8, 0xfa6484bb, 0x8d6612ae, 0xbf3c6f47,
0xd29be463, 0x542f5d9e, 0xaec2771b, 0xf64e6370,
0x740e0d8d, 0xe75b1357, 0xf8721671, 0xaf537d5d,
0x4040cb08, 0x4eb4e2cc, 0x34d2466a, 0x0115af84,
0xe1b00428, 0x95983a1d, 0x06b89fb4, 0xce6ea048,
0x6f3f3b82, 0x3520ab82, 0x011a1d4b, 0x277227f8,
0x611560b1, 0xe7933fdc, 0xbb3a792b, 0x344525bd,
0xa08839e1, 0x51ce794b, 0x2f32c9b7, 0xa01fbac9,
0xe01cc87e, 0xbcc7d1f6, 0xcf0111c3, 0xa1e8aac7,
0x1a908749, 0xd44fbd9a, 0xd0dadecb, 0xd50ada38,
0x0339c32a, 0xc6913667, 0x8df9317c, 0xe0b12b4f,
0xf79e59b7, 0x43f5bb3a, 0xf2d519ff, 0x27d9459c,
0xbf97222c, 0x15e6fc2a, 0x0f91fc71, 0x9b941525,
0xfae59361, 0xceb69ceb, 0xc2a86459, 0x12baa8d1,
0xb6c1075e, 0xe3056a0c, 0x10d25065, 0xcb03a442,
0xe0ec6e0e, 0x1698db3b, 0x4c98a0be, 0x3278e964,
0x9f1f9532, 0xe0d392df, 0xd3a0342b, 0x8971f21e,
0x1b0a7441, 0x4ba3348c, 0xc5be7120, 0xc37632d8,
0xdf359f8d, 0x9b992f2e, 0xe60b6f47, 0x0fe3f11d,
0xe54cda54, 0x1edad891, 0xce6279cf, 0xcd3e7e6f,
0x1618b166, 0xfd2c1d05, 0x848fd2c5, 0xf6fb2299,
0xf523f357, 0xa6327623, 0x93a83531, 0x56cccd02,
0xacf08162, 0x5a75ebb5, 0x6e163697, 0x88d273cc,
0xde966292, 0x81b949d0, 0x4c50901b, 0x71c65614,
0xe6c6c7bd, 0x327a140a, 0x45e1d006, 0xc3f27b9a,
0xc9aa53fd, 0x62a80f00, 0xbb25bfe2, 0x35bdd2f6,
0x71126905, 0xb2040222, 0xb6cbcf7c, 0xcd769c2b,
0x53113ec0, 0x1640e3d3, 0x38abbd60, 0x2547adf0,
0xba38209c, 0xf746ce76, 0x77afa1c5, 0x20756060,
0x85cbfe4e, 0x8ae88dd8, 0x7aaaf9b0, 0x4cf9aa7e,
0x1948c25c, 0x02fb8a8c, 0x01c36ae4, 0xd6ebe1f9,
0x90d4f869, 0xa65cdea0, 0x3f09252d, 0xc208e69f,
0xb74e6132, 0xce77e25b, 0x578fdfe3, 0x3ac372e6
};
/* !!! DEBUG
public static void main(String[] argv) {
byte[] key = {
(byte)0xd3, (byte)0x96, (byte)0xcf, (byte)0x07, (byte)0xfa, (byte)0xa2, (byte)0x64,
(byte)0xfe, (byte)0xf3, (byte)0xa2, (byte)0x06, (byte)0x07, (byte)0x1a, (byte)0xb6,
(byte)0x13, (byte)0xf6, (byte)0x06, (byte)0x18, (byte)0xf6, (byte)0xcc, (byte)0x32,
(byte)0xd9, (byte)0xbb, (byte)0x56, (byte)0x5b, (byte)0xa6, (byte)0xa1, (byte)0x72,
(byte)0x28, (byte)0xb3, (byte)0xec, (byte)0x64 };
byte[] txt = {
(byte)0x2e, (byte)0xbe, (byte)0xc5, (byte)0xac, (byte)0x02, (byte)0xa1, (byte)0xd5,
(byte)0x7f, (byte)0x01, (byte)0x00, (byte)0x00, (byte)0x00, (byte)0x1f, (byte)0x43,
(byte)0x6f, (byte)0x72, (byte)0x72, (byte)0x75, (byte)0x70, (byte)0x74, (byte)0x65,
(byte)0x64, (byte)0x20, (byte)0x63, (byte)0x68, (byte)0x65, (byte)0x63, (byte)0x6b,
(byte)0x20, (byte)0x62, (byte)0x79, (byte)0x74, (byte)0x65, (byte)0x73, (byte)0x20,
(byte)0x6f, (byte)0x6e, (byte)0x20, (byte)0x69, (byte)0x6e, (byte)0x70, (byte)0x75,
(byte)0x74, (byte)0x2e, (byte)0x91, (byte)0x9a, (byte)0x57, (byte)0xdd
};
ENC: b5 44 c6 69 9b e7 d7 3d 45 25 0d 8b b3 5a 28 f5 98 eb 3e ea a3 27 e3 ac 64 de fc b7 f5 49 c6 3f 31 5c ce 99 79 b5 3b a9 cc 44 67 f0 46 a3 7e ed
byte[] txt = {
(byte)0x00, (byte)0x11, (byte)0x22, (byte)0x33, (byte)0x44, (byte)0x55, (byte)0x66,
(byte)0x77 };
byte[] enc;
byte[] dec;
System.out.println("key: " + printHex(key));
System.out.println("txt: " + printHex(txt));
Blowfish cipher = new Blowfish();
cipher.setKey(key);
enc = cipher.encrypt(txt);
System.out.println("enc: " + printHex(enc));
cipher = new Blowfish();
cipher.setKey(key);
dec = cipher.decrypt(enc);
System.out.println("dec: " + printHex(dec));
}
static String printHex(byte[] buf) {
byte[] out = new byte[buf.length + 1];
out[0] = 0;
System.arraycopy(buf, 0, out, 1, buf.length);
BigInteger big = new BigInteger(out);
return big.toString(16);
}
*/
}
jta_2.6+dfsg.orig/de/mud/ssh/DES3.java 0000644 0001750 0001750 00000007054 10610772601 016104 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
* Additional NOTICE: This file uses DES (see DES.java for copyright
* information!)
*/
package de.mud.ssh;
public final class DES3 extends Cipher {
static {
System.err.println("3DES Cipher.");
}
DES des1 = new DES();
DES des2 = new DES();
DES des3 = new DES();
public synchronized void encrypt(byte[] src, int srcOff, byte[] dest, int destOff, int len) {
des1.encrypt(src, srcOff, dest, destOff, len);
des2.decrypt(dest, destOff, dest, destOff, len);
des3.encrypt(dest, destOff, dest, destOff, len);
}
public synchronized void decrypt(byte[] src, int srcOff, byte[] dest, int destOff, int len) {
des3.decrypt(src, srcOff, dest, destOff, len);
des2.encrypt(dest, destOff, dest, destOff, len);
des1.decrypt(dest, destOff, dest, destOff, len);
}
public void setKey(byte[] key) {
byte[] subKey = new byte[8];
des1.setKey(key);
System.arraycopy(key, 8, subKey, 0, 8);
des2.setKey(subKey);
System.arraycopy(key, 16, subKey, 0, 8);
des3.setKey(subKey);
}
/* !!! DEBUG
public static void main(String[] argv) {
byte[] key = {
(byte)0x12, (byte)0x34, (byte)0x56, (byte)0x78,
(byte)0x87, (byte)0x65, (byte)0x43, (byte)0x21,
(byte)0x44, (byte)0x55, (byte)0x66, (byte)0x77,
(byte)0x87, (byte)0x65, (byte)0x43, (byte)0x21,
(byte)0x87, (byte)0x65, (byte)0x43, (byte)0x21,
(byte)0x12, (byte)0x34, (byte)0x56, (byte)0x78,
};
byte[] txt = {
(byte)0x00, (byte)0x11, (byte)0x22, (byte)0x33,
(byte)0x44, (byte)0x55, (byte)0x66, (byte)0x77,
(byte)0x00, (byte)0x11, (byte)0x22, (byte)0x33,
(byte)0x44, (byte)0x55, (byte)0x66, (byte)0x77,
(byte)0x00, (byte)0x11, (byte)0x22, (byte)0x33,
(byte)0x44, (byte)0x55, (byte)0x66, (byte)0x77
};
byte[] enc;
byte[] dec;
System.out.println("key: " + printHex(key));
System.out.println("txt: " + printHex(txt));
DES3 cipher = new DES3();
cipher.setKey(key);
enc = cipher.encrypt(txt);
System.out.println("enc: " + printHex(enc));
cipher = new DES3();
cipher.setKey(key);
dec = cipher.decrypt(enc);
System.out.println("dec: " + printHex(dec));
}
static String printHex(byte[] buf) {
byte[] out = new byte[buf.length + 1];
out[0] = 0;
System.arraycopy(buf, 0, out, 1, buf.length);
BigInteger big = new BigInteger(out);
return big.toString(16);
}
static String printHex(int i) {
BigInteger b = BigInteger.valueOf((long)i + 0x100000000L);
BigInteger c = BigInteger.valueOf(0x100000000L);
if(b.compareTo(c) != -1)
b = b.subtract(c);
return b.toString(16);
}
*/
}
jta_2.6+dfsg.orig/de/mud/ssh/DES.java 0000644 0001750 0001750 00000062572 10610772601 016027 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* IMPORTANT NOTICE:
* The code herein cannot be placed under GPL or any other license and
* is provided as reference and to support DES encryption for communication
* with some SSH servers. Please see license notice below for detailled
* information.
*
* ---
* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
* All rights reserved.
*
* This package is an SSL implementation written
* by Eric Young (eay@cryptsoft.com).
* The implementation was written so as to conform with Netscapes SSL.
*
* This library is free for commercial and non-commercial use as long as
* the following conditions are aheared to. The following conditions
* apply to all code found in this distribution, be it the RC4, RSA,
* lhash, DES, etc., code; not just the SSL code. The SSL documentation
* included with this distribution is covered by the same copyright terms
* except that the holder is Tim Hudson (tjh@cryptsoft.com).
*
* Copyright remains Eric Young's, and as such any Copyright notices in
* the code are not to be removed.
* If this package is used in a product, Eric Young should be given attribution
* as the author of the parts of the library used.
* This can be in the form of a textual message at program startup or
* in documentation (online or textual) provided with the package.
*
* 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 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. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* "This product includes cryptographic software written by
* Eric Young (eay@cryptsoft.com)"
* The word 'cryptographic' can be left out if the rouines from the library
* being used are not cryptographic related :-).
* 4. If you include any Windows specific code (or a derivative thereof) from
* the apps directory (application code) you must include an acknowledgement:
* "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
*
* THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
* ANY EXPRESS 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 THE AUTHOR OR CONTRIBUTORS 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.
*
* The licence and distribution terms for any publically available version or
* derivative of this code cannot be changed. i.e. this code cannot simply be
* copied and put under another distribution licence
* [including the GNU Public Licence.]
* ----
*/
package de.mud.ssh;
public final class DES extends Cipher {
static {
System.err.println("DES Cipher Copyright Eric Young.");
}
protected int[] key_schedule = new int[32];
protected int IV0 = 0;
protected int IV1 = 0;
public synchronized void encrypt(byte[] src, int srcOff, byte[] dest, int destOff, int len) {
int[] out = new int[2];
int iv0 = IV0;
int iv1 = IV1;
int end = srcOff + len;
for (int si = srcOff, di = destOff; si < end; si += 8, di += 8) {
iv0 ^= ((src[si] & 0xff) | ((src[si + 1] & 0xff) << 8) |
((src[si + 2] & 0xff) << 16) | ((src[si + 3] & 0xff) << 24));
iv1 ^= ((src[si + 4] & 0xff) | ((src[si + 5] & 0xff) << 8) |
((src[si + 6] & 0xff) << 16) | ((src[si + 7] & 0xff) << 24));
encrypt(iv0, iv1, out);
iv0 = out[0];
iv1 = out[1];
dest[di] = (byte) (iv0 & 0xff);
dest[di + 1] = (byte) ((iv0 >>> 8) & 0xff);
dest[di + 2] = (byte) ((iv0 >>> 16) & 0xff);
dest[di + 3] = (byte) ((iv0 >>> 24) & 0xff);
dest[di + 4] = (byte) (iv1 & 0xff);
dest[di + 5] = (byte) ((iv1 >>> 8) & 0xff);
dest[di + 6] = (byte) ((iv1 >>> 16) & 0xff);
dest[di + 7] = (byte) ((iv1 >>> 24) & 0xff);
}
IV0 = iv0;
IV1 = iv1;
}
public synchronized void decrypt(byte[] src, int srcOff, byte[] dest, int destOff, int len) {
int[] out = new int[2];
int iv0 = IV0;
int iv1 = IV1;
int d0;
int d1;
int end = srcOff + len;
for (int si = srcOff, di = destOff; si < end; si += 8, di += 8) {
d0 = ((src[si] & 0xff) | ((src[si + 1] & 0xff) << 8) |
((src[si + 2] & 0xff) << 16) | ((src[si + 3] & 0xff) << 24));
d1 = ((src[si + 4] & 0xff) | ((src[si + 5] & 0xff) << 8) |
((src[si + 6] & 0xff) << 16) | ((src[si + 7] & 0xff) << 24));
decrypt(d0, d1, out);
iv0 ^= out[0];
iv1 ^= out[1];
dest[di] = (byte) (iv0 & 0xff);
dest[di + 1] = (byte) ((iv0 >>> 8) & 0xff);
dest[di + 2] = (byte) ((iv0 >>> 16) & 0xff);
dest[di + 3] = (byte) ((iv0 >>> 24) & 0xff);
dest[di + 4] = (byte) (iv1 & 0xff);
dest[di + 5] = (byte) ((iv1 >>> 8) & 0xff);
dest[di + 6] = (byte) ((iv1 >>> 16) & 0xff);
dest[di + 7] = (byte) ((iv1 >>> 24) & 0xff);
iv0 = d0;
iv1 = d1;
}
IV0 = iv0;
IV1 = iv1;
}
public void setKey(byte[] key) {
int i, c, d, t, s, shifts;
c = ((key[0] & 0xff) | ((key[1] & 0xff) << 8) |
((key[2] & 0xff) << 16) | ((key[3] & 0xff) << 24));
d = ((key[4] & 0xff) | ((key[5] & 0xff) << 8) |
((key[6] & 0xff) << 16) | ((key[7] & 0xff) << 24));
t = ((d >>> 4) ^ c) & 0x0f0f0f0f;
c ^= t;
d ^= t << 4;
t = (((c << (16 - (-2))) ^ c) & 0xcccc0000);
c = c ^ t ^ (t >>> (16 - (-2)));
t = (((d << (16 - (-2))) ^ d) & 0xcccc0000);
d = d ^ t ^ (t >>> (16 - (-2)));
t = ((d >>> 1) ^ c) & 0x55555555;
c ^= t;
d ^= t << 1;
t = ((c >>> 8) ^ d) & 0x00ff00ff;
d ^= t;
c ^= t << 8;
t = ((d >>> 1) ^ c) & 0x55555555;
c ^= t;
d ^= t << 1;
d = ((d & 0xff) << 16) | (d & 0xff00) |
((d >>> 16) & 0xff) | ((c >>> 4) & 0xf000000);
c &= 0x0fffffff;
shifts = 0x7efc;
for (i = 0; i < 16; i++) {
if ((shifts & 1) != 0) {
c = ((c >>> 2) | (c << 26));
d = ((d >>> 2) | (d << 26));
} else {
c = ((c >>> 1) | (c << 27));
d = ((d >>> 1) | (d << 27));
}
shifts >>>= 1;
c &= 0x0fffffff;
d &= 0x0fffffff;
s = des_skb[0][(c) & 0x3f] |
des_skb[1][((c >>> 6) & 0x03) | ((c >>> 7) & 0x3c)] |
des_skb[2][((c >>> 13) & 0x0f) | ((c >>> 14) & 0x30)] |
des_skb[3][((c >>> 20) & 0x01) | ((c >>> 21) & 0x06) | ((c >>> 22) & 0x38)];
t = des_skb[4][(d) & 0x3f] |
des_skb[5][((d >>> 7) & 0x03) | ((d >>> 8) & 0x3c)] |
des_skb[6][(d >>> 15) & 0x3f] |
des_skb[7][((d >>> 21) & 0x0f) | ((d >>> 22) & 0x30)];
key_schedule[i * 2] = ((t << 16) | (s & 0xffff));
s = ((s >>> 16) | (t & 0xffff0000));
key_schedule[(i * 2) + 1] = (s << 4) | (s >>> 28);
}
}
public void encrypt(int l, int r, int[] out) {
int t = 0, u = 0, i;
t = ((r >>> 4) ^ l) & 0x0f0f0f0f;
l ^= t;
r ^= t << 4;
t = ((l >>> 16) ^ r) & 0x0000ffff;
r ^= t;
l ^= t << 16;
t = ((r >>> 2) ^ l) & 0x33333333;
l ^= t;
r ^= t << 2;
t = ((l >>> 8) ^ r) & 0x00ff00ff;
r ^= t;
l ^= t << 8;
t = ((r >>> 1) ^ l) & 0x55555555;
l ^= t;
r ^= t << 1;
t = (r << 1) | (r >>> 31);
r = (l << 1) | (l >>> 31);
l = t;
for (i = 0; i < 32; i += 4) {
u = r ^ key_schedule[i];
t = r ^ key_schedule[i + 1];
t = ((t >>> 4) + (t << 28));
l ^=
(des_SPtrans[1][(t) & 0x3f] | des_SPtrans[3][(t >>> 8) & 0x3f] |
des_SPtrans[5][(t >>> 16) & 0x3f] | des_SPtrans[7][(t >>> 24) & 0x3f] |
des_SPtrans[0][(u) & 0x3f] | des_SPtrans[2][(u >>> 8) & 0x3f] |
des_SPtrans[4][(u >>> 16) & 0x3f] | des_SPtrans[6][(u >>> 24) & 0x3f]);
u = l ^ key_schedule[i + 2];
t = l ^ key_schedule[i + 3];
t = ((t >>> 4) + (t << 28));
r ^=
(des_SPtrans[1][(t) & 0x3f] | des_SPtrans[3][(t >>> 8) & 0x3f] |
des_SPtrans[5][(t >>> 16) & 0x3f] | des_SPtrans[7][(t >>> 24) & 0x3f] |
des_SPtrans[0][(u) & 0x3f] | des_SPtrans[2][(u >>> 8) & 0x3f] |
des_SPtrans[4][(u >>> 16) & 0x3f] | des_SPtrans[6][(u >>> 24) & 0x3f]);
}
l = (l >>> 1) | (l << 31);
r = (r >>> 1) | (r << 31);
t = ((r >>> 1) ^ l) & 0x55555555;
l ^= t;
r ^= t << 1;
t = ((l >>> 8) ^ r) & 0x00ff00ff;
r ^= t;
l ^= t << 8;
t = ((r >>> 2) ^ l) & 0x33333333;
l ^= t;
r ^= t << 2;
t = ((l >>> 16) ^ r) & 0x0000ffff;
r ^= t;
l ^= t << 16;
t = ((r >>> 4) ^ l) & 0x0f0f0f0f;
l ^= t;
r ^= t << 4;
out[0] = l;
out[1] = r;
}
public void decrypt(int l, int r, int[] out) {
int t, u, i;
t = ((r >>> 4) ^ l) & 0x0f0f0f0f;
l ^= t;
r ^= t << 4;
t = ((l >>> 16) ^ r) & 0x0000ffff;
r ^= t;
l ^= t << 16;
t = ((r >>> 2) ^ l) & 0x33333333;
l ^= t;
r ^= t << 2;
t = ((l >>> 8) ^ r) & 0x00ff00ff;
r ^= t;
l ^= t << 8;
t = ((r >>> 1) ^ l) & 0x55555555;
l ^= t;
r ^= t << 1;
t = (r << 1) | (r >>> 31);
r = (l << 1) | (l >>> 31);
l = t;
for (i = 30; i > 0; i -= 4) {
u = r ^ key_schedule[i];
t = r ^ key_schedule[i + 1];
t = ((t >>> 4) + (t << 28));
l ^=
(des_SPtrans[1][(t) & 0x3f] | des_SPtrans[3][(t >>> 8) & 0x3f] |
des_SPtrans[5][(t >>> 16) & 0x3f] | des_SPtrans[7][(t >>> 24) & 0x3f] |
des_SPtrans[0][(u) & 0x3f] | des_SPtrans[2][(u >>> 8) & 0x3f] |
des_SPtrans[4][(u >>> 16) & 0x3f] | des_SPtrans[6][(u >>> 24) & 0x3f]);
u = l ^ key_schedule[i - 2];
t = l ^ key_schedule[i - 1];
t = ((t >>> 4) + (t << 28));
r ^=
(des_SPtrans[1][(t) & 0x3f] | des_SPtrans[3][(t >>> 8) & 0x3f] |
des_SPtrans[5][(t >>> 16) & 0x3f] | des_SPtrans[7][(t >>> 24) & 0x3f] |
des_SPtrans[0][(u) & 0x3f] | des_SPtrans[2][(u >>> 8) & 0x3f] |
des_SPtrans[4][(u >>> 16) & 0x3f] | des_SPtrans[6][(u >>> 24) & 0x3f]);
}
l = (l >>> 1) | (l << 31);
r = (r >>> 1) | (r << 31);
t = ((r >>> 1) ^ l) & 0x55555555;
l ^= t;
r ^= t << 1;
t = ((l >>> 8) ^ r) & 0x00ff00ff;
r ^= t;
l ^= t << 8;
t = ((r >>> 2) ^ l) & 0x33333333;
l ^= t;
r ^= t << 2;
t = ((l >>> 16) ^ r) & 0x0000ffff;
r ^= t;
l ^= t << 16;
t = ((r >>> 4) ^ l) & 0x0f0f0f0f;
l ^= t;
r ^= t << 4;
out[0] = l;
out[1] = r;
}
/* Table for key generation. This used to be in sk.h.
* Copyright (C) 1993 Eric Young - see README for more details
*/
final static int des_skb[][] = {
/* for C bits (numbered as per FIPS 46) 1 2 3 4 5 6 */
{0x00000000, 0x00000010, 0x20000000, 0x20000010,
0x00010000, 0x00010010, 0x20010000, 0x20010010,
0x00000800, 0x00000810, 0x20000800, 0x20000810,
0x00010800, 0x00010810, 0x20010800, 0x20010810,
0x00000020, 0x00000030, 0x20000020, 0x20000030,
0x00010020, 0x00010030, 0x20010020, 0x20010030,
0x00000820, 0x00000830, 0x20000820, 0x20000830,
0x00010820, 0x00010830, 0x20010820, 0x20010830,
0x00080000, 0x00080010, 0x20080000, 0x20080010,
0x00090000, 0x00090010, 0x20090000, 0x20090010,
0x00080800, 0x00080810, 0x20080800, 0x20080810,
0x00090800, 0x00090810, 0x20090800, 0x20090810,
0x00080020, 0x00080030, 0x20080020, 0x20080030,
0x00090020, 0x00090030, 0x20090020, 0x20090030,
0x00080820, 0x00080830, 0x20080820, 0x20080830,
0x00090820, 0x00090830, 0x20090820, 0x20090830},
/* for C bits (numbered as per FIPS 46) 7 8 10 11 12 13 */
{0x00000000, 0x02000000, 0x00002000, 0x02002000,
0x00200000, 0x02200000, 0x00202000, 0x02202000,
0x00000004, 0x02000004, 0x00002004, 0x02002004,
0x00200004, 0x02200004, 0x00202004, 0x02202004,
0x00000400, 0x02000400, 0x00002400, 0x02002400,
0x00200400, 0x02200400, 0x00202400, 0x02202400,
0x00000404, 0x02000404, 0x00002404, 0x02002404,
0x00200404, 0x02200404, 0x00202404, 0x02202404,
0x10000000, 0x12000000, 0x10002000, 0x12002000,
0x10200000, 0x12200000, 0x10202000, 0x12202000,
0x10000004, 0x12000004, 0x10002004, 0x12002004,
0x10200004, 0x12200004, 0x10202004, 0x12202004,
0x10000400, 0x12000400, 0x10002400, 0x12002400,
0x10200400, 0x12200400, 0x10202400, 0x12202400,
0x10000404, 0x12000404, 0x10002404, 0x12002404,
0x10200404, 0x12200404, 0x10202404, 0x12202404},
/* for C bits (numbered as per FIPS 46) 14 15 16 17 19 20 */
{0x00000000, 0x00000001, 0x00040000, 0x00040001,
0x01000000, 0x01000001, 0x01040000, 0x01040001,
0x00000002, 0x00000003, 0x00040002, 0x00040003,
0x01000002, 0x01000003, 0x01040002, 0x01040003,
0x00000200, 0x00000201, 0x00040200, 0x00040201,
0x01000200, 0x01000201, 0x01040200, 0x01040201,
0x00000202, 0x00000203, 0x00040202, 0x00040203,
0x01000202, 0x01000203, 0x01040202, 0x01040203,
0x08000000, 0x08000001, 0x08040000, 0x08040001,
0x09000000, 0x09000001, 0x09040000, 0x09040001,
0x08000002, 0x08000003, 0x08040002, 0x08040003,
0x09000002, 0x09000003, 0x09040002, 0x09040003,
0x08000200, 0x08000201, 0x08040200, 0x08040201,
0x09000200, 0x09000201, 0x09040200, 0x09040201,
0x08000202, 0x08000203, 0x08040202, 0x08040203,
0x09000202, 0x09000203, 0x09040202, 0x09040203},
/* for C bits (numbered as per FIPS 46) 21 23 24 26 27 28 */
{0x00000000, 0x00100000, 0x00000100, 0x00100100,
0x00000008, 0x00100008, 0x00000108, 0x00100108,
0x00001000, 0x00101000, 0x00001100, 0x00101100,
0x00001008, 0x00101008, 0x00001108, 0x00101108,
0x04000000, 0x04100000, 0x04000100, 0x04100100,
0x04000008, 0x04100008, 0x04000108, 0x04100108,
0x04001000, 0x04101000, 0x04001100, 0x04101100,
0x04001008, 0x04101008, 0x04001108, 0x04101108,
0x00020000, 0x00120000, 0x00020100, 0x00120100,
0x00020008, 0x00120008, 0x00020108, 0x00120108,
0x00021000, 0x00121000, 0x00021100, 0x00121100,
0x00021008, 0x00121008, 0x00021108, 0x00121108,
0x04020000, 0x04120000, 0x04020100, 0x04120100,
0x04020008, 0x04120008, 0x04020108, 0x04120108,
0x04021000, 0x04121000, 0x04021100, 0x04121100,
0x04021008, 0x04121008, 0x04021108, 0x04121108},
/* for D bits (numbered as per FIPS 46) 1 2 3 4 5 6 */
{0x00000000, 0x10000000, 0x00010000, 0x10010000,
0x00000004, 0x10000004, 0x00010004, 0x10010004,
0x20000000, 0x30000000, 0x20010000, 0x30010000,
0x20000004, 0x30000004, 0x20010004, 0x30010004,
0x00100000, 0x10100000, 0x00110000, 0x10110000,
0x00100004, 0x10100004, 0x00110004, 0x10110004,
0x20100000, 0x30100000, 0x20110000, 0x30110000,
0x20100004, 0x30100004, 0x20110004, 0x30110004,
0x00001000, 0x10001000, 0x00011000, 0x10011000,
0x00001004, 0x10001004, 0x00011004, 0x10011004,
0x20001000, 0x30001000, 0x20011000, 0x30011000,
0x20001004, 0x30001004, 0x20011004, 0x30011004,
0x00101000, 0x10101000, 0x00111000, 0x10111000,
0x00101004, 0x10101004, 0x00111004, 0x10111004,
0x20101000, 0x30101000, 0x20111000, 0x30111000,
0x20101004, 0x30101004, 0x20111004, 0x30111004},
/* for D bits (numbered as per FIPS 46) 8 9 11 12 13 14 */
{0x00000000, 0x08000000, 0x00000008, 0x08000008,
0x00000400, 0x08000400, 0x00000408, 0x08000408,
0x00020000, 0x08020000, 0x00020008, 0x08020008,
0x00020400, 0x08020400, 0x00020408, 0x08020408,
0x00000001, 0x08000001, 0x00000009, 0x08000009,
0x00000401, 0x08000401, 0x00000409, 0x08000409,
0x00020001, 0x08020001, 0x00020009, 0x08020009,
0x00020401, 0x08020401, 0x00020409, 0x08020409,
0x02000000, 0x0A000000, 0x02000008, 0x0A000008,
0x02000400, 0x0A000400, 0x02000408, 0x0A000408,
0x02020000, 0x0A020000, 0x02020008, 0x0A020008,
0x02020400, 0x0A020400, 0x02020408, 0x0A020408,
0x02000001, 0x0A000001, 0x02000009, 0x0A000009,
0x02000401, 0x0A000401, 0x02000409, 0x0A000409,
0x02020001, 0x0A020001, 0x02020009, 0x0A020009,
0x02020401, 0x0A020401, 0x02020409, 0x0A020409},
/* for D bits (numbered as per FIPS 46) 16 17 18 19 20 21 */
{0x00000000, 0x00000100, 0x00080000, 0x00080100,
0x01000000, 0x01000100, 0x01080000, 0x01080100,
0x00000010, 0x00000110, 0x00080010, 0x00080110,
0x01000010, 0x01000110, 0x01080010, 0x01080110,
0x00200000, 0x00200100, 0x00280000, 0x00280100,
0x01200000, 0x01200100, 0x01280000, 0x01280100,
0x00200010, 0x00200110, 0x00280010, 0x00280110,
0x01200010, 0x01200110, 0x01280010, 0x01280110,
0x00000200, 0x00000300, 0x00080200, 0x00080300,
0x01000200, 0x01000300, 0x01080200, 0x01080300,
0x00000210, 0x00000310, 0x00080210, 0x00080310,
0x01000210, 0x01000310, 0x01080210, 0x01080310,
0x00200200, 0x00200300, 0x00280200, 0x00280300,
0x01200200, 0x01200300, 0x01280200, 0x01280300,
0x00200210, 0x00200310, 0x00280210, 0x00280310,
0x01200210, 0x01200310, 0x01280210, 0x01280310},
/* for D bits (numbered as per FIPS 46) 22 23 24 25 27 28 */
{0x00000000, 0x04000000, 0x00040000, 0x04040000,
0x00000002, 0x04000002, 0x00040002, 0x04040002,
0x00002000, 0x04002000, 0x00042000, 0x04042000,
0x00002002, 0x04002002, 0x00042002, 0x04042002,
0x00000020, 0x04000020, 0x00040020, 0x04040020,
0x00000022, 0x04000022, 0x00040022, 0x04040022,
0x00002020, 0x04002020, 0x00042020, 0x04042020,
0x00002022, 0x04002022, 0x00042022, 0x04042022,
0x00000800, 0x04000800, 0x00040800, 0x04040800,
0x00000802, 0x04000802, 0x00040802, 0x04040802,
0x00002800, 0x04002800, 0x00042800, 0x04042800,
0x00002802, 0x04002802, 0x00042802, 0x04042802,
0x00000820, 0x04000820, 0x00040820, 0x04040820,
0x00000822, 0x04000822, 0x00040822, 0x04040822,
0x00002820, 0x04002820, 0x00042820, 0x04042820,
0x00002822, 0x04002822, 0x00042822, 0x04042822}
};
/* Tables used for executing des. This used to be in spr.h.
* Copyright (C) 1993 Eric Young - see README for more details
*/
final static int des_SPtrans[][] = {
/* nibble 0 */
{0x00820200, 0x00020000, 0x80800000, 0x80820200,
0x00800000, 0x80020200, 0x80020000, 0x80800000,
0x80020200, 0x00820200, 0x00820000, 0x80000200,
0x80800200, 0x00800000, 0x00000000, 0x80020000,
0x00020000, 0x80000000, 0x00800200, 0x00020200,
0x80820200, 0x00820000, 0x80000200, 0x00800200,
0x80000000, 0x00000200, 0x00020200, 0x80820000,
0x00000200, 0x80800200, 0x80820000, 0x00000000,
0x00000000, 0x80820200, 0x00800200, 0x80020000,
0x00820200, 0x00020000, 0x80000200, 0x00800200,
0x80820000, 0x00000200, 0x00020200, 0x80800000,
0x80020200, 0x80000000, 0x80800000, 0x00820000,
0x80820200, 0x00020200, 0x00820000, 0x80800200,
0x00800000, 0x80000200, 0x80020000, 0x00000000,
0x00020000, 0x00800000, 0x80800200, 0x00820200,
0x80000000, 0x80820000, 0x00000200, 0x80020200},
/* nibble 1 */
{0x10042004, 0x00000000, 0x00042000, 0x10040000,
0x10000004, 0x00002004, 0x10002000, 0x00042000,
0x00002000, 0x10040004, 0x00000004, 0x10002000,
0x00040004, 0x10042000, 0x10040000, 0x00000004,
0x00040000, 0x10002004, 0x10040004, 0x00002000,
0x00042004, 0x10000000, 0x00000000, 0x00040004,
0x10002004, 0x00042004, 0x10042000, 0x10000004,
0x10000000, 0x00040000, 0x00002004, 0x10042004,
0x00040004, 0x10042000, 0x10002000, 0x00042004,
0x10042004, 0x00040004, 0x10000004, 0x00000000,
0x10000000, 0x00002004, 0x00040000, 0x10040004,
0x00002000, 0x10000000, 0x00042004, 0x10002004,
0x10042000, 0x00002000, 0x00000000, 0x10000004,
0x00000004, 0x10042004, 0x00042000, 0x10040000,
0x10040004, 0x00040000, 0x00002004, 0x10002000,
0x10002004, 0x00000004, 0x10040000, 0x00042000},
/* nibble 2 */
{0x41000000, 0x01010040, 0x00000040, 0x41000040,
0x40010000, 0x01000000, 0x41000040, 0x00010040,
0x01000040, 0x00010000, 0x01010000, 0x40000000,
0x41010040, 0x40000040, 0x40000000, 0x41010000,
0x00000000, 0x40010000, 0x01010040, 0x00000040,
0x40000040, 0x41010040, 0x00010000, 0x41000000,
0x41010000, 0x01000040, 0x40010040, 0x01010000,
0x00010040, 0x00000000, 0x01000000, 0x40010040,
0x01010040, 0x00000040, 0x40000000, 0x00010000,
0x40000040, 0x40010000, 0x01010000, 0x41000040,
0x00000000, 0x01010040, 0x00010040, 0x41010000,
0x40010000, 0x01000000, 0x41010040, 0x40000000,
0x40010040, 0x41000000, 0x01000000, 0x41010040,
0x00010000, 0x01000040, 0x41000040, 0x00010040,
0x01000040, 0x00000000, 0x41010000, 0x40000040,
0x41000000, 0x40010040, 0x00000040, 0x01010000},
/* nibble 3 */
{0x00100402, 0x04000400, 0x00000002, 0x04100402,
0x00000000, 0x04100000, 0x04000402, 0x00100002,
0x04100400, 0x04000002, 0x04000000, 0x00000402,
0x04000002, 0x00100402, 0x00100000, 0x04000000,
0x04100002, 0x00100400, 0x00000400, 0x00000002,
0x00100400, 0x04000402, 0x04100000, 0x00000400,
0x00000402, 0x00000000, 0x00100002, 0x04100400,
0x04000400, 0x04100002, 0x04100402, 0x00100000,
0x04100002, 0x00000402, 0x00100000, 0x04000002,
0x00100400, 0x04000400, 0x00000002, 0x04100000,
0x04000402, 0x00000000, 0x00000400, 0x00100002,
0x00000000, 0x04100002, 0x04100400, 0x00000400,
0x04000000, 0x04100402, 0x00100402, 0x00100000,
0x04100402, 0x00000002, 0x04000400, 0x00100402,
0x00100002, 0x00100400, 0x04100000, 0x04000402,
0x00000402, 0x04000000, 0x04000002, 0x04100400},
/* nibble 4 */
{0x02000000, 0x00004000, 0x00000100, 0x02004108,
0x02004008, 0x02000100, 0x00004108, 0x02004000,
0x00004000, 0x00000008, 0x02000008, 0x00004100,
0x02000108, 0x02004008, 0x02004100, 0x00000000,
0x00004100, 0x02000000, 0x00004008, 0x00000108,
0x02000100, 0x00004108, 0x00000000, 0x02000008,
0x00000008, 0x02000108, 0x02004108, 0x00004008,
0x02004000, 0x00000100, 0x00000108, 0x02004100,
0x02004100, 0x02000108, 0x00004008, 0x02004000,
0x00004000, 0x00000008, 0x02000008, 0x02000100,
0x02000000, 0x00004100, 0x02004108, 0x00000000,
0x00004108, 0x02000000, 0x00000100, 0x00004008,
0x02000108, 0x00000100, 0x00000000, 0x02004108,
0x02004008, 0x02004100, 0x00000108, 0x00004000,
0x00004100, 0x02004008, 0x02000100, 0x00000108,
0x00000008, 0x00004108, 0x02004000, 0x02000008},
/* nibble 5 */
{0x20000010, 0x00080010, 0x00000000, 0x20080800,
0x00080010, 0x00000800, 0x20000810, 0x00080000,
0x00000810, 0x20080810, 0x00080800, 0x20000000,
0x20000800, 0x20000010, 0x20080000, 0x00080810,
0x00080000, 0x20000810, 0x20080010, 0x00000000,
0x00000800, 0x00000010, 0x20080800, 0x20080010,
0x20080810, 0x20080000, 0x20000000, 0x00000810,
0x00000010, 0x00080800, 0x00080810, 0x20000800,
0x00000810, 0x20000000, 0x20000800, 0x00080810,
0x20080800, 0x00080010, 0x00000000, 0x20000800,
0x20000000, 0x00000800, 0x20080010, 0x00080000,
0x00080010, 0x20080810, 0x00080800, 0x00000010,
0x20080810, 0x00080800, 0x00080000, 0x20000810,
0x20000010, 0x20080000, 0x00080810, 0x00000000,
0x00000800, 0x20000010, 0x20000810, 0x20080800,
0x20080000, 0x00000810, 0x00000010, 0x20080010},
/* nibble 6 */
{0x00001000, 0x00000080, 0x00400080, 0x00400001,
0x00401081, 0x00001001, 0x00001080, 0x00000000,
0x00400000, 0x00400081, 0x00000081, 0x00401000,
0x00000001, 0x00401080, 0x00401000, 0x00000081,
0x00400081, 0x00001000, 0x00001001, 0x00401081,
0x00000000, 0x00400080, 0x00400001, 0x00001080,
0x00401001, 0x00001081, 0x00401080, 0x00000001,
0x00001081, 0x00401001, 0x00000080, 0x00400000,
0x00001081, 0x00401000, 0x00401001, 0x00000081,
0x00001000, 0x00000080, 0x00400000, 0x00401001,
0x00400081, 0x00001081, 0x00001080, 0x00000000,
0x00000080, 0x00400001, 0x00000001, 0x00400080,
0x00000000, 0x00400081, 0x00400080, 0x00001080,
0x00000081, 0x00001000, 0x00401081, 0x00400000,
0x00401080, 0x00000001, 0x00001001, 0x00401081,
0x00400001, 0x00401080, 0x00401000, 0x00001001},
/* nibble 7 */
{0x08200020, 0x08208000, 0x00008020, 0x00000000,
0x08008000, 0x00200020, 0x08200000, 0x08208020,
0x00000020, 0x08000000, 0x00208000, 0x00008020,
0x00208020, 0x08008020, 0x08000020, 0x08200000,
0x00008000, 0x00208020, 0x00200020, 0x08008000,
0x08208020, 0x08000020, 0x00000000, 0x00208000,
0x08000000, 0x00200000, 0x08008020, 0x08200020,
0x00200000, 0x00008000, 0x08208000, 0x00000020,
0x00200000, 0x00008000, 0x08000020, 0x08208020,
0x00008020, 0x08000000, 0x00000000, 0x00208000,
0x08200020, 0x08008020, 0x08008000, 0x00200020,
0x08208000, 0x00000020, 0x00200020, 0x08008000,
0x08208020, 0x00200000, 0x08200000, 0x08000020,
0x00208000, 0x00008020, 0x08008020, 0x08200000,
0x00000020, 0x08208000, 0x00208020, 0x00000000,
0x08000000, 0x08200020, 0x00008000, 0x00208020}
};
}
jta_2.6+dfsg.orig/de/mud/ssh/SshPacket2.java 0000644 0001750 0001750 00000020751 10610772601 017354 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.ssh;
import java.io.IOException;
import java.math.BigInteger;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
/**
* @author Marcus Meissner
* @version $Id: SshPacket2.java 499 2005-09-29 08:24:54Z leo $
*/
public class SshPacket2 extends SshPacket {
private final static boolean debug = true;
//SSH_RECEIVE_PACKET
private byte[] packet_length_array = new byte[5]; // 4 bytes
private int packet_length = 0; // 32-bit sign int
private int padlen = 0; // packet length 1 byte unsigned
private byte[] crc_array = new byte[4]; // 32-bit crc
private int position = 0;
private int phase_packet = 0;
private final int PHASE_packet_length = 0;
private final int PHASE_block = 1;
private SshCrypto crypto = null;
public SshPacket2(SshCrypto _crypto) {
/* receiving packet */
position = 0;
phase_packet = PHASE_packet_length;
crypto = _crypto;
}
public SshPacket2(byte newType) {
setType(newType);
}
/**
* Return the mp-int at the position offset in the data
* First 4 bytes are the number of bytes in the integer, msb first
* (for example, the value 0x00012345 would have 17 bits). The
* value zero has zero bits. It is permissible that the number of
* bits be larger than the real number of bits.
* The number of bits is followed by (bits + 7) / 8 bytes of binary
* data, msb first, giving the value of the integer.
*/
public BigInteger getMpInt() {
return new BigInteger(1,getBytes(getInt32()));
}
public void putMpInt(BigInteger bi) {
byte[] mpbytes = bi.toByteArray(), xbytes;
int i;
for (i = 0; (i < mpbytes.length) && ( mpbytes[i] == 0 ) ; i++) /* EMPTY */ ;
xbytes = new byte[mpbytes.length - i];
System.arraycopy(mpbytes,i,xbytes,0,mpbytes.length - i);
putInt32(mpbytes.length - i);
putBytes(xbytes);
}
public byte[] getPayLoad(SshCrypto xcrypt, long seqnr)
throws IOException {
byte[] data = getData();
int blocksize = 8;
// crypted data is:
// packet length [ payloadlen + padlen + type + data ]
packet_length = 4 + 1 + 1;
if (data!=null)
packet_length += data.length;
// pad it up to full blocksize.
// If not crypto, zeroes, otherwise random.
// (zeros because we do not want to tell the attacker the state of our
// random generator)
int padlen = blocksize - (packet_length % blocksize);
if (padlen < 4) padlen += blocksize;
byte[] padding = new byte[padlen];
System.out.println("packet length is "+packet_length+", padlen is "+padlen);
if (xcrypt == null)
for(int i=0; i>8) & 0xff);
block[1] = (byte) ((xlen>>16) & 0xff);
block[0] = (byte) ((xlen>>24) & 0xff);
block[4] = (byte)padlen;
block[5] = getType();
System.arraycopy(data,0,block,6,data.length);
System.arraycopy(padding,0,block,6+data.length,padlen);
byte[] md5sum;
if (xcrypt != null) {
MessageDigest md5 = null;
try {
md5 = MessageDigest.getInstance("MD5");
} catch (NoSuchAlgorithmException e) {
System.err.println("SshPacket2: unable to load message digest algorithm: "+e);
}
byte[] seqint = new byte[4];
seqint[0] = (byte)((seqnr >> 24) & 0xff);
seqint[1] = (byte)((seqnr >> 16) & 0xff);
seqint[2] = (byte)((seqnr >> 8) & 0xff);
seqint[3] = (byte)((seqnr ) & 0xff);
md5.update(seqint,0,4);
md5.update(block,0,block.length);
md5sum = md5.digest();
} else {
md5sum = new byte[0];
}
if (xcrypt != null)
block = xcrypt.encrypt(block);
byte[] sendblock = new byte[block.length + md5sum.length];
System.arraycopy(block,0,sendblock,0,block.length);
System.arraycopy(md5sum,0,sendblock,block.length,md5sum.length);
return sendblock;
};
private byte block[];
public byte[] addPayload(byte buff[]) {
int boffset = 0;
byte b;
byte[] newbuf = null;
int hmaclen = 0;
if (crypto!=null) hmaclen = 16;
System.out.println("addPayload2 "+buff.length);
/*
* Note: The whole packet is encrypted, except for the MAC.
*
* (So I have to rewrite it again).
*/
while(boffset < buff.length) {
switch (phase_packet) {
// 4 bytes
// Packet length: 32 bit unsigned integer
// gives the length of the packet, not including the length field
// and padding. maximum is 262144 bytes.
case PHASE_packet_length:
packet_length_array[position++] = buff[boffset++];
if (position==5) {
packet_length =
(packet_length_array[3]&0xff) +
((packet_length_array[2]&0xff)<<8) +
((packet_length_array[1]&0xff)<<16) +
((packet_length_array[0]&0xff)<<24);
padlen = packet_length_array[4];
position=0;
System.out.println("SSH2: packet length "+packet_length);
System.out.println("SSH2: padlen "+padlen);
packet_length += hmaclen; /* len(md5) */
block = new byte[packet_length-1]; /* padlen already done */
phase_packet++;
}
break; //switch (phase_packet)
//8*(packet_length/8 +1) bytes
case PHASE_block :
if (position < block.length) {
int amount = buff.length - boffset;
if (amount > 0) {
if (amount > block.length - position)
amount = block.length - position;
System.arraycopy(buff,boffset,block,position,amount);
boffset += amount;
position += amount;
}
}
if (position==block.length) { //the block is complete
if (buff.length>boffset) {
newbuf = new byte[buff.length-boffset];
System.arraycopy(buff,boffset,newbuf,0,buff.length-boffset);
}
byte[] decryptedBlock = new byte[block.length - hmaclen];
byte[] data;
packet_length -= hmaclen;
System.arraycopy(block,0,decryptedBlock,0,block.length-hmaclen);
if (crypto != null)
decryptedBlock = crypto.decrypt(decryptedBlock);
for (int i = 0; i < decryptedBlock.length; i++)
System.out.print(" "+decryptedBlock[i]);
System.out.println("");
setType(decryptedBlock[0]);
System.err.println("Packet type: "+getType());
System.err.println("Packet len: "+packet_length);
//data
if(packet_length > padlen+1+1) {
data = new byte[packet_length-1-padlen-1];
System.arraycopy(decryptedBlock,1,data,0,data.length);
putData(data);
} else {
putData(null);
}
/* MAC! */
return newbuf;
}
break;
}
}
return null;
};
/*
private boolean checkCrc(){
byte[] crc_arrayCheck = new byte[4];
long crcCheck;
crcCheck = SshMisc.crc32(decryptedBlock, decryptedBlock.length-4);
crc_arrayCheck[3] = (byte) (crcCheck & 0xff);
crc_arrayCheck[2] = (byte) ((crcCheck>>8) & 0xff);
crc_arrayCheck[1] = (byte) ((crcCheck>>16) & 0xff);
crc_arrayCheck[0] = (byte) ((crcCheck>>24) & 0xff);
if(debug) {
System.err.println(crc_arrayCheck[3]+" == "+crc_array[3]);
System.err.println(crc_arrayCheck[2]+" == "+crc_array[2]);
System.err.println(crc_arrayCheck[1]+" == "+crc_array[1]);
System.err.println(crc_arrayCheck[0]+" == "+crc_array[0]);
}
if (crc_arrayCheck[3] != crc_array[3]) return false;
if (crc_arrayCheck[2] != crc_array[2]) return false;
if (crc_arrayCheck[1] != crc_array[1]) return false;
if (crc_arrayCheck[0] != crc_array[0]) return false;
return true;
}
*/
}
jta_2.6+dfsg.orig/de/mud/ssh/IDEA.java 0000644 0001750 0001750 00000022517 10610772601 016111 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
/*
* Information about the base of this code:
* Xuejia Lai: On the Design and Security of Block Ciphers, ETH
* Series in Information Processing, vol. 1, Hartung-Gorre
* Verlag, Konstanz, Switzerland, 1992. Another source was Bruce
* Schneier: Applied Cryptography, John Wiley & Sons, 1994.
*
* The IDEA mathematical formula may be covered by one or more of the
* following patents: PCT/CH91/00117, EP 0 482 154 B1, US Pat. 5,214,703.
*/
package de.mud.ssh;
/**
* @author Marcus Meissner
* @version $Id: IDEA.java 499 2005-09-29 08:24:54Z leo $
*/
public final class IDEA extends Cipher {
protected int[] key_schedule = new int[52];
protected int IV0 = 0;
protected int IV1 = 0;
public synchronized void encrypt(byte[] src, int srcOff, byte[] dest, int destOff, int len) {
int[] out = new int[2];
int iv0 = IV0;
int iv1 = IV1;
int end = srcOff + len;
for (int si = srcOff, di = destOff; si < end; si += 8, di += 8) {
encrypt(iv0, iv1, out);
iv0 = out[0];
iv1 = out[1];
iv0 ^= ((src[si + 3] & 0xff) | ((src[si + 2] & 0xff) << 8) |
((src[si + 1] & 0xff) << 16) | ((src[si] & 0xff) << 24));
iv1 ^= ((src[si + 7] & 0xff) | ((src[si + 6] & 0xff) << 8) |
((src[si + 5] & 0xff) << 16) | ((src[si + 4] & 0xff) << 24));
if (di + 8 <= end) {
dest[di + 3] = (byte) (iv0 & 0xff);
dest[di + 2] = (byte) ((iv0 >>> 8) & 0xff);
dest[di + 1] = (byte) ((iv0 >>> 16) & 0xff);
dest[di] = (byte) ((iv0 >>> 24) & 0xff);
dest[di + 7] = (byte) (iv1 & 0xff);
dest[di + 6] = (byte) ((iv1 >>> 8) & 0xff);
dest[di + 5] = (byte) ((iv1 >>> 16) & 0xff);
dest[di + 4] = (byte) ((iv1 >>> 24) & 0xff);
} else {
switch (end - di) {
case 7:
dest[di + 6] = (byte) ((iv1 >>> 8) & 0xff);
case 6:
dest[di + 5] = (byte) ((iv1 >>> 16) & 0xff);
case 5:
dest[di + 4] = (byte) ((iv1 >>> 24) & 0xff);
case 4:
dest[di + 3] = (byte) (iv0 & 0xff);
case 3:
dest[di + 2] = (byte) ((iv0 >>> 8) & 0xff);
case 2:
dest[di + 1] = (byte) ((iv0 >>> 16) & 0xff);
case 1:
dest[di] = (byte) ((iv0 >>> 24) & 0xff);
}
}
}
IV0 = iv0;
IV1 = iv1;
}
public synchronized void decrypt(byte[] src, int srcOff, byte[] dest, int destOff, int len) {
int[] out = new int[2];
int iv0 = IV0;
int iv1 = IV1;
int plain0, plain1;
int end = srcOff + len;
for (int si = srcOff, di = destOff; si < end; si += 8, di += 8) {
decrypt(iv0, iv1, out);
iv0 = ((src[si + 3] & 0xff) | ((src[si + 2] & 0xff) << 8) |
((src[si + 1] & 0xff) << 16) | ((src[si] & 0xff) << 24));
iv1 = ((src[si + 7] & 0xff) | ((src[si + 6] & 0xff) << 8) |
((src[si + 5] & 0xff) << 16) | ((src[si + 4] & 0xff) << 24));
plain0 = out[0] ^ iv0;
plain1 = out[1] ^ iv1;
if (di + 8 <= end) {
dest[di + 3] = (byte) (plain0 & 0xff);
dest[di + 2] = (byte) ((plain0 >>> 8) & 0xff);
dest[di + 1] = (byte) ((plain0 >>> 16) & 0xff);
dest[di] = (byte) ((plain0 >>> 24) & 0xff);
dest[di + 7] = (byte) (plain1 & 0xff);
dest[di + 6] = (byte) ((plain1 >>> 8) & 0xff);
dest[di + 5] = (byte) ((plain1 >>> 16) & 0xff);
dest[di + 4] = (byte) ((plain1 >>> 24) & 0xff);
} else {
switch (end - di) {
case 7:
dest[di + 6] = (byte) ((plain1 >>> 8) & 0xff);
case 6:
dest[di + 5] = (byte) ((plain1 >>> 16) & 0xff);
case 5:
dest[di + 4] = (byte) ((plain1 >>> 24) & 0xff);
case 4:
dest[di + 3] = (byte) (plain0 & 0xff);
case 3:
dest[di + 2] = (byte) ((plain0 >>> 8) & 0xff);
case 2:
dest[di + 1] = (byte) ((plain0 >>> 16) & 0xff);
case 1:
dest[di] = (byte) ((plain0 >>> 24) & 0xff);
}
}
}
IV0 = iv0;
IV1 = iv1;
}
public void setKey(byte[] key) {
int i, ki = 0, j = 0;
for (i = 0; i < 8; i++)
key_schedule[i] = ((key[2 * i] & 0xff) << 8) | (key[(2 * i) + 1] & 0xff);
for (i = 8, j = 0; i < 52; i++) {
j++;
key_schedule[ki + j + 7] = ((key_schedule[ki + (j & 7)] << 9) |
(key_schedule[ki + ((j + 1) & 7)] >>> 7)) & 0xffff;
ki += j & 8;
j &= 7;
}
}
public final void encrypt(int l, int r, int[] out) {
int t1 = 0, t2 = 0, x1, x2, x3, x4, ki = 0;
x1 = (l >>> 16);
x2 = (l & 0xffff);
x3 = (r >>> 16);
x4 = (r & 0xffff);
for (int round = 0; round < 8; round++) {
x1 = mulop(x1 & 0xffff, key_schedule[ki++]);
x2 = (x2 + key_schedule[ki++]);
x3 = (x3 + key_schedule[ki++]);
x4 = mulop(x4 & 0xffff, key_schedule[ki++]);
t1 = (x1 ^ x3);
t2 = (x2 ^ x4);
t1 = mulop(t1 & 0xffff, key_schedule[ki++]);
t2 = (t1 + t2);
t2 = mulop(t2 & 0xffff, key_schedule[ki++]);
t1 = (t1 + t2);
x1 = (x1 ^ t2);
x4 = (x4 ^ t1);
t1 = (t1 ^ x2);
x2 = (t2 ^ x3);
x3 = t1;
}
t2 = x2;
x1 = mulop(x1 & 0xffff, key_schedule[ki++]);
x2 = (t1 + key_schedule[ki++]);
x3 = ((t2 + key_schedule[ki++]) & 0xffff);
x4 = mulop(x4 & 0xffff, key_schedule[ki]);
out[0] = (x1 << 16) | (x2 & 0xffff);
out[1] = (x3 << 16) | (x4 & 0xffff);
}
public final void decrypt(int l, int r, int[] out) {
encrypt(l, r, out);
}
public static final int mulop(int a, int b) {
int ab = a * b;
if (ab != 0) {
int lo = ab & 0xffff;
int hi = (ab >>> 16) & 0xffff;
return ((lo - hi) + ((lo < hi) ? 1 : 0));
}
if (a == 0)
return (1 - b);
return (1 - a);
}
/* !!! REMOVE DEBUG !!!
public static void main(String[] argv) {
byte[] key = {
(byte) 0xd3, (byte) 0x96, (byte) 0xcf, (byte) 0x07, (byte) 0xfa, (byte) 0xa2, (byte) 0x64,
(byte) 0xfe, (byte) 0xf3, (byte) 0xa2, (byte) 0x06, (byte) 0x07, (byte) 0x1a, (byte) 0xb6,
(byte) 0x13, (byte) 0xf6
};
byte[] txt = {
(byte) 0x2e, (byte) 0xbe, (byte) 0xc5, (byte) 0xac, (byte) 0x02, (byte) 0xa1, (byte) 0xd5,
(byte) 0x7f, (byte) 0x01, (byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x1f, (byte) 0x43,
(byte) 0x6f, (byte) 0x72, (byte) 0x72, (byte) 0x75, (byte) 0x70, (byte) 0x74, (byte) 0x65,
(byte) 0x64, (byte) 0x20, (byte) 0x63, (byte) 0x68, (byte) 0x65, (byte) 0x63, (byte) 0x6b,
(byte) 0x20, (byte) 0x62, (byte) 0x79, (byte) 0x74, (byte) 0x65, (byte) 0x73, (byte) 0x20,
(byte) 0x6f, (byte) 0x6e, (byte) 0x20, (byte) 0x69, (byte) 0x6e, (byte) 0x70, (byte) 0x75,
(byte) 0x74, (byte) 0x2e, (byte) 0x91, (byte) 0x9a, (byte) 0x57, (byte) 0xdd
};
byte[] enc;
byte[] dec;
System.out.println("key: " + printHex(key));
System.out.println("txt: " + printHex(txt));
IDEA cipher = new IDEA();
cipher.setKey(key);
for (int i = 0; i < 52; i++) {
if ((i & 0x7) == 0)
System.out.println("");
System.out.print(" " + cipher.key_schedule[i]);
}
enc = cipher.encrypt(txt);
System.out.println("enc: " + printHex(enc));
cipher = new IDEA();
cipher.setKey(key);
dec = cipher.decrypt(enc);
System.out.println("dec: " + printHex(dec));
}
static String printHex(byte[] buf) {
byte[] out = new byte[buf.length + 1];
out[0] = 0;
System.arraycopy(buf, 0, out, 1, buf.length);
BigInteger big = new BigInteger(out);
return big.toString(16);
}
*/
}
/*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/ jta_2.6+dfsg.orig/de/mud/flash/ 0000755 0001750 0001750 00000000000 10610772601 015035 5 ustar paul paul jta_2.6+dfsg.orig/de/mud/flash/FlashTerminal.java 0000644 0001750 0001750 00000025516 10610772601 020442 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.flash;
import de.mud.terminal.VDUBuffer;
import de.mud.terminal.VDUDisplay;
import de.mud.terminal.VDUInput;
import org.jdom.Element;
import org.jdom.JDOMException;
import org.jdom.Text;
import org.jdom.input.SAXBuilder;
import org.jdom.output.XMLOutputter;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.StringReader;
import java.net.Socket;
import java.util.Iterator;
public class FlashTerminal implements VDUDisplay, Runnable {
private final static int debug = 0;
private boolean simpleMode = true;
private boolean terminalReady = false;
private VDUBuffer buffer;
private BufferedWriter writer;
private BufferedReader reader;
/** A list of colors used for representation of the display */
private String color[] = {"#000000",
"#ff0000",
"#00ff00",
"#ffff00",
"#0000ff",
"#ff00ff",
"#00ffff",
"#ffffff",
null, // bold color
null, // inverted color
};
public void start(Socket flashSocket) {
try {
if (debug > 0) System.err.println("FlashTerminal: got connection: " + flashSocket);
writer = new BufferedWriter(new OutputStreamWriter(flashSocket.getOutputStream()));
reader = new BufferedReader(new InputStreamReader(flashSocket.getInputStream()));
(new Thread(this)).run();
} catch (IOException e) {
System.err.println("FlashTerminal: unable to accept connection: " + e);
}
}
public void updateScrollBar() {
// dont do anything... or?
}
protected void disconnect() {
// do nothing by default
}
/**
* Output performance information
* @param msg message from the flash client
*/
private void perf(String msg) {
System.err.print(System.currentTimeMillis());
System.err.println(" " + msg);
}
public void run() {
char buf[] = new char[1024];
int n = 0;
do {
try {
if (debug > 0)
System.err.println("FlashTerminal: waiting for keyboard input ...");
// read from flash frontend
n = reader.read(buf);
if (n > 0 && buf[0] == '<') {
handleXMLCommand(new String(buf, 0, n - 1));
continue;
}
if (debug > 0)
System.err.println("FlashTerminal: got " + n + " keystokes: " + (n > 0 ? new String(buf, 0, n) : ""));
if (n > 0 && (buffer instanceof VDUInput)) {
if (simpleMode) {
// in simple mode simply write the data to the remote host
// we have to convert the chars to bytes ...
byte tmp[] = new byte[n];
for (int i = 0; i < n - 1; i++) {
tmp[i] = (byte) buf[i];
}
((VDUInput) buffer).write((byte[]) tmp);
} else {
// write each key for it's own
for (int i = 0; i < n - 1; i++) {
((VDUInput) buffer).keyTyped((int) buf[i], buf[i], 0);
}
}
}
} catch (IOException e) {
System.err.println("FlashTerminal: i/o exception reading keyboard input");
}
} while (n >= 0);
if (debug > 0) System.err.println("FlashTerminal: end of keyboard input");
disconnect();
}
private SAXBuilder builder = new SAXBuilder();
/**
* Handle XML Commands sent by the remote host.
* @param xml string containing the xml commands
*/
private void handleXMLCommand(String xml) {
System.err.println("handleXMLCommand(" + xml + ")");
StringReader src = new StringReader("" + xml.replace('\0', ' ') + "");
try {
Element root = builder.build(src).getRootElement();
Iterator cmds = root.getChildren().iterator();
while (cmds.hasNext()) {
Element command = (Element) cmds.next();
String name = command.getName();
if ("mode".equals(name)) {
simpleMode = "true".equals(command.getAttribute("simple").getValue().toLowerCase());
} else if ("timestamp".equals(name)) {
perf(command.getAttribute("msg").getValue());
} else if ("start".equals(name)) {
terminalReady = true;
buffer.update[0] = true;
redraw();
}
}
} catch (JDOMException e) {
System.err.println("error reading command: " + e);
}
}
// placeholder for the terminal element and the xml outputter
private Element terminal = new Element("terminal");
private XMLOutputter xmlOutputter = new XMLOutputter();
/**
* Redraw terminal (send new/changed terminal lines to flash frontend).
*/
public void redraw() {
if (debug > 0)
System.err.println("FlashTerminal: redraw()");
if (terminalReady && writer != null) {
try {
// remove children from terminal
terminal.removeChildren();
if (simpleMode) {
Element result = redrawSimpleTerminal(terminal);
if (result.hasChildren()) {
xmlOutputter.output(result, writer);
}
} else {
xmlOutputter.output(redrawFullTerminal(terminal), writer);
}
writer.write(0);
writer.flush();
if (debug > 0)
System.err.println("FlashTerminal: flushed data ...");
} catch (IOException e) {
System.err.println("FlashTerminal: error writing to client: " + e);
writer = null;
}
}
}
/**
* The simple terminal only draws new lines and ignores
* changes on lines aready written.
* @param terminal
* @return
*/
private Element redrawSimpleTerminal(Element terminal) {
terminal.setAttribute("simple", "true");
int checkPoint = buffer.scrollMarker < 0 ? 0 : buffer.scrollMarker;
// first check whether our check point is in the back buffer
while (checkPoint < buffer.screenBase) {
terminal.addContent(redrawLine(0, checkPoint++));
}
// then dive into the screen area ...
while (checkPoint < buffer.bufSize) {
int line = checkPoint - (buffer.screenBase - 1);
if (line > buffer.getCursorRow())
break;
terminal.addContent(redrawLine(0, checkPoint++));
}
// update scroll marker
buffer.scrollMarker = checkPoint;
buffer.update[0] = false;
return terminal;
}
/**
* Redraw a complete terminal with updates on all visible lines.
* @param terminal the root terminal tag to add changed lines to
* @return the final terminal tag
*/
private Element redrawFullTerminal(Element terminal) {
// cycle through buffer and create terminal update ...
for (int l = 0; l < buffer.height; l++) {
if (!buffer.update[0] && !buffer.update[l + 1]) continue;
buffer.update[l + 1] = false;
terminal.addContent(redrawLine(l, buffer.windowBase));
}
buffer.update[0] = false;
return terminal;
}
/**
* Redraw a sinle line by looking at chunks and formatting them.
* @param l the current line
* @param base the "window"-base within the buffer
* @return an element with the formatted line
*/
private Element redrawLine(int l, int base) {
Element line = new Element("line");
line.setAttribute("row", "" + l);
// determine the maximum of characters we can print in one go
for (int c = 0; c < buffer.width; c++) {
int addr = 0;
int currAttr = buffer.charAttributes[base + l][c];
while ((c + addr < buffer.width) &&
((buffer.charArray[base + l][c + addr] < ' ') ||
(buffer.charAttributes[base + l][c + addr] == currAttr))) {
if (buffer.charArray[base + l][c + addr] < ' ') {
buffer.charArray[base + l][c + addr] = ' ';
buffer.charAttributes[base + l][c + addr] = 0;
continue;
}
addr++;
}
if (addr > 0) {
String tmp = new String(buffer.charArray[base + l], c, addr);
// create new text node and make sure we insert (160)
Text text = new Text(tmp.replace(' ', (char) 160));
Element chunk = null;
if ((currAttr & 0xfff) != 0) {
if ((currAttr & VDUBuffer.BOLD) != 0)
chunk = addChunk(new Element("B"), chunk, text);
if ((currAttr & VDUBuffer.UNDERLINE) != 0)
chunk = addChunk(new Element("U"), chunk, text);
if ((currAttr & VDUBuffer.INVERT) != 0)
chunk = addChunk(new Element("I"), chunk, text);
if ((currAttr & buffer.COLOR_FG) != 0) {
String fg = color[((currAttr & buffer.COLOR_FG) >> 4) - 1];
Element font = new Element("FONT").setAttribute("COLOR", fg);
chunk = addChunk(font, chunk, text);
}
/*
if ((currAttr & buffer.COLOR_BG) != 0) {
Color bg = color[((currAttr & buffer.COLOR_BG) >> 8) - 1];
}
*/
}
if (chunk == null) {
line.addContent(text);
} else {
line.addContent(chunk);
}
}
c += addr - 1;
}
return line;
}
/**
* Helper method to wrap a chunk or piece of text in another element.
* @param el the element to put the text or chunk into
* @param chunk a chunk of elements
* @param text a text element
* @return a new chunk made up from the element
*/
private Element addChunk(Element el, Element chunk, Text text) {
if (chunk == null)
return el.addContent(text);
else
return el.addContent(chunk);
}
/**
* Set the VDUBuffer that contains the terminal screen and back-buffer
* @param buffer the terminal buffer
*/
public void setVDUBuffer(VDUBuffer buffer) {
this.buffer = buffer;
if (simpleMode) {
this.buffer.setCursorPosition(0, 23);
}
this.buffer.setDisplay(this);
this.buffer.update[0] = true;
}
/**
* Get the current buffer.
* @return the VDUBuffer
*/
public VDUBuffer getVDUBuffer() {
return buffer;
}
}
jta_2.6+dfsg.orig/de/mud/flash/FlashTerminalServer.java 0000644 0001750 0001750 00000014442 10610772601 021625 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.flash;
import de.mud.telnet.TelnetProtocolHandler;
import de.mud.terminal.vt320;
import java.awt.Dimension;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.Socket;
import java.net.ServerSocket;
/**
* Flash Terminal Server implementation
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: FlashTerminalServer.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class FlashTerminalServer implements Runnable {
private final static int debug = 0;
/**
* Read all parameters from the applet configuration and
* do initializations for the plugins and the applet.
*/
public static void main(String args[]) {
System.out.println("FlashTerminalServer (c) 2002 Matthias L. Jugel, Marcus Mei�ner");
if(args.length < 2) {
System.err.println("usage: FlashTerminalServer host port");
System.exit(0);
}
if (debug > 0)
System.err.println("FlashTerminalServer: main(" + args[0] + ", "+args[1] + ")");
try {
ServerSocket serverSocket = new ServerSocket(8080);
// create a new
while(true) {
System.out.println("FlashTerminalServer: waiting for connection ...");
Socket flashClientSocket = serverSocket.accept();
System.out.println("FlashTerminalServer: Connect to: "+flashClientSocket);
new FlashTerminalServer(args[0], args[1], flashClientSocket);
}
} catch (IOException e) {
System.err.println("FlashTerminalServer: error opening server socket: "+e);
}
}
/** hold the socket */
private Socket socket;
private InputStream is;
private OutputStream os;
private boolean running;
/** the terminal */
private vt320 emulation;
private FlashTerminal terminal;
/** the telnet protocol handler */
private TelnetProtocolHandler telnet;
private boolean localecho = true;
public FlashTerminalServer(String host, String port, Socket flashSocket) {
// we now create a new terminal that is used for the system
// if you want to configure it please refer to the api docs
emulation = new vt320() {
/** before sending data transform it using telnet (which is sending it) */
public void write(byte[] b) {
try {
if (localecho) {
emulation.putString(new String(b) + "\r");
}
telnet.transpose(b);
} catch (IOException e) {
System.err.println("FlashTerminalServer: error sending data: " + e);
}
}
};
// then we create the actual telnet protocol handler that will negotiate
// incoming data and transpose outgoing (see above)
telnet = new TelnetProtocolHandler() {
/** get the current terminal type */
public String getTerminalType() {
return emulation.getTerminalID();
}
/** get the current window size */
public Dimension getWindowSize() {
return new Dimension(emulation.getColumns(), emulation.getRows());
}
/** notify about local echo */
public void setLocalEcho(boolean echo) {
localecho = true;
}
/** notify about EOR end of record */
public void notifyEndOfRecord() {
// only used when EOR needed, like for line mode
if(debug > 0)
System.err.println("FlashTerminalServer: EOR");
terminal.redraw();
}
/** write data to our back end */
public void write(byte[] b) throws IOException {
if(debug > 0)
System.err.println("FlashTerminalServer: writing " + Integer.toHexString(b[0]) + " " + new String(b));
os.write(b);
}
};
try {
terminal = new FlashTerminal() {
public void disconnect() {
running = false;
try {
socket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
};
terminal.setVDUBuffer(emulation);
// open new socket and get streams
socket = new Socket(host, Integer.parseInt(port));
is = socket.getInputStream();
os = socket.getOutputStream();
(new Thread(this)).start();
terminal.start(flashSocket);
} catch (IOException e) {
System.err.println("FlashTerminalServer: error connecting to remote host: "+e);
} catch (NumberFormatException e) {
System.err.println("FlashTerminalServer: "+port+" is not a correct number");
}
}
public void run() {
if (debug > 0) System.err.println("FlashTerminalServer: run()");
running = true;
byte[] b = new byte[4096];
int n = 0;
while (running && n >= 0) {
try {
n = telnet.negotiate(b); // we still have stuff buffered ...
if (n > 0)
emulation.putString(new String(b, 0, n));
while (true) {
n = is.read(b);
if(debug > 0)
System.err.println("FlashTerminalServer: got " + n + " bytes");
if (n <= 0)
continue;
telnet.inputfeed(b, n);
n = 0;
while (true) {
n = telnet.negotiate(b);
if (n > 0)
emulation.putString(new String(b, 0, n));
if (n == -1) // buffer empty.
break;
}
}
} catch (IOException e) {
e.printStackTrace();
break;
}
}
System.err.println("FlashTerminalServer: finished reading from remote host");
}
} jta_2.6+dfsg.orig/de/mud/jta/ 0000755 0001750 0001750 00000000000 10610772601 014516 5 ustar paul paul jta_2.6+dfsg.orig/de/mud/jta/PluginListener.java 0000644 0001750 0001750 00000002340 10610772601 020324 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
/**
* A tag interface for a plugin message listener.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: PluginListener.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface PluginListener {
}
jta_2.6+dfsg.orig/de/mud/jta/Common.java 0000644 0001750 0001750 00000013012 10610772601 016606 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
import de.mud.jta.event.ConfigurationRequest;
import javax.swing.JComponent;
import javax.swing.JMenu;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Properties;
import java.util.Vector;
/**
* The common part of the JTA - Telnet/SSH for the JAVA(tm) platform
* is handled here. Mainly this includes the loading of the plugins and
* the screen setup of the visual plugins.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: Common.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Meissner
*/
public class Common extends PluginLoader {
public final static String DEFAULT_PATH = "de.mud.jta.plugin";
public Common(Properties config) {
// configure the plugin path
super(getPluginPath(config.getProperty("pluginPath")));
System.out.println("** JTA - Telnet/SSH for the JAVA(tm) platform");
System.out.println("** Version 2.6 for Java 2+");
System.out.println("** Copyright (c) 1996-2005 Matthias L. Jugel, "
+ "Marcus Meissner");
try {
Version build =
(Version) Class.forName("de.mud.jta.Build").newInstance();
System.out.println("** Build: " + build.getDate());
} catch (Exception e) {
System.out.println("** Build: patched or selfmade, no date");
System.err.println(e);
}
Vector names = split(config.getProperty("plugins"), ',');
if (names == null) {
System.err.println("jta: no plugins found! aborting ...");
return;
}
Enumeration e = names.elements();
while (e.hasMoreElements()) {
String name = (String) e.nextElement();
String id = null;
int idx;
if ((idx = name.indexOf("(")) > 1) {
if (name.indexOf(")", idx) > idx)
id = name.substring(idx + 1, name.indexOf(")", idx));
else
System.err.println("jta: missing ')' for plugin '" + name + "'");
name = name.substring(0, idx);
}
System.out.println("jta: loading plugin '" + name + "'"
+ (id != null && id.length() > 0 ?
", ID: '" + id + "'" : ""));
Plugin plugin = addPlugin(name, id);
if (plugin == null) {
System.err.println("jta: ignoring plugin '" + name + "'"
+ (id != null && id.length() > 0 ?
", ID: '" + id + "'" : ""));
continue;
}
}
broadcast(new ConfigurationRequest(new PluginConfig(config)));
}
/**
* Get the list of visual components currently registered.
* @return a map of components
*/
public Map getComponents() {
Map plugins = getPlugins();
Iterator pluginIt = plugins.keySet().iterator();
Map components = new HashMap();
while (pluginIt.hasNext()) {
String name = (String) pluginIt.next();
Plugin plugin = (Plugin) plugins.get(name);
if (plugin instanceof VisualPlugin) {
JComponent c = ((VisualPlugin) plugin).getPluginVisual();
if (c != null) {
String id = plugin.getId();
components.put(name + (id != null ? "(" + id + ")" : ""), c);
}
}
}
return components;
}
public Map getMenus() {
Map plugins = getPlugins();
Iterator pluginIt = plugins.keySet().iterator();
Map menus = new HashMap();
while (pluginIt.hasNext()) {
String name = (String) pluginIt.next();
Plugin plugin = (Plugin) plugins.get(name);
if (plugin instanceof VisualPlugin) {
JMenu menu = ((VisualPlugin) plugin).getPluginMenu();
if (menu != null) {
String id = plugin.getId();
menus.put(name + (id != null ? "(" + id + ")" : ""), menu);
}
}
}
return menus;
}
/**
* Convert the plugin path from a separated string list to a Vector.
* @param path the string path
* @return a vector containing the path
*/
private static Vector getPluginPath(String path) {
if (path == null)
path = DEFAULT_PATH;
return split(path, ':');
}
/**
* Split up comma separated lists of strings. This is quite strict, no
* whitespace characters are allowed.
* @param s the string to be split up
* @return an array of strings
*/
public static Vector split(String s, char separator) {
if (s == null) return null;
Vector v = new Vector();
int old = -1, idx = s.indexOf(separator);
while (idx >= 0) {
v.addElement(s.substring(old + 1, idx));
old = idx;
idx = s.indexOf(separator, old + 1);
}
v.addElement(s.substring(old + 1));
return v;
}
}
jta_2.6+dfsg.orig/de/mud/jta/Applet.java 0000644 0001750 0001750 00000046157 10610772601 016623 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
import de.mud.jta.event.AppletRequest;
import de.mud.jta.event.FocusStatusListener;
import de.mud.jta.event.OnlineStatusListener;
import de.mud.jta.event.ReturnFocusRequest;
import de.mud.jta.event.SocketRequest;
import de.mud.jta.event.SoundListener;
import javax.swing.JApplet;
import javax.swing.JFrame;
import javax.swing.RootPaneContainer;
import java.awt.BorderLayout;
import java.awt.Button;
import java.awt.Component;
import java.awt.Menu;
import java.awt.MenuBar;
import java.awt.MenuItem;
import java.awt.MenuShortcut;
import java.awt.PrintJob;
import java.awt.datatransfer.Clipboard;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.net.URL;
import java.util.Enumeration;
import java.util.Iterator;
import java.util.Map;
import java.util.Properties;
import java.util.Vector;
/**
* JTA - Telnet/SSH for the JAVA(tm) platform: Applet
* This is the implementation of whole set of applications. It's modular
* structure allows to configure the software to act either as a sophisticated
* terminal emulation and/or, adding the network backend, as telnet
* implementation. Additional modules provide features like scripting or an
* improved graphical user interface.
* This software is written entirely in Javatm.
* This is the Applet implementation for the software. It initializes
* the system and adds all needed components, such as the telnet backend and
* the terminal front end.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: Applet.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Meissner
*/
public class Applet extends JApplet {
private final static int debug = 0;
private String frameTitle = null;
private RootPaneContainer appletFrame;
/** holds the defaults */
private Properties options = new Properties();
/** hold the common part of the jta */
private Common pluginLoader;
/** hold the host and port for our connection */
private String host, port;
/** disconnect on leave, this is to force applets to break the connection */
private boolean disconnect = true;
/** connect on startup, this is to force applets to connect on detach */
private boolean connect = false;
/** close the window (if it exists) after the connection is lost */
private boolean disconnectCloseWindow = true;
private Plugin focussedPlugin;
private Clipboard clipboard;
private boolean online = false;
/**
* Read all parameters from the applet configuration and
* do initializations for the plugins and the applet.
*/
public void init() {
if (debug > 0) System.err.println("Applet: init()");
if (pluginLoader == null) {
try {
options.load(Applet.class
.getResourceAsStream("/de/mud/jta/default.conf"));
} catch (Exception e) {
try {
URL url = new URL(getCodeBase() + "default.conf");
options.load(url.openStream());
} catch (Exception e1) {
System.err.println("jta: cannot load default.conf");
System.err.println("jta: try extracting it from the jar file");
System.err.println("jta: expected file here: "
+ getCodeBase() + "default.conf");
}
}
String value;
// try to load the local configuration and merge it with the defaults
if ((value = getParameter("config")) != null) {
Properties appletParams = new Properties();
URL url = null;
try {
url = new URL(value);
} catch (Exception e) {
try {
url = new URL(getCodeBase() + value);
} catch (Exception ce) {
System.err.println("jta: could not find config file: " + ce);
}
}
if (url != null) {
try {
appletParams.load(Applet.class.getResourceAsStream("/de/mud/jta/" + value));
Enumeration ape = appletParams.keys();
while (ape.hasMoreElements()) {
String key = (String) ape.nextElement();
options.put(key, appletParams.getProperty(key));
}
} catch (Exception e) {
try {
appletParams.load(url.openStream());
Enumeration ape = appletParams.keys();
while (ape.hasMoreElements()) {
String key = (String) ape.nextElement();
options.put(key, appletParams.getProperty(key));
}
} catch (Exception e2) {
System.err.println("jta: could not load config file: " + e2);
}
}
}
}
// see if there are parameters in the html to override properties
parameterOverride(options);
// configure the application and load all plugins
pluginLoader = new Common(options);
// set the host to our code base, no other hosts are allowed anyway
host = options.getProperty("Socket.host");
if (host == null)
host = getCodeBase().getHost();
port = options.getProperty("Socket.port");
if (port == null)
port = "23";
if ((new Boolean(options.getProperty("Applet.connect"))
.booleanValue()))
connect = true;
if (!(new Boolean(options.getProperty("Applet.disconnect"))
.booleanValue()))
disconnect = false;
if (!(new Boolean(options.getProperty("Applet.disconnect.closeWindow"))
.booleanValue()))
disconnectCloseWindow = false;
frameTitle = options.getProperty("Applet.detach.title");
if ((new Boolean(options.getProperty("Applet.detach"))).booleanValue()) {
if (frameTitle == null) {
appletFrame = (RootPaneContainer)new JFrame("jta: " + host + (port.equals("23")?"":" " + port));
} else {
appletFrame = (RootPaneContainer)new JFrame(frameTitle);
}
} else {
appletFrame = (RootPaneContainer)this;
}
appletFrame.getContentPane().setLayout(new BorderLayout());
Map componentList = pluginLoader.getComponents();
Iterator names = componentList.keySet().iterator();
while (names.hasNext()) {
String name = (String) names.next();
Component c = (Component) componentList.get(name);
if ((value = options.getProperty("layout." + name)) != null) {
appletFrame.getContentPane().add(value, c);
} else {
System.err.println("jta: no layout property set for '" + name + "'");
System.err.println("jta: ignoring '" + name + "'");
}
}
pluginLoader.registerPluginListener(new SoundListener() {
public void playSound(URL audioClip) {
Applet.this.getAudioClip(audioClip).play();
}
});
pluginLoader.broadcast(new AppletRequest(this));
if (appletFrame != this) {
final String startText = options.getProperty("Applet.detach.startText");
final String stopText = options.getProperty("Applet.detach.stopText");
final Button close = new Button();
// this works for Netscape only!
Vector privileges =
Common.split(options.getProperty("Applet.Netscape.privilege"), ',');
Class privilegeManager = null;
Method enable = null;
try {
privilegeManager =
Class.forName("netscape.security.PrivilegeManager");
enable = privilegeManager
.getMethod("enablePrivilege", new Class[]{String.class});
} catch (Exception e) {
System.err.println("Applet: This is not Netscape ...");
}
if (privilegeManager != null && enable != null && privileges != null)
for (int i = 0; i < privileges.size(); i++)
try {
enable.invoke(privilegeManager,
new Object[]{privileges.elementAt(i)});
System.out.println("Applet: access for '" +
privileges.elementAt(i) + "' allowed");
} catch (Exception e) {
System.err.println("Applet: access for '" +
privileges.elementAt(i) + "' denied");
}
// set up the clipboard
try {
clipboard = appletFrame.getContentPane().getToolkit().getSystemClipboard();
System.err.println("Applet: acquired system clipboard: " + clipboard);
} catch (Exception e) {
System.err.println("Applet: system clipboard access denied: " +
((e instanceof InvocationTargetException) ?
((InvocationTargetException) e).getTargetException() : e));
// e.printStackTrace();
} finally {
if (clipboard == null) {
System.err.println("Applet: copy & paste only within the JTA");
clipboard = new Clipboard("de.mud.jta.Main");
}
}
if ((new Boolean(options.getProperty("Applet.detach.immediately"))
.booleanValue())) {
if ((new Boolean(options.getProperty("Applet.detach.fullscreen"))
.booleanValue()))
((JFrame) appletFrame)
.setSize(appletFrame.getContentPane().getToolkit().getScreenSize());
else
((JFrame) appletFrame).pack();
((JFrame) appletFrame).show();
pluginLoader.broadcast(new SocketRequest(host, Integer.parseInt(port)));
pluginLoader.broadcast(new ReturnFocusRequest());
close.setLabel(startText != null ? stopText : "Disconnect");
} else
close.setLabel(startText != null ? startText : "Connect");
close.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
if (((JFrame) appletFrame).isVisible()) {
pluginLoader.broadcast(new SocketRequest());
((JFrame) appletFrame).setVisible(false);
close.setLabel(startText != null ? startText : "Connect");
} else {
if (frameTitle == null)
((JFrame) appletFrame)
.setTitle("jta: " + host + (port.equals("23")?"":" " + port));
if ((new Boolean(options.getProperty("Applet.detach.fullscreen"))
.booleanValue()))
((JFrame) appletFrame)
.setSize(appletFrame.getContentPane().getToolkit().getScreenSize());
else
((JFrame) appletFrame).pack();
((JFrame) appletFrame).show();
if (port == null || port.length() <= 0)
port = "23";
getAppletContext().showStatus("Trying " + host + " " + port + " ...");
pluginLoader.broadcast(new SocketRequest(host,
Integer.parseInt(port)));
pluginLoader.broadcast(new ReturnFocusRequest());
close.setLabel(stopText != null ? stopText : "Disconnect");
}
}
});
getContentPane().setLayout(new BorderLayout());
getContentPane().add("Center", close);
// add a menu bar
MenuBar mb = new MenuBar();
Menu file = new Menu("File");
file.setShortcut(new MenuShortcut(KeyEvent.VK_F, true));
MenuItem tmp;
file.add(tmp = new MenuItem("Connect"));
tmp.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
pluginLoader.broadcast(new SocketRequest(host,
Integer.parseInt(port)));
}
});
file.add(tmp = new MenuItem("Disconnect"));
tmp.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
pluginLoader.broadcast(new SocketRequest());
}
});
file.add(new MenuItem("-"));
file.add(tmp = new MenuItem("Print"));
tmp.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
if (pluginLoader.getComponents().get("Terminal") != null) {
PrintJob printJob =
appletFrame.getContentPane().getToolkit()
.getPrintJob((JFrame) appletFrame, "JTA Terminal", null);
((Component) pluginLoader.getComponents().get("Terminal"))
.print(printJob.getGraphics());
printJob.end();
}
}
});
file.add(new MenuItem("-"));
file.add(tmp = new MenuItem("Exit"));
tmp.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
((JFrame) appletFrame).setVisible(false);
pluginLoader.broadcast(new SocketRequest());
close.setLabel(startText != null ? startText : "Connect");
}
});
mb.add(file);
Menu edit = new Menu("Edit");
edit.setShortcut(new MenuShortcut(KeyEvent.VK_E, true));
edit.add(tmp = new MenuItem("Copy"));
tmp.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
if (debug > 2)
System.err.println("Applet: copy: " + focussedPlugin);
if (focussedPlugin instanceof VisualTransferPlugin)
((VisualTransferPlugin) focussedPlugin).copy(clipboard);
}
});
edit.add(tmp = new MenuItem("Paste"));
tmp.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
if (debug > 2)
System.err.println("Applet: paste: " + focussedPlugin);
if (focussedPlugin instanceof VisualTransferPlugin)
((VisualTransferPlugin) focussedPlugin).paste(clipboard);
}
});
mb.add(edit);
Map menuList = pluginLoader.getMenus();
names = menuList.keySet().iterator();
while (names.hasNext()) {
String name = (String) names.next();
Object o = menuList.get(name);
if (o instanceof Menu) mb.add((Menu) o);
}
Menu help = new Menu("Help");
help.setShortcut(new MenuShortcut(KeyEvent.VK_HELP, true));
help.add(tmp = new MenuItem("General"));
tmp.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
Help.show(appletFrame.getContentPane(), options.getProperty("Help.url"));
}
});
mb.setHelpMenu(help);
// only add the menubar if the property is true
if ((new Boolean(options.getProperty("Applet.detach.menuBar"))
.booleanValue()))
((JFrame) appletFrame).setMenuBar(mb);
// add window closing event handler
try {
((JFrame) appletFrame).addWindowListener(new WindowAdapter() {
public void windowClosing(WindowEvent evt) {
pluginLoader.broadcast(new SocketRequest());
((JFrame) appletFrame).setVisible(false);
close.setLabel(startText != null ? startText : "Connect");
}
});
} catch (Exception e) {
System.err.println("Applet: could not set up Window event listener");
System.err.println("Applet: you will not be able to close it");
}
pluginLoader.registerPluginListener(new OnlineStatusListener() {
public void online() {
if (debug > 0) System.err.println("Terminal: online");
online = true;
if (((JFrame) appletFrame).isVisible() == false)
((JFrame) appletFrame).setVisible(true);
}
public void offline() {
if (debug > 0) System.err.println("Terminal: offline");
online = false;
if (disconnectCloseWindow) {
((JFrame) appletFrame).setVisible(false);
close.setLabel(startText != null ? startText : "Connect");
}
}
});
// register a focus status listener, so we know when a plugin got focus
pluginLoader.registerPluginListener(new FocusStatusListener() {
public void pluginGainedFocus(Plugin plugin) {
if (Applet.debug > 0)
System.err.println("Applet: " + plugin + " got focus");
focussedPlugin = plugin;
}
public void pluginLostFocus(Plugin plugin) {
// we ignore the lost focus
if (Applet.debug > 0)
System.err.println("Applet: " + plugin + " lost focus");
}
});
} else
// if we have no external frame use this online status listener
pluginLoader.registerPluginListener(new OnlineStatusListener() {
public void online() {
if (debug > 0) System.err.println("Terminal: online");
online = true;
}
public void offline() {
if (debug > 0) System.err.println("Terminal: offline");
online = false;
}
});
}
}
/**
* Start the applet. Connect to the remote host.
*/
public void start() {
if (!online && (appletFrame == this || connect)) {
if (debug > 0) System.err.println("start(" + host + ", " + port + ")");
getAppletContext().showStatus("Trying " + host + " " + port + " ...");
pluginLoader.broadcast(new SocketRequest(host, Integer.parseInt(port)));
pluginLoader.broadcast(new ReturnFocusRequest());
}
}
/**
* Stop the applet and disconnect.
*/
public void stop() {
if (online && disconnect) {
if (debug > 0) System.err.println("stop()");
pluginLoader.broadcast(new SocketRequest());
}
}
/**
* Override any properties that are found in the configuration files
* with possible values found as applet parameters.
* @param options the loaded configuration file properties
*/
private void parameterOverride(Properties options) {
Enumeration e = options.keys();
while (e.hasMoreElements()) {
String key = (String) e.nextElement(), value = getParameter(key);
if (value != null) {
System.out.println("Applet: overriding value of " + key + " with " + value);
// options.setProperty(key, value);
options.put(key, value);
}
}
}
}
jta_2.6+dfsg.orig/de/mud/jta/FilterPlugin.java 0000644 0001750 0001750 00000004107 10610772601 017767 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
import java.io.IOException;
/**
* The filter plugin is the base interface for plugins that want to intercept
* the communication between front end and back end plugins. Filters and
* protocol handlers are a good example.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: FilterPlugin.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface FilterPlugin {
/**
* Set the source plugin where we get our data from and where the data
* sink (write) is. The actual data handling should be done in the
* read() and write() methods.
* @param source the data source
*/
public void setFilterSource(FilterPlugin source)
throws IllegalArgumentException;
public FilterPlugin getFilterSource();
/**
* Read a block of data from the back end.
* @param b the buffer to read the data into
* @return the amount of bytes actually read
*/
public int read(byte[] b)
throws IOException;
/**
* Write a block of data to the back end.
* @param b the buffer to be sent
*/
public void write(byte[] b)
throws IOException;
}
jta_2.6+dfsg.orig/de/mud/jta/Build.java 0000644 0001750 0001750 00000002206 10610772601 016420 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
/**
* The build class shows the date and time if the release
*/
public class Build implements Version {
public String getDate() {
return "20051219-0941";
}
}
jta_2.6+dfsg.orig/de/mud/jta/default.conf 0000644 0001750 0001750 00000010357 10610772601 017017 0 ustar paul paul # This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
#
# (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
#
# Please visit http://javatelnet.org/ for updates and contact.
#
# --LICENSE NOTICE--
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
# --LICENSE NOTICE--
#
# -- IMPORTANT NOTICE --
# Copy this file when creating your own configuration and name it different.
# default.conf is used by the software for initial setup. Your own config
# may not need all the fields found in this file but only those you want
# to change.
# -- IMPORTANT NOTICE --
# =======================================================================
# common program defaults
# =======================================================================
plugins = Status,Socket,Telnet,Terminal
pluginPath = de.mud.jta.plugin
layout = BorderLayout
layout.Terminal = Center
layout.Status = South
layout.MudConnector = North
# help url/filename
Help.url = /index.html
# =======================================================================
# Applet defaults
# =======================================================================
Applet.detach = false
Applet.detach.fullscreen = false
Applet.detach.immediately = false
Applet.detach.menuBar = true
Applet.detach.startText = Connect
Applet.detach.stopText = Disonnect
Applet.disconnect = true
Applet.disconnect.closeWindow = true
# to make Netscape behave good we would like to have some privileges
Applet.Netscape.privilege = UniversalConnect,UniversalPrintJobAccess,UniversalSystemClipboardAccess
# =======================================================================
# Socket defaults
# =======================================================================
# This is set to the webserver by default.
Socket.host =
Socket.port = 23
# for SSH use the port below
#Socket.port = 22
# =======================================================================
# Timeout settings
# =======================================================================
Timeout.seconds = 60
Timeout.command = exit\n
# =======================================================================
# Terminal defaults
# =======================================================================
Terminal.foreground = #ffffff
Terminal.background = #000000
Terminal.cursor.foreground = #000000
Terminal.cursor.background = #ffffff
Terminal.print.color = false
Terminal.border = 2
Terminal.borderRaised = false
# if you use your own file use a fully qualified URL!
Terminal.colorSet = /de/mud/terminal/colorSet.conf
Terminal.scrollBar = West
# now the real terminal configuration
Terminal.id = vt320
Terminal.buffer = 100
Terminal.size = [80,24]
Terminal.resize = screen
Terminal.font = Monospaced
Terminal.fontStyle = plain
Terminal.fontSize = 11
# if you use your own file use a fully qualified URL!
Terminal.keyCodes = /de/mud/terminal/keyCodes.conf
Terminal.VMS = false
Terminal.IBM = false
# the setting below should be correct, but it does not work
#Terminal.encoding = ISO8859_1
# the setting used it probably incorrect but forces the default behaviour
Terminal.encoding = latin1
#Terminal.beep = http://www.mud.de/se/jta/BOUNCE.WAV
# =======================================================================
# MudConnect defaults
# =======================================================================
MudConnector.listURL = http://www.mudconnector.com/java/Telnet/javalist.db
# =======================================================================
# MudConnect defaults
# =======================================================================
Capture.url = Configure this URL!
jta_2.6+dfsg.orig/de/mud/jta/Main.java 0000644 0001750 0001750 00000030425 10610772601 016251 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
import de.mud.jta.event.FocusStatusListener;
import de.mud.jta.event.OnlineStatusListener;
import de.mud.jta.event.ReturnFocusRequest;
import de.mud.jta.event.SocketRequest;
import javax.swing.JComponent;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.JOptionPane;
import javax.swing.KeyStroke;
import java.awt.PrintJob;
import java.awt.datatransfer.Clipboard;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.io.FileInputStream;
import java.io.IOException;
import java.net.URL;
import java.util.Iterator;
import java.util.Map;
import java.util.Properties;
/**
* JTA - Telnet/SSH for the JAVA(tm) platform
* This is the implementation of whole set of applications. It's modular
* structure allows to configure the software to act either as a sophisticated
* terminal emulation and/or, adding the network backend, as telnet
* implementation. Additional modules provide features like scripting or an
* improved graphical user interface.
* This software is written entirely in Javatm.
* This is the main program for the command line telnet. It initializes the
* system and adds all needed components, such as the telnet backend and
* the terminal front end. In contrast to applet functionality it parses
* command line arguments used for configuring the software. Additionally
* this application is not restricted in the sense of Javatmp
* security.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: Main.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Meissner
*/
public class Main {
private final static int debug = 0;
private final static boolean personalJava = false;
/** holds the last focussed plugin */
private static Plugin focussedPlugin;
/** holds the system clipboard or our own */
private static Clipboard clipboard;
private static String host, port;
public static void main(String args[]) {
final Properties options = new Properties();
try {
options.load(Main.class.getResourceAsStream("/de/mud/jta/default.conf"));
} catch (IOException e) {
System.err.println("jta: cannot load default.conf");
}
String error = parseOptions(options, args);
if (error != null) {
System.err.println(error);
System.err.println("usage: de.mud.jta.Main [-plugins pluginlist] "
+ "[-addplugin plugin] "
+ "[-config url_or_file] "
+ "[-term id] [host [port]]");
System.exit(0);
}
String cfg = options.getProperty("Main.config");
if (cfg != null)
try {
options.load(new URL(cfg).openStream());
} catch (IOException e) {
try {
options.load(new FileInputStream(cfg));
} catch (Exception fe) {
System.err.println("jta: cannot load " + cfg);
}
}
host = options.getProperty("Socket.host");
port = options.getProperty("Socket.port");
final JFrame frame = new JFrame("jta: " + host + (port.equals("23")?"":" " + port));
// set up the clipboard
try {
clipboard = frame.getToolkit().getSystemClipboard();
} catch (Exception e) {
System.err.println("jta: system clipboard access denied");
System.err.println("jta: copy & paste only within the JTA");
clipboard = new Clipboard("de.mud.jta.Main");
}
// configure the application and load all plugins
final Common setup = new Common(options);
if (port == null || port.length() == 0) {
if (setup.getPlugins().containsKey("SSH")) {
port = "22";
} else {
port = "23";
}
}
setup.registerPluginListener(new OnlineStatusListener() {
public void online() {
frame.setTitle("jta: " + host + (port.equals("23")?"":" " + port));
}
public void offline() {
frame.setTitle("jta: offline");
}
});
// register a focus status listener, so we know when a plugin got focus
setup.registerPluginListener(new FocusStatusListener() {
public void pluginGainedFocus(Plugin plugin) {
if (Main.debug > 0)
System.err.println("Main: " + plugin + " got focus");
focussedPlugin = plugin;
}
public void pluginLostFocus(Plugin plugin) {
// we ignore the lost focus
if (Main.debug > 0)
System.err.println("Main: " + plugin + " lost focus");
}
});
Map componentList = setup.getComponents();
Iterator names = componentList.keySet().iterator();
while (names.hasNext()) {
String name = (String) names.next();
JComponent c = (JComponent) componentList.get(name);
if (options.getProperty("layout." + name) == null) {
System.err.println("jta: no layout property set for '" + name + "'");
frame.add("South", c);
} else
frame.getContentPane().add(options.getProperty("layout." + name), c);
}
if (!personalJava) {
frame.addWindowListener(new WindowAdapter() {
public void windowClosing(WindowEvent evt) {
setup.broadcast(new SocketRequest());
frame.setVisible(false);
frame.dispose();
System.exit(0);
}
});
// add a menu bar
JMenuBar mb = new JMenuBar();
JMenu file = new JMenu("File");
file.setMnemonic(KeyEvent.VK_F);
JMenuItem tmp;
file.add(tmp = new JMenuItem("Connect"));
tmp.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_C, KeyEvent.SHIFT_MASK | KeyEvent.CTRL_MASK));
tmp.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
String destination =
JOptionPane.showInputDialog(frame,
new JLabel("Enter your destination host (host[:port])"),
"Connect", JOptionPane.QUESTION_MESSAGE
);
if (destination != null) {
int sep = 0;
if ((sep = destination.indexOf(' ')) > 0 || (sep = destination.indexOf(':')) > 0) {
host = destination.substring(0, sep);
port = destination.substring(sep + 1);
} else {
host = destination;
}
setup.broadcast(new SocketRequest());
setup.broadcast(new SocketRequest(host, Integer.parseInt(port)));
}
}
});
file.add(tmp = new JMenuItem("Disconnect"));
tmp.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
setup.broadcast(new SocketRequest());
}
});
file.addSeparator();
if (setup.getComponents().get("Terminal") != null) {
file.add(tmp = new JMenuItem("Print"));
tmp.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_P, KeyEvent.CTRL_MASK));
tmp.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
PrintJob printJob =
frame.getToolkit().getPrintJob(frame, "JTA Terminal", null);
// return if the user clicked cancel
if (printJob == null) return;
((JComponent) setup.getComponents().get("Terminal"))
.print(printJob.getGraphics());
printJob.end();
}
});
file.addSeparator();
}
file.add(tmp = new JMenuItem("Exit"));
tmp.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
frame.dispose();
System.exit(0);
}
});
mb.add(file);
JMenu edit = new JMenu("Edit");
edit.add(tmp = new JMenuItem("Copy"));
tmp.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_C, KeyEvent.CTRL_MASK));
tmp.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
if (focussedPlugin instanceof VisualTransferPlugin)
((VisualTransferPlugin) focussedPlugin).copy(clipboard);
}
});
edit.add(tmp = new JMenuItem("Paste"));
tmp.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_V, KeyEvent.CTRL_MASK));
tmp.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
if (focussedPlugin instanceof VisualTransferPlugin)
((VisualTransferPlugin) focussedPlugin).paste(clipboard);
}
});
mb.add(edit);
Map menuList = setup.getMenus();
names = menuList.keySet().iterator();
while (names.hasNext()) {
String name = (String) names.next();
mb.add((JMenu) menuList.get(name));
}
JMenu help = new JMenu("Help");
help.setMnemonic(KeyEvent.VK_HELP);
help.add(tmp = new JMenuItem("General"));
tmp.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
Help.show(frame, options.getProperty("Help.url"));
}
});
mb.add(help);
frame.setJMenuBar(mb);
} // !personalJava
frame.pack();
if ((new Boolean(options.getProperty("Applet.detach.fullscreen"))
.booleanValue()))
frame.setSize(frame.getToolkit().getScreenSize());
else
frame.pack();
frame.setVisible(true);
if(debug > 0)
System.err.println("host: '"+host+"', "+host.length());
if (host != null && host.length() > 0) {
setup.broadcast(new SocketRequest(host, Integer.parseInt(port)));
}
/* make sure the focus goes somewhere to start off with */
setup.broadcast(new ReturnFocusRequest());
}
/**
* Parse the command line argumens and override any standard options
* with the new values if applicable.
*
* This method did not work with jdk 1.1.x as the setProperty()
* method is not available. So it uses now the put() method from
* Hashtable instead.
*
* @param options the original options
* @param args the command line parameters
* @return a possible error message if problems occur
*/
private static String parseOptions(Properties options, String args[]) {
boolean host = false, port = false;
for (int n = 0; n < args.length; n++) {
if (args[n].equals("-config"))
if (!args[n + 1].startsWith("-"))
options.put("Main.config", args[++n]);
else
return "missing parameter for -config";
else if (args[n].equals("-plugins"))
if (!args[n + 1].startsWith("-"))
options.put("plugins", args[++n]);
else
return "missing parameter for -plugins";
else if (args[n].equals("-addplugin"))
if (!args[n + 1].startsWith("-"))
options.put("plugins", args[++n] + "," + options.get("plugins"));
else
return "missing parameter for -addplugin";
else if (args[n].equals("-term"))
if (!args[n + 1].startsWith("-"))
options.put("Terminal.id", args[++n]);
else
return "missing parameter for -term";
else if (!host) {
options.put("Socket.host", args[n]);
host = true;
} else if (host && !port) {
options.put("Socket.port", args[n]);
port = true;
} else
return "unknown parameter '" + args[n] + "'";
}
return null;
}
}
jta_2.6+dfsg.orig/de/mud/jta/ssh.conf 0000644 0001750 0001750 00000002631 10610772601 016164 0 ustar paul paul # This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
#
# (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
#
# Please visit http://javatelnet.org/ for updates and contact.
#
# --LICENSE NOTICE--
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
# --LICENSE NOTICE--
#
# This is an example file how to configure the applet. It may contain
# any property defined in de/mud/jta/default.conf or by a plugin.
#
# common definitions
plugins = Status,Socket,SSH,Terminal
layout.Status = South
layout.Terminal = Center
Terminal.resize = screen
Applet.disconnect = false
# commented out so the login window pops up
#SSH.password =
Socket.port = 22
# Terminal configuration
Terminal.foreground = #ffffff
Terminal.background = #000000
Terminal.id = vt100
jta_2.6+dfsg.orig/de/mud/jta/SmallApplet.java 0000644 0001750 0001750 00000013102 10610772601 017574 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
import de.mud.telnet.TelnetProtocolHandler;
import de.mud.terminal.SwingTerminal;
import de.mud.terminal.vt320;
import de.mud.terminal.SwingTerminal;
import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.Graphics;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.Socket;
/**
* Small Telnet Applet implementation
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: SmallApplet.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class SmallApplet extends java.applet.Applet implements Runnable {
private final static int debug = 0;
/** hold the host and port for our connection */
private String host, port;
/** hold the socket */
private Socket socket;
private InputStream is;
private OutputStream os;
private Thread reader;
/** the terminal */
private vt320 emulation;
private SwingTerminal terminal;
/** the telnet protocol handler */
private TelnetProtocolHandler telnet;
private boolean localecho = false;
/**
* Read all parameters from the applet configuration and
* do initializations for the plugins and the applet.
*/
public void init() {
if (debug > 0) System.err.println("jta: init()");
host = getParameter("host");
port = getParameter("port");
// we now create a new terminal that is used for the system
// if you want to configure it please refer to the api docs
emulation = new vt320() {
/** before sending data transform it using telnet (which is sending it) */
public void write(byte[] b) {
try {
if (localecho)
emulation.putString(new String(b));
telnet.transpose(b);
} catch (IOException e) {
System.err.println("jta: error sending data: " + e);
}
}
};
terminal = new SwingTerminal(emulation);
// put terminal into the applet
setLayout(new BorderLayout());
add("Center", terminal);
// then we create the actual telnet protocol handler that will negotiate
// incoming data and transpose outgoing (see above)
telnet = new TelnetProtocolHandler() {
/** get the current terminal type */
public String getTerminalType() {
return emulation.getTerminalID();
}
/** get the current window size */
public Dimension getWindowSize() {
return new Dimension(emulation.getColumns(), emulation.getRows());
}
/** notify about local echo */
public void setLocalEcho(boolean echo) {
localecho = true;
}
/** notify about EOR end of record */
public void notifyEndOfRecord() {
// only used when EOR needed, like for line mode
}
/** write data to our back end */
public void write(byte[] b) throws IOException {
os.write(b);
}
};
}
boolean running = false;
/**
* Start the applet. Connect to the remote host.
*/
public void start() {
if (debug > 0)
System.err.println("jta: start()");
// disconnect if we are already connected
if (socket != null) stop();
try {
// open new socket and get streams
socket = new Socket(host, Integer.parseInt(port));
is = socket.getInputStream();
os = socket.getOutputStream();
reader = new Thread(this);
running = true;
reader.start();
} catch (Exception e) {
System.err.println("jta: error connecting: " + e);
stop();
}
}
/**
* Stop the applet and disconnect.
*/
public void stop() {
if (debug > 0)
System.err.println("jta: stop()");
// when applet stops, disconnect
if (socket != null) {
try {
socket.close();
} catch (Exception e) {
System.err.println("jta: could not cleanly disconnect: " + e);
}
socket = null;
try {
running = false;
} catch (Exception e) {
// ignore
}
reader = null;
}
}
/**
* Continuously read from remote host and display the data on screen.
*/
public void run() {
if (debug > 0)
System.err.println("jta: run()");
byte[] b = new byte[256];
int n = 0;
while (running && n >= 0)
try {
do {
n = telnet.negotiate(b);
if (debug > 0 && n > 0)
System.err.println("jta: \"" + (new String(b, 0, n)) + "\"");
if (n > 0) emulation.putString(new String(b, 0, n));
} while (running && n > 0);
n = is.read(b);
telnet.inputfeed(b, n);
} catch (IOException e) {
stop();
break;
}
}
public void update(Graphics g) {
paint(g);
}
}
jta_2.6+dfsg.orig/de/mud/jta/Help.java 0000644 0001750 0001750 00000006342 10610772601 016256 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
import javax.swing.JButton;
import javax.swing.JEditorPane;
import javax.swing.JFrame;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import java.awt.BorderLayout;
import java.awt.Component;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.io.BufferedReader;
import java.io.IOException;
import java.net.URL;
/**
* Help display for JTA.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: Help.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class Help {
public static JEditorPane helpText = new JEditorPane();
public static void show(Component parent, String url) {
BufferedReader reader = null;
System.err.println("Help: " + url);
try {
helpText.setPage(Help.class.getResource(url));
} catch (IOException e) {
try {
helpText.setPage(new URL(url));
}
catch (Exception ee)
{
System.err.println("unable to load help");
JOptionPane.showMessageDialog(parent, "JTA - Telnet/SSH for the JAVA(tm) platform\r\n(c) 1996-2005 Matthias L. Jugel, Marcus Meißner\r\n\r\n",
"jta", JOptionPane.INFORMATION_MESSAGE);
return;
}
}
helpText.setEditable(false);
JScrollPane scrollPane =
new JScrollPane(helpText,
JScrollPane.VERTICAL_SCROLLBAR_ALWAYS,
JScrollPane.HORIZONTAL_SCROLLBAR_AS_NEEDED);
scrollPane.setSize(800, 600);
final JFrame frame = new JFrame("HELP");
frame.getContentPane().setLayout(new BorderLayout());
frame.getContentPane().add(BorderLayout.CENTER, scrollPane);
JPanel panel = new JPanel();
JButton close = new JButton("Close Help");
panel.add(close);
close.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
frame.setVisible(false);
}
});
frame.addWindowListener(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
frame.setVisible(false);
}
});
frame.getContentPane().add(BorderLayout.SOUTH, close);
frame.setSize(800, 600);
frame.setVisible(true);
}
}
jta_2.6+dfsg.orig/de/mud/jta/VisualPlugin.java 0000644 0001750 0001750 00000003220 10610772601 020000 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
import javax.swing.*;
/**
* To show data on-screen a plugin may have a visible component. That component
* may either be a single awt component or a container with severel elements.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: VisualPlugin.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface VisualPlugin {
/**
* Get the visible components from the plugin.
* @return a component that represents the plugin
*/
public JComponent getPluginVisual();
/**
* Get the menu entry for this component.
* @return a menu that can be used to change the plugin state
*/
public JMenu getPluginMenu();
}
jta_2.6+dfsg.orig/de/mud/jta/VisualTransferPlugin.java 0000644 0001750 0001750 00000003114 10610772601 021507 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
import java.awt.datatransfer.Clipboard;
/**
* A visual plugin that also allows to copy and paste data.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: VisualTransferPlugin.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface VisualTransferPlugin extends VisualPlugin {
/**
* Copy currently selected text into the clipboard.
* @param clipboard the clipboard
*/
public void copy(Clipboard clipboard);
/**
* Paste text from clipboard to the plugin.
* @param clipboard the clipboard
*/
public void paste(Clipboard clipboard);
}
jta_2.6+dfsg.orig/de/mud/jta/Build.java.tmpl 0000644 0001750 0001750 00000002177 10610772601 017402 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
/**
* The build class shows the date and time if the release
*/
public class Build implements Version {
public String getDate() {
return "@date@";
}
}
jta_2.6+dfsg.orig/de/mud/jta/Version.java 0000644 0001750 0001750 00000002025 10610772601 017005 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
public interface Version {
public String getDate();
}
jta_2.6+dfsg.orig/de/mud/jta/PluginConfig.java 0000644 0001750 0001750 00000006164 10610772601 017754 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
import java.util.Properties;
/**
* Plugin configuration container. This class extends the Properties
* to allow specific duplications of plugins. To get the value of a
* property for a plugin simply call getProperty() with the plugin name,
* the unique id (which may be null) and the key you look for. A fallback
* value will be returned if it exists.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: PluginConfig.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class PluginConfig extends Properties {
public PluginConfig(Properties props) {
super(props);
}
/**
* Get property value for a certain plugin with the specified id.
* This method will return the default value if no value for the specified
* id exists.
* @param plugin the plugin to get the setup for
* @param id plugin id as specified in the config file
* @param key the property key to search for
* @return the property value or null
*/
public String getProperty(String plugin, String id, String key) {
if(id == null) id = ""; else id = "("+id+")";
String result = getProperty(plugin+id, key);
if(result == null)
result = getProperty(plugin, key);
return result;
}
/**
* Get the property value for a certain plugin.
* @param plugin the plugin to get setup for
* @param key the property key to search for
*/
public String getProperty(String plugin, String key) {
return getProperty(plugin+"."+key);
}
/**
* Set the property value for a certain plugin and id.
* @param plugin the name of the plugin
* @param id the unique id of the plugin
* @param key the property key
* @param value the new value
*/
public void setProperty(String plugin, String id, String key, String value) {
if(id == null) id = ""; else id = "("+id+")";
setProperty(plugin+id, key, value);
}
/**
* Set the property value for a certain plugin.
* @param plugin the name of the plugin
* @param key the property key
* @param value the new value
*/
public void setProperty(String plugin, String key, String value) {
setProperty(plugin+"."+key, value);
}
}
jta_2.6+dfsg.orig/de/mud/jta/Plugin.java 0000644 0001750 0001750 00000004701 10610772601 016621 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
/**
* Plugin base class for the JTA. A plugin is a component
* for the PluginBus and may occur several times. If we have more than one
* plugin of the same type the protected value id contains the unique plugin
* id as configured in the configuration.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: Plugin.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class Plugin {
/** holds the plugin bus used for communication between plugins */
protected PluginBus bus;
/**
* in case we have several plugins of the same type this contains their
* unique id
*/
protected String id;
/**
* Create a new plugin and set the plugin bus used by this plugin and
* the unique id. The unique id may be null if there is only one plugin
* used by the system.
* @param bus the plugin bus
* @param id the unique plugin id
*/
public Plugin(PluginBus bus, String id) {
this.bus = bus;
this.id = id;
}
/**
* Return identifier for this plugin.
* @return id string
*/
public String getId() {
return id;
}
/**
* Print an error message to stderr prepending the plugin name. This method
* is public due to compatibility with Java 1.1
* @param msg the error message
*/
public void error(String msg) {
String name = getClass().toString();
name = name.substring(name.lastIndexOf('.') + 1);
System.err.println(name + (id != null ? "(" + id + ")" : "") + ": " + msg);
}
}
jta_2.6+dfsg.orig/de/mud/jta/Wrapper.java 0000644 0001750 0001750 00000013517 10610772601 017010 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
import java.io.InputStream;
import java.io.OutputStream;
import java.io.IOException;
import java.net.Socket;
import java.util.Vector;
import java.util.Properties;
import java.awt.Dimension;
import de.mud.telnet.ScriptHandler;
/**
* To write a program using the wrapper
* you may use the following piece of code as an example:
*
* TelnetWrapper telnet = new TelnetWrapper();
* try {
* telnet.connect(args[0], 23);
* telnet.login("user", "password");
* telnet.setPrompt("user@host");
* telnet.waitfor("Terminal type?");
* telnet.send("dumb");
* System.out.println(telnet.send("ls -l"));
* } catch(java.io.IOException e) {
* e.printStackTrace();
* }
*
* Please keep in mind that the password is visible for anyone who can
* download the class file. So use this only for public accounts or if
* you are absolutely sure nobody can see the file.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: Wrapper.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei\u00dfner
*/
public class Wrapper {
/** debugging level */
private final static int debug = 0;
protected ScriptHandler scriptHandler = new ScriptHandler();
private Thread reader;
protected InputStream in;
protected OutputStream out;
protected Socket socket;
protected String host;
protected int port = 23;
protected Vector script = new Vector();
/** Connect the socket and open the connection. */
public void connect(String host, int port) throws IOException {
if(debug>0) System.err.println("Wrapper: connect("+host+","+port+")");
try {
socket = new java.net.Socket(host, port);
in = socket.getInputStream();
out = socket.getOutputStream();
} catch(Exception e) {
System.err.println("Wrapper: "+e);
disconnect();
throw ((IOException)e);
}
}
/** Disconnect the socket and close the connection. */
public void disconnect() throws IOException {
if(debug>0) System.err.println("Wrapper: disconnect()");
if (socket != null)
socket.close();
}
/**
* Login into remote host. This is a convenience method and only
* works if the prompts are "login:" and "Password:".
* @param user the user name
* @param pwd the password
*/
public void login(String user, String pwd) throws IOException {
waitfor("login:"); // throw output away
send(user);
waitfor("Password:"); // throw output away
send(pwd);
}
/**
* Set the prompt for the send() method.
*/
private String prompt = null;
public void setPrompt(String prompt) {
this.prompt = prompt;
}
public String getPrompt() {
return prompt;
}
/**
* Send a command to the remote host. A newline is appended and if
* a prompt is set it will return the resulting data until the prompt
* is encountered.
* @param cmd the command
* @return output of the command or null if no prompt is set
*/
public String send(String cmd) throws IOException { return null; }
/**
* Wait for a string to come from the remote host and return all
* that characters that are received until that happens (including
* the string being waited for).
*
* @param match the string to look for
* @return skipped characters
*/
public String waitfor( String[] searchElements ) throws IOException {
ScriptHandler[] handlers = new ScriptHandler[searchElements.length];
for ( int i = 0; i < searchElements.length; i++ ) {
// initialize the handlers
handlers[i] = new ScriptHandler();
handlers[i].setup( searchElements[i] );
}
byte[] b1 = new byte[1];
int n = 0;
StringBuffer ret = new StringBuffer();
String current;
while(n >= 0) {
n = read(b1);
if(n > 0) {
current = new String( b1, 0, n );
if (debug > 0)
System.err.print( current );
ret.append( current );
for ( int i = 0; i < handlers.length ; i++ ) {
if ( handlers[i].match( ret.toString().getBytes(), ret.length() ) ) {
return ret.toString();
} // if
} // for
} // if
} // while
return null; // should never happen
}
public String waitfor(String match) throws IOException {
String[] matches = new String[1];
matches[0] = match;
return waitfor(matches);
}
/**
* Read data from the socket and use telnet negotiation before returning
* the data read.
* @param b the input buffer to read in
* @return the amount of bytes read
*/
public int read(byte[] b) throws IOException { return -1; };
/**
* Write data to the socket.
* @param b the buffer to be written
*/
public void write(byte[] b) throws IOException {
out.write(b);
}
public String getTerminalType() {
return "dumb";
}
public Dimension getWindowSize() {
return new Dimension(80,24);
}
public void setLocalEcho(boolean echo) {
if(debug > 0)
System.err.println("local echo "+(echo ? "on" : "off"));
}
}
jta_2.6+dfsg.orig/de/mud/jta/PluginBus.java 0000644 0001750 0001750 00000003276 10610772601 017301 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
/**
* A plugin bus is used for communication between plugins. The interface
* describes the broadcast method that should broad cast the message
* to all plugins known and return an answer message immediatly.
* The functionality is just simuliar to a bus, but depends on the
* actual implementation of the bus.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: PluginBus.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface PluginBus {
/** Broadcast a plugin message to all listeners. */
public Object broadcast(PluginMessage message);
/** Register a plugin listener with this bus object */
public void registerPluginListener(PluginListener listener);
}
jta_2.6+dfsg.orig/de/mud/jta/event/ 0000755 0001750 0001750 00000000000 10610772601 015637 5 ustar paul paul jta_2.6+dfsg.orig/de/mud/jta/event/FocusStatus.java 0000644 0001750 0001750 00000004162 10610772601 020770 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.Plugin;
import de.mud.jta.PluginMessage;
import de.mud.jta.PluginListener;
import java.awt.event.FocusEvent;
/**
* Notify all listeners that a component has got the input focus.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: FocusStatus.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class FocusStatus implements PluginMessage {
protected Plugin plugin;
protected FocusEvent event;
/** Create a new online status message with the specified value. */
public FocusStatus(Plugin plugin, FocusEvent event) {
this.plugin = plugin;
this.event = event;
}
/**
* Notify the listers about the focus status of the sending component.
* @param pl the list of plugin message listeners
* @return null
*/
public Object firePluginMessage(PluginListener pl) {
if(pl instanceof FocusStatusListener)
switch(event.getID()) {
case FocusEvent.FOCUS_GAINED:
((FocusStatusListener)pl).pluginGainedFocus(plugin); break;
case FocusEvent.FOCUS_LOST:
((FocusStatusListener)pl).pluginLostFocus(plugin);
}
return null;
}
}
jta_2.6+dfsg.orig/de/mud/jta/event/SetWindowSizeListener.java 0000644 0001750 0001750 00000002711 10610772601 022767 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginListener;
import java.awt.Dimension;
/**
* This is the interface for a window size listener.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: WindowSizeListener.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface SetWindowSizeListener extends PluginListener {
/** Set the current window size of the terminal in rows and columns. */
public void setWindowSize(int columns, int rows);
}
jta_2.6+dfsg.orig/de/mud/jta/event/LocalEchoListener.java 0000644 0001750 0001750 00000002676 10610772601 022054 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginListener;
/**
* This interface should be used by plugins who would like to be notified
* about the local echo property.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: LocalEchoListener.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface LocalEchoListener extends PluginListener {
/** Called if the local echo property changes. */
public void setLocalEcho(boolean echo);
}
jta_2.6+dfsg.orig/de/mud/jta/event/TerminalTypeListener.java 0000644 0001750 0001750 00000002777 10610772601 022642 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginListener;
/**
* This is the interface for a terminal type listener. It should return
* the terminal type id as a string. Valid terminal types include
* VT52, VT100, VT200, VT220, VT320, ANSI etc.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: TerminalTypeListener.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface TerminalTypeListener extends PluginListener {
/** Return the terminal type string */
public String getTerminalType();
}
jta_2.6+dfsg.orig/de/mud/jta/event/SetWindowSizeRequest.java 0000644 0001750 0001750 00000003406 10610772601 022634 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginMessage;
import de.mud.jta.PluginListener;
import de.mud.jta.event.SetWindowSizeListener;
/**
* Request the current window size of the terminal.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: WindowSizeRequest.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class SetWindowSizeRequest implements PluginMessage {
private int columns, rows;
public SetWindowSizeRequest(int c, int r) {
rows = r;
columns = c;
}
/**
* Set the new size of the window
* @param pl the list of plugin message listeners
*/
public Object firePluginMessage(PluginListener pl) {
if(pl instanceof SetWindowSizeListener) {
((SetWindowSizeListener)pl).setWindowSize(columns, rows);
}
return null;
}
}
jta_2.6+dfsg.orig/de/mud/jta/event/WindowSizeListener.java 0000644 0001750 0001750 00000002671 10610772601 022320 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginListener;
import java.awt.Dimension;
/**
* This is the interface for a window size listener.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: WindowSizeListener.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface WindowSizeListener extends PluginListener {
/** Return the current window size of the terminal in rows and columns. */
public Dimension getWindowSize();
}
jta_2.6+dfsg.orig/de/mud/jta/event/AppletRequest.java 0000644 0001750 0001750 00000003320 10610772601 021276 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginListener;
import de.mud.jta.PluginMessage;
import javax.swing.JApplet;
/**
* Tell listeners the applet object.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: AppletRequest.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class AppletRequest implements PluginMessage {
protected JApplet applet;
public AppletRequest(JApplet applet) {
this.applet = applet;
}
/**
* Notify all listeners of a configuration event.
* @param pl the list of plugin message listeners
*/
public Object firePluginMessage(PluginListener pl) {
if (pl instanceof AppletListener) {
((AppletListener) pl).setApplet(applet);
}
return null;
}
}
jta_2.6+dfsg.orig/de/mud/jta/event/TerminalTypeRequest.java 0000644 0001750 0001750 00000003436 10610772601 022476 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginMessage;
import de.mud.jta.PluginListener;
import de.mud.jta.event.TerminalTypeListener;
/**
* Request message for the current terminal type.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: TerminalTypeRequest.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class TerminalTypeRequest implements PluginMessage {
/**
* Ask all terminal type listener about the terminal type and return
* the first answer.
* @param pl the list of plugin message listeners
* @return the terminal type or null
*/
public Object firePluginMessage(PluginListener pl) {
if(pl instanceof TerminalTypeListener) {
Object ret = ((TerminalTypeListener)pl).getTerminalType();
if(ret != null) return ret;
}
return null;
}
}
jta_2.6+dfsg.orig/de/mud/jta/event/SocketRequest.java 0000644 0001750 0001750 00000004150 10610772601 021303 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginMessage;
import de.mud.jta.PluginListener;
import de.mud.jta.event.SocketListener;
/**
* Notification of a socket request. Send this message if the system
* should connect or disconnect.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: SocketRequest.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class SocketRequest implements PluginMessage {
String host;
int port;
/** Create a new disconnect message */
public SocketRequest() {
host = null;
}
/** Create a new connect message */
public SocketRequest(String host, int port) {
this.host = host;
this.port = port;
}
/**
* Tell all listeners that we would like to connect.
* @param pl the list of plugin message listeners
* @return the terminal type or null
*/
public Object firePluginMessage(PluginListener pl) {
if(pl instanceof SocketListener) try {
if(host != null)
((SocketListener)pl).connect(host, port);
else
((SocketListener)pl).disconnect();
} catch(Exception e) {
e.printStackTrace();
}
return null;
}
}
jta_2.6+dfsg.orig/de/mud/jta/event/TelnetCommandRequest.java 0000644 0001750 0001750 00000003756 10610772601 022620 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginMessage;
import de.mud.jta.PluginListener;
import de.mud.jta.event.TelnetCommandListener;
import java.io.IOException;
/**
* Notification of the end of record event
*
* Maintainer: Marcus Meissner
*
* @version $Id: TelnetCommandRequest.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class TelnetCommandRequest implements PluginMessage {
/** Create a new telnet command request with the specified value. */
byte cmd;
public TelnetCommandRequest(byte command ) { cmd = command; }
/**
* Notify all listeners about the end of record message
* @param pl the list of plugin message listeners
* @return always null
*/
public Object firePluginMessage(PluginListener pl) {
if(pl instanceof TelnetCommandListener) {
try {
((TelnetCommandListener)pl).sendTelnetCommand(cmd);
} catch (IOException io) {
System.err.println("io exception caught:"+io);
io.printStackTrace();
}
}
return null;
}
}
jta_2.6+dfsg.orig/de/mud/jta/event/SoundListener.java 0000644 0001750 0001750 00000002567 10610772601 021312 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginListener;
import java.net.URL;
/**
* Play a sound when requested.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: SoundListener.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface SoundListener extends PluginListener {
/** Play a sound that is given as a URL */
public void playSound(URL audioClip);
}
jta_2.6+dfsg.orig/de/mud/jta/event/TelnetCommandListener.java 0000644 0001750 0001750 00000003046 10610772601 022745 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginListener;
import java.io.IOException;
/**
* This interface should be used by plugins who would like to be notified
* about the end of record event
*
* Maintainer: Marcus Meissner
*
* @version $Id: TelnetCommandListener.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface TelnetCommandListener extends PluginListener {
/** Called by code in the terminal interface or somewhere for sending
* telnet commands
*/
public void sendTelnetCommand(byte command) throws IOException;
}
jta_2.6+dfsg.orig/de/mud/jta/event/OnlineStatusListener.java 0000644 0001750 0001750 00000002725 10610772601 022646 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginListener;
import java.awt.Dimension;
/**
* This is the interface for a online status listener.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: OnlineStatusListener.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface OnlineStatusListener extends PluginListener {
/** Called when the system is online. */
public void online();
/** Called when the system is offline. */
public void offline();
}
jta_2.6+dfsg.orig/de/mud/jta/event/EndOfRecordRequest.java 0000644 0001750 0001750 00000003411 10610772601 022204 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginMessage;
import de.mud.jta.PluginListener;
import de.mud.jta.event.EndOfRecordListener;
/**
* Notification of the end of record event
*
* Maintainer: Marcus Meissner
*
* @version $Id: EndOfRecordRequest.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class EndOfRecordRequest implements PluginMessage {
/** Create a new local echo request with the specified value. */
public EndOfRecordRequest() { }
/**
* Notify all listeners about the end of record message
* @param pl the list of plugin message listeners
* @return always null
*/
public Object firePluginMessage(PluginListener pl) {
if(pl instanceof EndOfRecordListener)
((EndOfRecordListener)pl).EndOfRecord();
return null;
}
}
jta_2.6+dfsg.orig/de/mud/jta/event/SoundRequest.java 0000644 0001750 0001750 00000003337 10610772601 021151 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginMessage;
import de.mud.jta.PluginListener;
import de.mud.jta.event.SoundListener;
import java.net.URL;
/**
* Play a sound.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: SoundRequest.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class SoundRequest implements PluginMessage {
protected URL audioClip;
public SoundRequest(URL audioClip) {
this.audioClip = audioClip;
}
/**
* Notify all listeners that they may play the sound.
* @param pl the list of plugin message listeners
*/
public Object firePluginMessage(PluginListener pl) {
if(pl instanceof SoundListener) {
((SoundListener)pl).playSound(audioClip);
}
return null;
}
}
jta_2.6+dfsg.orig/de/mud/jta/event/LocalEchoRequest.java 0000644 0001750 0001750 00000003627 10610772601 021714 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginMessage;
import de.mud.jta.PluginListener;
import de.mud.jta.event.LocalEchoListener;
/**
* Notification of the local echo property. The terminal should echo all
* typed in characters locally of this is true.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: LocalEchoRequest.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class LocalEchoRequest implements PluginMessage {
protected boolean xecho = false;
/** Create a new local echo request with the specified value. */
public LocalEchoRequest(boolean echo) {
xecho = echo;
}
/**
* Notify all listeners about the status of local echo.
* @param pl the list of plugin message listeners
* @return always null
*/
public Object firePluginMessage(PluginListener pl) {
if(pl instanceof LocalEchoListener)
((LocalEchoListener)pl).setLocalEcho(xecho);
return null;
}
}
jta_2.6+dfsg.orig/de/mud/jta/event/ConfigurationListener.java 0000644 0001750 0001750 00000002701 10610772601 023017 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginListener;
import de.mud.jta.PluginConfig;
/**
* Configuration listener will be notified of configuration events.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: ConfigurationListener.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface ConfigurationListener extends PluginListener {
/** Called for configuration changes. */
public void setConfiguration(PluginConfig config);
}
jta_2.6+dfsg.orig/de/mud/jta/event/FocusStatusListener.java 0000644 0001750 0001750 00000003050 10610772601 022471 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.Plugin;
import de.mud.jta.PluginListener;
import java.awt.Dimension;
/**
* This is the interface for a focus status listener.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: FocusStatusListener.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface FocusStatusListener extends PluginListener {
/** Called if a plugin gained the input focus. */
public void pluginGainedFocus(Plugin plugin);
/** Called if a plugin lost the input focus. */
public void pluginLostFocus(Plugin plugin);
}
jta_2.6+dfsg.orig/de/mud/jta/event/EndOfRecordListener.java 0000644 0001750 0001750 00000002661 10610772601 022347 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginListener;
/**
* This interface should be used by plugins who would like to be notified
* about the end of record event
*
* Maintainer: Marcus Meissner
*
* @version $Id: EndOfRecordListener.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface EndOfRecordListener extends PluginListener {
/** Called if the end of record event appears */
public void EndOfRecord();
}
jta_2.6+dfsg.orig/de/mud/jta/event/WindowSizeRequest.java 0000644 0001750 0001750 00000003262 10610772601 022160 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginMessage;
import de.mud.jta.PluginListener;
import de.mud.jta.event.WindowSizeListener;
/**
* Request the current window size of the terminal.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: WindowSizeRequest.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class WindowSizeRequest implements PluginMessage {
/**
* Return the size of the window
* @param pl the list of plugin message listeners
*/
public Object firePluginMessage(PluginListener pl) {
if(pl instanceof WindowSizeListener) {
Object ret = ((WindowSizeListener)pl).getWindowSize();
if(ret != null) return ret;
}
return null;
}
}
jta_2.6+dfsg.orig/de/mud/jta/event/ReturnFocusListener.java 0000644 0001750 0001750 00000003040 10610772601 022464 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginListener;
/**
* This interface should be used by plugins who would like to be notified
* about the return of the focus from another plugin.
*
* Implemented after a suggestion by Dave <david@mirrabooka.com>
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: ReturnFocusListener.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface ReturnFocusListener extends PluginListener {
/** Called if the end of return focus message is sent. */
public void returnFocus();
}
jta_2.6+dfsg.orig/de/mud/jta/event/OnlineStatus.java 0000644 0001750 0001750 00000003546 10610772601 021142 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginMessage;
import de.mud.jta.PluginListener;
/**
* Notify all listeners that we on or offline.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: OnlineStatus.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class OnlineStatus implements PluginMessage {
protected boolean online;
/** Create a new online status message with the specified value. */
public OnlineStatus(boolean online) {
this.online = online;
}
/**
* Notify the listers about the online status.
* @param pl the list of plugin message listeners
* @return the window size or null
*/
public Object firePluginMessage(PluginListener pl) {
if(pl instanceof OnlineStatusListener)
if(online)
((OnlineStatusListener)pl).online();
else
((OnlineStatusListener)pl).offline();
return null;
}
}
jta_2.6+dfsg.orig/de/mud/jta/event/AppletListener.java 0000644 0001750 0001750 00000002743 10610772601 021443 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginListener;
import javax.swing.JApplet;
/**
* This is the interface is for applet listeners, plugins that
* want to know the applet object.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: AppletListener.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface AppletListener extends PluginListener {
/** Return the current window size of the terminal in rows and columns. */
public void setApplet(JApplet applet);
}
jta_2.6+dfsg.orig/de/mud/jta/event/ConfigurationRequest.java 0000644 0001750 0001750 00000003606 10610772601 022667 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginMessage;
import de.mud.jta.PluginListener;
import de.mud.jta.PluginConfig;
import de.mud.jta.event.ConfigurationListener;
/**
* Configuration request message. Subclassing this message can be used to
* make the configuration more specific and efficient.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: ConfigurationRequest.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class ConfigurationRequest implements PluginMessage {
PluginConfig config;
public ConfigurationRequest(PluginConfig config) {
this.config = config;
}
/**
* Notify all listeners of a configuration event.
* @param pl the list of plugin message listeners
*/
public Object firePluginMessage(PluginListener pl) {
if(pl instanceof ConfigurationListener) {
((ConfigurationListener)pl).setConfiguration(config);
}
return null;
}
}
jta_2.6+dfsg.orig/de/mud/jta/event/SocketListener.java 0000644 0001750 0001750 00000003251 10610772601 021441 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginListener;
import java.net.UnknownHostException;
import java.io.IOException;
/**
* The socket listener should be implemented by plugins that want to know
* when the whole systems connects or disconnects.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: SocketListener.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface SocketListener extends PluginListener {
/** Called if a connection should be established. */
public void connect(String host, int port)
throws UnknownHostException, IOException;
/** Called if the connection should be stopped. */
public void disconnect()
throws IOException;
}
jta_2.6+dfsg.orig/de/mud/jta/event/ReturnFocusRequest.java 0000644 0001750 0001750 00000003425 10610772601 022336 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.event;
import de.mud.jta.PluginMessage;
import de.mud.jta.PluginListener;
import de.mud.jta.event.ReturnFocusListener;
/**
* Notify listeners that the focus is to be returned to whoever wants it.
*
* Implemented after a suggestion by Dave <david@mirrabooka.com>
*
* Maintainer: Matthias L. Jugel
*
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class ReturnFocusRequest implements PluginMessage {
/** Create a new return focus request.*/
public ReturnFocusRequest() { }
/**
* Notify all listeners about return focus message.
* @param pl the list of plugin message listeners
* @return always null
*/
public Object firePluginMessage(PluginListener pl) {
if(pl instanceof ReturnFocusListener)
((ReturnFocusListener)pl).returnFocus();
return null;
}
}
jta_2.6+dfsg.orig/de/mud/jta/PluginLoader.java 0000644 0001750 0001750 00000015430 10610772601 017751 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
import java.lang.reflect.Constructor;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.Map;
import java.util.Vector;
import java.util.List;
import java.util.ArrayList;
/**
* The plugin loader tries to load the plugin by name and returns a
* corresponding plugin object. It takes care of connecting filter
* plugins
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: PluginLoader.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class PluginLoader implements PluginBus {
/** holds the current version id */
public final static String ID = "$Id: PluginLoader.java 499 2005-09-29 08:24:54Z leo $";
private final static int debug = 0;
/** the path to standard plugins */
private Vector PATH = null;
/** holds all the filters */
private List filter = new ArrayList();
private Map plugins;
/**
* Create new plugin loader and set up with default plugin path.
*/
public PluginLoader() {
this(null);
}
/**
* Create new plugin loader and set up with specified plugin path.
* @param path the default search path for plugins
*/
public PluginLoader(Vector path) {
plugins = new HashMap();
if (path == null) {
PATH = new Vector();
PATH.addElement("de.mud.jta.plugin");
} else
PATH = path;
}
/**
* Add a new plugin to the system and register the plugin load as its
* communication bus. If the plugin is a filter plugin and if it is
* not the first filter the last added filter will be set as its filter
* source.
* @param name the string name of the plugin
* @return the newly created plugin or null in case of an error
*/
public Plugin addPlugin(String name, String id) {
Plugin plugin = loadPlugin(name, id);
// if it was not found, try without a path as a last resort
if (plugin == null)
plugin = loadPlugin(null, name, id);
// nothing found, tell the user
if (plugin == null) {
System.err.println("plugin loader: plugin '" + name + "' was not found!");
return null;
}
// configure the filter plugins
if (plugin instanceof FilterPlugin) {
if (filter.size() > 0)
((FilterPlugin) plugin)
.setFilterSource((FilterPlugin) filter.get(filter.size() - 1));
filter.add(plugin);
}
plugins.put(name+(id == null ? "" : "(" + id + ")"), plugin);
return plugin;
}
/**
* Replace a plugin with a new one, actually reloads the plugin.
* @param name name of plugin to be replaced
* @param id unique id
* @return the newly loaded plugin
*/
public Plugin replacePlugin(String name, String id) {
Plugin plugin = loadPlugin(name, id);
if(plugin != null) {
Plugin oldPlugin = (Plugin)plugins.get(name + (id == null ? "" : "(" + id + ")"));
if(filter.contains(oldPlugin)) {
int index = filter.indexOf(oldPlugin);
filter.set(index, plugin);
((FilterPlugin)plugin).setFilterSource(((FilterPlugin)oldPlugin).getFilterSource());
if(index < filter.size() - 1) {
((FilterPlugin)filter.get(index + 1)).setFilterSource((FilterPlugin)plugin);
}
}
}
return plugin;
}
/**
* Load a plugin by cycling through the plugin path.
* @param name the class name of the plugin
* @param id an id in case of multiple plugins of the same name
* @return the loaded plugin or null if none was found
*/
private Plugin loadPlugin(String name, String id) {
Plugin plugin = null;
// cycle through the PATH to load plugin
Enumeration pathList = PATH.elements();
while (pathList.hasMoreElements()) {
String path = (String) pathList.nextElement();
plugin = loadPlugin(path, name, id);
if (plugin != null) {
return plugin;
}
}
plugin = loadPlugin(null, name, id);
return plugin;
}
/**
* Load a plugin using the specified path name and id.
* @param path the package where the plugin can be found
* @param name the class name of the plugin
* @param id an id for multiple plugins of the same name
* @return a loaded plugin or null if none was found
*/
private Plugin loadPlugin(String path, String name, String id) {
Plugin plugin = null;
String fullClassName = (path == null) ? name : path + "." + name;
// load the plugin by name and instantiate it
try {
Class c = Class.forName(fullClassName);
Constructor cc = c.getConstructor(new Class[]{PluginBus.class,
String.class});
plugin = (Plugin) cc.newInstance(new Object[]{this, id});
return plugin;
} catch (ClassNotFoundException ce) {
if (debug > 0)
System.err.println("plugin loader: plugin not found: " + fullClassName);
} catch (Exception e) {
System.err.println("plugin loader: can't load plugin: " + fullClassName);
e.printStackTrace();
}
return null;
}
/** holds the plugin listener we serve */
private Vector listener = new Vector();
/**
* Register a new plugin listener.
*/
public void registerPluginListener(PluginListener l) {
listener.addElement(l);
}
/**
* Implementation of the plugin bus. Broadcast a message to all
* listeners we know of. The message takes care that the right
* methods are called in the listeners.
* @param message the plugin message to be sent
* @return the answer to the sent message
*/
public Object broadcast(PluginMessage message) {
if (debug > 0) System.err.println("broadcast(" + message + ")");
if (message == null || listener == null)
return null;
Enumeration e = listener.elements();
Object res = null;
while (res == null && e.hasMoreElements())
res = message.firePluginMessage((PluginListener) e.nextElement());
return res;
}
public Map getPlugins() {
return plugins;
}
}
jta_2.6+dfsg.orig/de/mud/jta/PluginMessage.java 0000644 0001750 0001750 00000002727 10610772601 020134 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta;
/**
* The base interface for a plugin message.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: PluginMessage.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public interface PluginMessage {
/**
* Fire the message to all listeners that are compatible with this
* message and return the result.
* @param pl the list of plugin message listeners
* @return the result message
*/
public Object firePluginMessage(PluginListener pl);
}
jta_2.6+dfsg.orig/de/mud/jta/plugin/ 0000755 0001750 0001750 00000000000 10610772601 016014 5 ustar paul paul jta_2.6+dfsg.orig/de/mud/jta/plugin/Shell.java 0000644 0001750 0001750 00000006677 10610772601 017746 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
import de.mud.jta.Plugin;
import de.mud.jta.FilterPlugin;
import de.mud.jta.PluginBus;
import de.mud.jta.PluginConfig;
import de.mud.jta.event.LocalEchoRequest;
import de.mud.jta.event.SocketListener;
import de.mud.jta.event.ConfigurationListener;
import de.mud.jta.event.OnlineStatus;
// import java.io.InputStream;
// import java.io.OutputStream;
import java.io.IOException;
/**
* The shell plugin is the backend component for terminal emulation using
* a shell. It provides the i/o streams of the shell as data source.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: Shell.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner, Pete Zaitcev
*/
public class Shell extends Plugin implements FilterPlugin {
protected String shellCommand;
private HandlerPTY pty;
public Shell(final PluginBus bus, final String id) {
super(bus, id);
bus.registerPluginListener(new ConfigurationListener() {
public void setConfiguration(PluginConfig cfg) {
String tmp;
if((tmp = cfg.getProperty("Shell", id, "command")) != null) {
shellCommand = tmp;
// System.out.println("Shell: Setting config " + tmp); // P3
} else {
// System.out.println("Shell: Not setting config"); // P3
shellCommand = "/bin/sh";
}
}
});
bus.registerPluginListener(new SocketListener() {
// we do actually ignore these parameters
public void connect(String host, int port) {
// XXX Fix this together with window size changes
// String ttype = (String)bus.broadcast(new TerminalTypeRequest());
// String ttype = getTerminalType();
// if(ttype == null) ttype = "dumb";
// XXX Add try around here to catch missing DLL/.so.
pty = new HandlerPTY();
if(pty.start(shellCommand) == 0) {
bus.broadcast(new OnlineStatus(true));
} else {
bus.broadcast(new OnlineStatus(false));
}
}
public void disconnect() {
bus.broadcast(new OnlineStatus(false));
pty = null;
}
});
}
public void setFilterSource(FilterPlugin plugin) {
// we do not have a source other than our socket
}
public FilterPlugin getFilterSource() {
return null;
}
public int read(byte[] b) throws IOException {
if(pty == null) return 0;
int ret = pty.read(b);
if(ret <= 0) {
throw new IOException("EOF on PTY");
}
return ret;
}
public void write(byte[] b) throws IOException {
if(pty != null) pty.write(b);
}
}
jta_2.6+dfsg.orig/de/mud/jta/plugin/MudConnector.java 0000644 0001750 0001750 00000026573 10610772601 021274 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
import de.mud.jta.Plugin;
import de.mud.jta.PluginBus;
import de.mud.jta.PluginConfig;
import de.mud.jta.VisualPlugin;
import de.mud.jta.event.ConfigurationListener;
import de.mud.jta.event.ReturnFocusListener;
import de.mud.jta.event.SocketRequest;
import javax.swing.JButton;
import javax.swing.JComponent;
import javax.swing.JLabel;
import javax.swing.JList;
import javax.swing.JMenu;
import javax.swing.JMenuItem;
import javax.swing.JPanel;
import javax.swing.JTextField;
import javax.swing.JScrollPane;
import javax.swing.event.ListSelectionEvent;
import javax.swing.event.ListSelectionListener;
import java.awt.BorderLayout;
import java.awt.CardLayout;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.GridLayout;
import java.awt.Image;
import java.awt.MenuItem;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.io.StreamTokenizer;
import java.net.URL;
import java.util.Map;
import java.util.HashMap;
import java.util.Collections;
import java.util.List;
import java.util.ArrayList;
/**
* The MudConnector (http://www.mudconnector.com) plugin. The plugin will
* download a list of MUDs from a special list availabe at the url above
* and the user can select the mud and connect to it. This usually requires
* the relayd program to be run on the web server as this plugin tries to
* establish connections to other hosts than the web server.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: MudConnector.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class MudConnector
extends Plugin
implements VisualPlugin, Runnable, ActionListener {
/** debugging level */
private final static int debug = 0;
protected URL listURL = null;
protected int step;
protected Map mudList = null;
protected JList mudListSelector = new JList();
protected JTextField mudName, mudAddr, mudPort;
protected JButton connect;
protected JPanel mudListPanel;
protected CardLayout layouter;
protected ProgressBar progress;
protected JLabel errorLabel;
protected JMenu MCMenu;
/**
* Implementation of a progress bar to display the progress of
* loading the mud list.
*/
class ProgressBar extends JComponent {
int max, current;
String text;
Dimension size = new Dimension(250, 20);
Image backingStore;
public void setMax(int max) {
this.max = max;
}
public void update(Graphics g) {
paint(g);
}
public void paint(Graphics g) {
if (backingStore == null) {
backingStore = createImage(getSize().width, getSize().height);
redraw();
}
g.drawImage(backingStore, 0, 0, this);
}
private void redraw() {
if (backingStore == null || text == null) return;
Graphics g = backingStore.getGraphics();
int width = (int) (((float) current / (float) max) * getSize().width);
g.fill3DRect(0, 0, getSize().width, getSize().height, false);
g.setColor(getBackground());
g.fill3DRect(0, 0, width, getSize().height, true);
g.setColor(getForeground());
g.setXORMode(getBackground());
String percent = "" + (current * 100 / (max > 0?max:1))
+ "% / " + current + " of "+max;
g.drawString(percent,
getSize().width / 2 -
getFontMetrics(getFont()).stringWidth(percent) / 2,
getSize().height / 2);
g.drawString(text,
getSize().width / 2 -
getFontMetrics(getFont()).stringWidth(text) / 2,
getSize().height / 2 + 12);
paint(getGraphics());
}
public void adjust(int value, String name) {
if ((current = value) > max)
current = max;
text = name;
if (((float) current / (float) step) == (int) (current / step))
redraw();
}
public void setSize(int width, int height) {
size = new Dimension(width, height);
}
public Dimension getPreferredSize() {
return size;
}
public Dimension getMinimumSize() {
return size;
}
}
/**
* Create the list plugin and get the url to the actual list.
*/
public MudConnector(final PluginBus bus, final String id) {
super(bus, id);
bus.registerPluginListener(new ConfigurationListener() {
public void setConfiguration(PluginConfig config) {
String url =
config.getProperty("MudConnector", id, "listURL");
if (url != null) {
try {
listURL = new URL(url);
} catch (Exception e) {
MudConnector.this.error("" + e);
errorLabel.setText("Error: " + e);
}
} else {
MudConnector.this.error("no listURL specified");
errorLabel.setText("Missing list URL");
layouter.show(mudListPanel, "ERROR");
}
String sstep = config.getProperty("MudConnector", id, "step");
try {
step = Integer.parseInt(sstep);
} catch (Exception e) {
if (sstep != null)
MudConnector.this.error("warning: " + sstep + " is not a number");
step = 10;
}
}
});
bus.registerPluginListener(new ReturnFocusListener() {
public void returnFocus() {
setup();
}
});
mudListPanel = new JPanel(layouter = new CardLayout()) {
public void update(java.awt.Graphics g) {
paint(g);
}
};
mudListPanel.add("ERROR", errorLabel = new JLabel("Loading ..."));
JPanel panel = new JPanel(new BorderLayout());
panel.add("North", new JLabel("Loading mud list ... please wait"));
panel.add("Center", progress = new ProgressBar());
mudListPanel.add("PROGRESS", panel);
panel = new JPanel(new BorderLayout());
JScrollPane scrollPane = new JScrollPane(mudListSelector);
panel.add("Center", scrollPane);
mudListPanel.add("MUDLIST", panel);
panel.add("East", panel = new JPanel(new GridLayout(3, 1)));
panel.add(mudName = new JTextField(20));
mudName.setEditable(false);
JPanel apanel = new JPanel(new BorderLayout());
apanel.add("Center", mudAddr = new JTextField(20));
mudAddr.setEditable(false);
apanel.add("East", mudPort = new JTextField(6));
mudPort.setEditable(false);
panel.add(apanel);
panel.add(connect = new JButton("Connect"));
connect.addActionListener(this);
mudListSelector.setVisibleRowCount(3);
mudListSelector.addListSelectionListener(new ListSelectionListener() {
public void valueChanged(ListSelectionEvent evt) {
JList list = (JList) evt.getSource();
list.ensureIndexIsVisible(list.getSelectedIndex());
String item = (String) list.getSelectedValue();
mudName.setText(item);
Object mud[] = (Object[]) mudList.get(item);
mudAddr.setText((String) mud[0]);
mudPort.setText(((Integer) mud[1]).toString());
}
});
layouter.show(mudListPanel, "PROGRESS");
MCMenu = new JMenu("MudConnector");
}
private void setup() {
if (mudList == null && listURL != null)
(new Thread(this)).start();
}
public void run() {
try {
Map menuList = new HashMap();
mudList = new HashMap();
BufferedReader r =
new BufferedReader(new InputStreamReader(listURL.openStream()));
String line = r.readLine();
int mudCount = 0;
try {
mudCount = Integer.parseInt(line);
} catch (NumberFormatException nfe) {
error("number of muds: " + nfe);
}
System.out.println("MudConnector: expecting " + mudCount + " mud entries");
progress.setMax(mudCount);
StreamTokenizer ts = new StreamTokenizer(r);
ts.resetSyntax();
ts.whitespaceChars(0, 9);
ts.ordinaryChars(32, 255);
ts.wordChars(32, 255);
String name, host;
Integer port;
int token, counter = 0, idx = 0;
while ((token = ts.nextToken()) != ts.TT_EOF) {
name = ts.sval;
if ((token = ts.nextToken()) != ts.TT_EOF) {
if (token == ts.TT_EOL)
error(name + ": unexpected end of line"
+ ", missing host and port");
host = ts.sval;
port = new Integer(23);
if ((token = ts.nextToken()) != ts.TT_EOF)
try {
if (token == ts.TT_EOL)
error(name + ": default port 23");
port = new Integer(ts.sval);
} catch (NumberFormatException nfe) {
error("port for " + name + ": " + nfe);
}
if (debug > 0)
error(name + " [" + host + "," + port + "]");
mudList.put(name, new Object[]{host, port, new Integer(idx++)});
progress.adjust(++counter, name);
mudListPanel.repaint();
String key = (""+name.charAt(0)).toUpperCase();
JMenu subMenu = (JMenu) menuList.get(key);
if (subMenu == null) {
subMenu = new JMenu(key);
MCMenu.add(subMenu);
menuList.put(key, subMenu);
}
JMenuItem item = new JMenuItem(name);
item.addActionListener(MudConnector.this);
subMenu.add(item);
}
while (token != ts.TT_EOF && token != ts.TT_EOL)
token = ts.nextToken();
}
List list = new ArrayList(mudList.keySet());
Collections.sort(list);
mudListSelector.setListData(list.toArray());
System.out.println("MudConnector: found " + mudList.size() + " entries");
} catch (Exception e) {
error("error: " + e);
errorLabel.setText("Error: " + e);
layouter.show(mudListPanel, "ERROR");
}
layouter.show(mudListPanel, "MUDLIST");
}
public void actionPerformed(ActionEvent evt) {
if (evt.getSource() instanceof MenuItem) {
String item = evt.getActionCommand();
int idx = ((Integer) ((Object[]) mudList.get(item))[2]).intValue();
mudListSelector.setSelectedIndex(idx);
mudName.setText(item);
Object mud[] = (Object[]) mudList.get(item);
mudAddr.setText((String) mud[0]);
mudPort.setText(((Integer) mud[1]).toString());
}
String addr = mudAddr.getText();
String port = mudPort.getText();
if (addr != null) {
bus.broadcast(new SocketRequest());
if (port == null || port.length() <= 0)
port = "23";
bus.broadcast(new SocketRequest(addr, Integer.parseInt(port)));
}
}
public JComponent getPluginVisual() {
return mudListPanel;
}
public JMenu getPluginMenu() {
return MCMenu;
}
}
jta_2.6+dfsg.orig/de/mud/jta/plugin/HandlerPTY.java 0000644 0001750 0001750 00000003306 10610772601 020633 0 ustar paul paul // JNI interface to slave process.
// This is a part of Shell plugin.
// If not for a static member, we'd have HandlerPTY private to Shell. XXX
// HandlerPTY is meant to be robust, in a way that you can
// instantiate it and work with it until it throws an exception,
/*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
public class HandlerPTY {
public native int start(String cmd); // open + fork/exec
public native void close();
public native int read(byte[] b);
public native int write(byte[] b);
private int fd;
boolean good = false;
static {
// System.loadLibrary("libutil"); // forkpty on Linux lives in libutil
System.loadLibrary("jtapty");
}
protected void finalize() throws Throwable {
super.finalize();
if(good) {
close();
}
}
}
jta_2.6+dfsg.orig/de/mud/jta/plugin/ButtonBar.java 0000644 0001750 0001750 00000043266 10610772601 020572 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
import de.mud.jta.FilterPlugin;
import de.mud.jta.Plugin;
import de.mud.jta.PluginBus;
import de.mud.jta.PluginConfig;
import de.mud.jta.VisualPlugin;
import de.mud.jta.event.ConfigurationListener;
import de.mud.jta.event.SocketRequest;
import de.mud.jta.event.TelnetCommandRequest;
import javax.swing.JButton;
import javax.swing.JComponent;
import javax.swing.JLabel;
import javax.swing.JList;
import javax.swing.JMenu;
import javax.swing.JPanel;
import javax.swing.JTextField;
import javax.swing.event.ListSelectionEvent;
import javax.swing.event.ListSelectionListener;
import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.StreamTokenizer;
import java.net.URL;
import java.util.HashMap;
import java.util.Map;
/**
* Implementation of a programmable button bar to be used as a plugin
* in the Java(tm) Telnet Applet/Application. The button bar is configured
* using a input file that contains the setup for the button bar.
* A typical setup file may look like:
*
* #
* # Example for writing a button bar config file.
* #
* # The syntaxt for defining buttons, input fields and breaks is as follows:
* #
* # - defining a button:
* # A button is defined by giving the keyword 'button' followed by the text
* # of the button and the command that should be sent when pressing the
* # button. If the command contains whitespace characters, enclode it in
* # quote (") characters!
* #
* button Connect "\$connect(\@host@,\@port@)"
* #
* # - defining a label:
* # A labvel is defined by giving the keyword 'label' followed by the text
* # of the label. If the label contains whitespace characters, enclode it in
* # quote (") characters!
* #
* label "Hello User"
* #
* # - defining an input field:
* # An input field is defined just like the button above, but it has one more
* # parameter, the size of the input field. So you define it, by giving the
* # keyword 'input' followed by the name of the input field (for reference)
* # followed by the size of the input field and optionally a third parameter
* # which is the initial text to be displayed in that field.
* #
* input host 20 "tanis"
* stretch
* input port 4 "23"
* #
* # Now after the button and two input fields we define another button which
* # will be shown last in the row. Order is significant for the order in
* # which the buttons and fields appear.
* #
* button Disconnect "\\$disconnect()" break
* #
* # To implement an input line that is cleared and sends text use this:
* # The following line send the text in the input field "send" and appends
* # a newline.
* input send 20 "\\@send@\n" "ls"
* #
* # - Defining a choice
* # A choice is defined just like the button above, but it has multiple
* # text/command pairs. If the text or command contain whitespace characters,
* # enclose them in quote (") characters. The text and command data may be
* # spread over several lines for better readability. Make the first command
* # empty because it is initially selected, and choosing it will have no
* # effect until some other item has been chosen.
* #choice "- choose -" ""
* # "Text 1" "Command 1"
* # "Text 2" "Command 2"
* # "Text 3" "Command 3"
* # etc...
*
* Other possible keywords are break which does introduce a new
* line so that buttons and input fields defined next will appear in a new
* line below and stretch to make the just defined button or input
* field stretched as far as possible on the line. That last keyword is
* useful to fill the space.
*
* @version $Id: ButtonBar.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class ButtonBar extends Plugin
implements FilterPlugin, VisualPlugin, ActionListener, ListSelectionListener {
/** the panel that contains the buttons and input fields */
protected JPanel panel = new JPanel();
// these tables contain our buttons and fields.
private Map buttons = null;
private Map choices = null;
private Map fields = null;
// the switch for clearing input fields after enter
private boolean clearFields = true;
/**
* Initialize the button bar and register plugin listeners
*/
public ButtonBar(PluginBus bus, final String id) {
super(bus, id);
// configure the button bar
bus.registerPluginListener(new ConfigurationListener() {
public void setConfiguration(PluginConfig cfg) {
String file = cfg.getProperty("ButtonBar", id, "setup");
clearFields =
(new Boolean(cfg.getProperty("ButtonBar", id, "clearFields")))
.booleanValue();
// check for the setup file
if (file == null) {
ButtonBar.this.error("no setup file");
return;
}
StreamTokenizer setup = null;
InputStream is = null;
try {
is = getClass().getResourceAsStream(file);
} catch (Exception e) {
// ignore any errors here
}
// if the resource access fails, try URL
if (is == null)
try {
is = new URL(file).openStream();
} catch (Exception ue) {
ButtonBar.this.error("could not find: " + file);
return;
}
// create a new stream tokenizer to read the file
try {
InputStreamReader ir = new InputStreamReader(is);
setup = new StreamTokenizer(new BufferedReader(ir));
} catch (Exception e) {
ButtonBar.this.error("cannot load " + file + ": " + e);
return;
}
setup.commentChar('#');
setup.quoteChar('"');
fields = new HashMap();
buttons = new HashMap();
choices = new HashMap();
GridBagLayout l = new GridBagLayout();
GridBagConstraints c = new GridBagConstraints();
panel.setLayout(l);
c.fill = GridBagConstraints.BOTH;
int token;
int ChoiceCount = 0;
JList list;
// parse the setup file
try {
while ((token = setup.nextToken()) != StreamTokenizer.TT_EOF) {
switch (token) {
case StreamTokenizer.TT_WORD:
// reset the constraints
c.gridwidth = 1;
c.weightx = 0.0;
c.weighty = 0.0;
// keyword found, parse arguments
if (setup.sval.equals("button")) {
if ((token = setup.nextToken()) != StreamTokenizer.TT_EOF) {
String descr = setup.sval;
if ((token = setup.nextToken()) != StreamTokenizer.TT_EOF) {
JButton b = new JButton(descr);
buttons.put(b, setup.sval);
b.addActionListener(ButtonBar.this);
l.setConstraints(b, constraints(c, setup));
panel.add(b);
} else
ButtonBar.this.error(descr + ": missing button command");
} else
ButtonBar.this.error("unexpected end of file");
} else if (setup.sval.equals("label")) {
if ((token = setup.nextToken()) != StreamTokenizer.TT_EOF) {
String descr = setup.sval;
JLabel b = new JLabel(descr);
l.setConstraints(b, constraints(c, setup));
panel.add(b);
} else
ButtonBar.this.error("unexpected end of file");
/* choice - new stuff added APS 07-dec-2001 for Choice
* buttons
* Choice info is held in the choices hash. There are two
* sorts of hash entry:
* 1) for each choices button on the terminal, key=choice
* object, value=ID ("C1.", "C2.", etc)
* 2) for each item, key=ID+user's text (eg "C1.opt1"),
* value=user's command
*/
} else if (setup.sval.equals("choice")) {
ChoiceCount++;
String ident = "C" + ChoiceCount + ".";
list = new JList();
choices.put(list, ident);
list.addListSelectionListener(ButtonBar.this);// Choices use ItemListener, not Action
l.setConstraints(list, constraints(c, setup));
panel.add(list);
while ((token = setup.nextToken()) != StreamTokenizer.TT_EOF) {
if (isKeyword(setup.sval)) {// Got command ... Back off.
setup.pushBack();
break;
}
String descr = setup.sval; // This is the hash key.
token = setup.nextToken();
if (token == StreamTokenizer.TT_EOF) {
ButtonBar.this.error("unexpected end of file");
} else {
String value = setup.sval;
if (isKeyword(value)) { // Missing command - complain but continue
System.err.println(descr + ": missing choice command");
setup.pushBack();
break;
}
System.out.println("choice: name='" + descr + "', value='" + value);
list.add(descr, new JLabel(descr));
choices.put(ident + descr, value);
}
}
ButtonBar.this.error("choices hash: " + choices);
} else if (setup.sval.equals("input")) {
if ((token = setup.nextToken()) != StreamTokenizer.TT_EOF) {
String descr = setup.sval;
if ((token = setup.nextToken()) ==
StreamTokenizer.TT_NUMBER) {
int size = (int) setup.nval;
String init = "", command = "";
token = setup.nextToken();
if (isKeyword(setup.sval))
setup.pushBack();
else
command = setup.sval;
token = setup.nextToken();
if (isKeyword(setup.sval)) {
setup.pushBack();
init = command;
} else
init = setup.sval;
JTextField t = new JTextField(init, size);
if (!init.equals(command)) {
buttons.put(t, command);
t.addActionListener(ButtonBar.this);
}
fields.put(descr, t);
l.setConstraints(t, constraints(c, setup));
panel.add(t);
} else
ButtonBar.this.error(descr + ": missing field size");
} else
ButtonBar.this.error("unexpected end of file");
}
break;
default:
ButtonBar.this.error("syntax error at line " + setup.lineno());
}
}
} catch (IOException e) {
ButtonBar.this.error("unexpected error while reading setup: " + e);
}
panel.validate();
}
});
}
private GridBagConstraints constraints(GridBagConstraints c,
StreamTokenizer setup)
throws IOException {
if (setup.nextToken() == StreamTokenizer.TT_WORD)
if (setup.sval.equals("break"))
c.gridwidth = GridBagConstraints.REMAINDER;
else if (setup.sval.equals("stretch"))
c.weightx = 1.0;
else
setup.pushBack();
else
setup.pushBack();
return c;
}
public void valueChanged(ListSelectionEvent evt) {
String tmp, ident;
if ((ident = (String) choices.get(evt.getSource())) != null) {
// It's a choice - get the text from the selected item
JList list = (JList) evt.getSource();
tmp = (String) choices.get(ident + list.getSelectedValue());
if (tmp != null) processEvent(tmp);
}
}
public void actionPerformed(ActionEvent evt) {
String tmp;
if ((tmp = (String) buttons.get(evt.getSource())) != null)
processEvent(tmp);
}
private void processEvent(String tmp) {
String cmd = "", function = null;
int idx = 0, oldidx = 0;
while ((idx = tmp.indexOf('\\', oldidx)) >= 0 &&
++idx <= tmp.length()) {
cmd += tmp.substring(oldidx, idx - 1);
switch (tmp.charAt(idx)) {
case 'b':
cmd += "\b";
break;
case 'e':
cmd += "";
break;
case 'n':
cmd += "\n";
break;
case 'r':
cmd += "\r";
break;
case '$':
{
int ni = tmp.indexOf('(', idx + 1);
if (ni < idx) {
error("ERROR: Function: missing '('");
break;
}
if (ni == ++idx) {
error("ERROR: Function: missing name");
break;
}
function = tmp.substring(idx, ni);
idx = ni + 1;
ni = tmp.indexOf(')', idx);
if (ni < idx) {
error("ERROR: Function: missing ')'");
break;
}
tmp = tmp.substring(idx, ni);
idx = oldidx = 0;
continue;
}
case '@':
{
int ni = tmp.indexOf('@', idx + 1);
if (ni < idx) {
error("ERROR: Input Field: '@'-End Marker not found");
break;
}
if (ni == ++idx) {
error("ERROR: Input Field: no name specified");
break;
}
String name = tmp.substring(idx, ni);
idx = ni;
JTextField t;
if (fields == null || (t = (JTextField) fields.get(name)) == null) {
error("ERROR: Input Field: requested input \"" +
name + "\" does not exist");
break;
}
cmd += t.getText();
if (clearFields) t.setText("");
break;
}
default :
cmd += tmp.substring(idx, ++idx);
}
oldidx = ++idx;
}
if (oldidx <= tmp.length()) cmd += tmp.substring(oldidx, tmp.length());
if (function != null) {
if (function.equals("break")) {
bus.broadcast(new TelnetCommandRequest((byte) 243)); // BREAK
return;
}
if (function.equals("exit")) {
try {
System.exit(0);
} catch (Exception e) {
error("cannot exit: " + e);
}
}
if (function.equals("connect")) {
String address = null;
int port = -1;
try {
if ((idx = cmd.indexOf(",")) >= 0) {
try {
port = Integer.parseInt(cmd.substring(idx + 1, cmd.length()));
} catch (Exception e) {
port = -1;
}
cmd = cmd.substring(0, idx);
}
if (cmd.length() > 0) address = cmd;
if (address != null)
if (port != -1)
bus.broadcast(new SocketRequest(address, port));
else
bus.broadcast(new SocketRequest(address, 23));
else
error("connect: no address");
} catch (Exception e) {
error("connect(): failed");
e.printStackTrace();
}
} else if (function.equals("disconnect"))
bus.broadcast(new SocketRequest());
else if (function.equals("detach")) {
error("detach not implemented yet");
} else
error("ERROR: function not implemented: \"" + function + "\"");
return;
}
// cmd += tmp.substring(oldidx, tmp.length());
if (cmd.length() > 0)
try {
write(cmd.getBytes());
} catch (IOException e) {
error("send: " + e);
}
}
public JComponent getPluginVisual() {
return panel;
}
public JMenu getPluginMenu() {
return null;
}
FilterPlugin source;
public void setFilterSource(FilterPlugin source) {
this.source = source;
}
public FilterPlugin getFilterSource() {
return source;
}
public int read(byte[] b) throws IOException {
return source.read(b);
}
public void write(byte[] b) throws IOException {
source.write(b);
}
private static boolean isKeyword(String txt) {
return (
txt.equals("button") ||
txt.equals("label") ||
txt.equals("input") ||
txt.equals("stretch") ||
txt.equals("choice") ||
txt.equals("break")
);
}
}
jta_2.6+dfsg.orig/de/mud/jta/plugin/Capture.java 0000644 0001750 0001750 00000033562 10610772601 020273 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
import de.mud.jta.FilterPlugin;
import de.mud.jta.Plugin;
import de.mud.jta.PluginBus;
import de.mud.jta.PluginConfig;
import de.mud.jta.VisualPlugin;
import de.mud.jta.event.ConfigurationListener;
import javax.swing.JButton;
import javax.swing.JComponent;
import javax.swing.JDialog;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JMenu;
import javax.swing.JMenuItem;
import javax.swing.JPanel;
import javax.swing.JTextArea;
import javax.swing.JTextField;
import java.awt.BorderLayout;
import java.awt.Font;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.io.BufferedReader;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLConnection;
import java.net.URLEncoder;
import java.util.Hashtable;
/**
* A capture plugin that captures data and stores it in a
* defined location. The location is specified as a plugin
* configuration option Capture.url and can be used in
* conjunction with the UploadServlet from the tools directory.
*
* Parametrize the plugin carefully:
* Capture.url should contain a unique URL can may have
* parameters for identifying the upload.
* Example: http://mg.mud.de/servlet/UpladServlet?id=12345
*
* The actually captured data will be appended as the parameter
* content.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: Capture.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class Capture extends Plugin
implements FilterPlugin, VisualPlugin, ActionListener {
// this enables or disables the compilation of menu entries
private final static boolean personalJava = false;
// for debugging output
private final static int debug = 0;
/** The remote storage URL */
protected Hashtable remoteUrlList = new Hashtable();
/** The plugin menu */
protected JMenu menu;
protected JDialog errorDialog;
protected JDialog fileDialog;
protected JDialog doneDialog;
/** Whether the capture is currently enabled or not */
protected boolean captureEnabled = false;
// menu entries and the viewing frame/textarea
private JMenuItem start, stop, clear;
private JFrame frame;
private JTextArea textArea;
private JTextField fileName;
/**
* Initialize the Capture plugin. This sets up the menu entries
* and registers the plugin on the bus.
*/
public Capture(final PluginBus bus, final String id) {
super(bus, id);
if (!personalJava) {
// set up viewing frame
frame = new JFrame("Java Telnet Applet: Captured Text");
frame.getContentPane().setLayout(new BorderLayout());
frame.getContentPane().add(textArea = new JTextArea(24, 80), BorderLayout.CENTER);
textArea.setFont(new Font("Monospaced", Font.PLAIN, 12));
frame.addWindowListener(new WindowAdapter() {
public void windowClosing(WindowEvent e) {
frame.setVisible(false);
}
});
frame.pack();
// an error dialogue, in case the upload fails
errorDialog = new JDialog(frame, "Error", true);
errorDialog.getContentPane().setLayout(new BorderLayout());
errorDialog.getContentPane().add(new JLabel("Cannot store data on remote server!"), BorderLayout.NORTH);
JPanel panel = new JPanel();
JButton button = new JButton("Close Dialog");
panel.add(button);
errorDialog.getContentPane().add(panel, BorderLayout.SOUTH);
button.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
errorDialog.setVisible(false);
}
});
// an error dialogue, in case the upload fails
doneDialog = new JDialog(frame, "Success", true);
doneDialog.getContentPane().setLayout(new BorderLayout());
doneDialog.getContentPane().add(new JLabel("Successfully saved data!"), BorderLayout.NORTH);
panel = new JPanel();
button = new JButton("Close Dialog");
panel.add(button);
doneDialog.getContentPane().add(panel, BorderLayout.SOUTH);
button.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
errorDialog.setVisible(false);
}
});
fileDialog = new JDialog(frame, "Enter File Name", true);
fileDialog.getContentPane().setLayout(new BorderLayout());
ActionListener saveFileListener = new ActionListener() {
public void actionPerformed(ActionEvent e) {
String params = (String) remoteUrlList.get("URL.file.params.orig");
params = params == null ? "" : params + "&";
remoteUrlList.put("URL.file.params", params + "file=" + URLEncoder.encode(fileName.getText()));
saveFile("URL.file");
fileDialog.setVisible(false);
}
};
panel = new JPanel();
panel.add(new JLabel("File Name: "));
panel.add(fileName = new JTextField(30));
fileName.addActionListener(saveFileListener);
fileDialog.getContentPane().add(panel, BorderLayout.CENTER);
panel = new JPanel();
panel.add(button = new JButton("Cancel"));
button.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
fileDialog.setVisible(false);
}
});
panel.add(button = new JButton("Save File"));
button.addActionListener(saveFileListener);
fileDialog.getContentPane().add(panel, BorderLayout.SOUTH);
fileDialog.pack();
// set up menu entries
menu = new JMenu("Capture");
start = new JMenuItem("Start");
start.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
if (debug > 0) System.out.println("Capture: start capturing");
captureEnabled = true;
start.setEnabled(false);
stop.setEnabled(true);
}
});
menu.add(start);
stop = new JMenuItem("Stop");
stop.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
if (debug > 0) System.out.println("Capture: stop capturing");
captureEnabled = false;
start.setEnabled(true);
stop.setEnabled(false);
}
});
stop.setEnabled(false);
menu.add(stop);
clear = new JMenuItem("Clear");
clear.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
if (debug > 0) System.out.println("Capture: cleared captured text");
textArea.setText("");
}
});
menu.add(clear);
menu.addSeparator();
JMenuItem view = new JMenuItem("View/Hide Text");
view.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
if (debug > 0) System.out.println("view/hide text: " + frame.isVisible());
if (frame.isVisible()) {
frame.setVisible(false);
frame.hide();
} else {
frame.setVisible(true);
frame.show();
}
}
});
menu.add(view);
} // !personalJava
// configure the remote URL
bus.registerPluginListener(new ConfigurationListener() {
public void setConfiguration(PluginConfig config) {
String tmp;
JMenuItem save = new JMenuItem("Save As File");
menu.add(save);
if ((tmp = config.getProperty("Capture", id, "file.url")) != null) {
try {
remoteUrlList.put("URL.file", new URL(tmp));
if ((tmp = config.getProperty("Capture", id, "file.params")) != null) {
remoteUrlList.put("URL.file.params.orig", tmp);
}
save.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
fileDialog.setVisible(true);
}
});
save.setActionCommand("URL.file");
} catch (MalformedURLException e) {
System.err.println("capture url invalid: " + e);
}
} else {
save.setEnabled(false);
}
int i = 1;
while ((tmp = config.getProperty("Capture", id, i + ".url")) != null) {
try {
String urlID = "URL." + i;
URL remoteURL = new URL(tmp);
remoteUrlList.put(urlID, remoteURL);
if ((tmp = config.getProperty("Capture", id, i + ".params")) != null) {
remoteUrlList.put(urlID + ".params", tmp);
}
// use name if applicable or URL
if ((tmp = config.getProperty("Capture", id, i + ".name")) != null) {
save = new JMenuItem("Save As " + tmp);
} else {
save = new JMenuItem("Save As " + remoteURL.toString());
}
// enable menu entry
save.setEnabled(true);
save.addActionListener(Capture.this);
save.setActionCommand(urlID);
menu.add(save);
// count up
i++;
} catch (MalformedURLException e) {
System.err.println("capture url invalid: " + e);
}
}
}
});
if (!personalJava) {
}
}
public void actionPerformed(ActionEvent e) {
String urlID = e.getActionCommand();
if (debug > 0)
System.err.println("Capture: storing text: "
+ urlID + ": "
+ remoteUrlList.get(urlID));
saveFile(urlID);
}
private void saveFile(String urlID) {
URL url = (URL) remoteUrlList.get(urlID);
try {
URLConnection urlConnection = url.openConnection();
DataOutputStream out;
BufferedReader in;
// Let the RTS know that we want to do output.
urlConnection.setDoInput(true);
// Let the RTS know that we want to do output.
urlConnection.setDoOutput(true);
// No caching, we want the real thing.
urlConnection.setUseCaches(false);
// Specify the content type.
urlConnection.setRequestProperty("Content-Type", "application/x-www-form-urlencoded");
// retrieve extra arguments
// Send POST output.
// send the data to the url receiver ...
out = new DataOutputStream(urlConnection.getOutputStream());
String content = (String) remoteUrlList.get(urlID + ".params");
content = (content == null ? "" : content + "&") + "content=" + URLEncoder.encode(textArea.getText());
if (debug > 0) System.err.println("Capture: " + content);
out.writeBytes(content);
out.flush();
out.close();
// retrieve response from the remote host and display it.
if (debug > 0) System.err.println("Capture: reading response");
in = new BufferedReader(new InputStreamReader(urlConnection.getInputStream()));
String str;
while (null != ((str = in.readLine()))) {
System.out.println("Capture: " + str);
}
in.close();
doneDialog.pack();
doneDialog.setVisible(true);
} catch (IOException ioe) {
System.err.println("Capture: cannot store text on remote server: " + url);
ioe.printStackTrace();
JTextArea errorMsg = new JTextArea(ioe.toString(), 5, 30);
errorMsg.setEditable(false);
errorDialog.add(errorMsg, BorderLayout.CENTER);
errorDialog.pack();
errorDialog.setVisible(true);
}
if (debug > 0) System.err.println("Capture: storage complete: " + url);
}
// this is where we get the data from (left side in plugins list)
protected FilterPlugin source;
/**
* The filter source is the plugin where Capture is connected to.
* In the list of plugins this is the one to the left.
* @param source the next plugin
*/
public void setFilterSource(FilterPlugin source) {
if (debug > 0) System.err.println("Capture: connected to: " + source);
this.source = source;
}
public FilterPlugin getFilterSource() {
return source;
}
/**
* Read data from the left side plugin, capture the content and
* pass it on to the next plugin which called this method.
* @param b the buffer to store data into
*/
public int read(byte[] b) throws IOException {
int size = source.read(b);
if (captureEnabled && size > 0) {
String tmp = new String(b, 0, size);
textArea.append(tmp);
}
return size;
}
/**
* Write data to the backend but also append it to the capture buffer.
* @param b the buffer with data to write
*/
public void write(byte[] b) throws IOException {
if (captureEnabled) {
textArea.append(new String(b));
}
source.write(b);
}
/**
* The Capture plugin has no visual component that is embedded in
* the JTA main frame, so this returns null.
* @return always null
*/
public JComponent getPluginVisual() {
return null;
}
/**
* The Capture menu for the menu bar as configured in the constructor.
* @return the drop down menu
*/
public JMenu getPluginMenu() {
return menu;
}
}
jta_2.6+dfsg.orig/de/mud/jta/plugin/Terminal.java 0000644 0001750 0001750 00000052545 10610772601 020445 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
import de.mud.jta.FilterPlugin;
import de.mud.jta.Plugin;
import de.mud.jta.PluginBus;
import de.mud.jta.PluginConfig;
import de.mud.jta.VisualTransferPlugin;
import de.mud.jta.event.ConfigurationListener;
import de.mud.jta.event.FocusStatus;
import de.mud.jta.event.LocalEchoListener;
import de.mud.jta.event.OnlineStatusListener;
import de.mud.jta.event.ReturnFocusListener;
import de.mud.jta.event.SoundRequest;
import de.mud.jta.event.TelnetCommandRequest;
import de.mud.jta.event.SetWindowSizeRequest;
import de.mud.jta.event.TerminalTypeListener;
import de.mud.jta.event.WindowSizeListener;
import de.mud.terminal.vt320;
import de.mud.terminal.SwingTerminal;
import javax.swing.JComponent;
import javax.swing.JMenu;
import javax.swing.JMenuItem;
import javax.swing.JPanel;
import javax.swing.JScrollBar;
import javax.swing.JFrame;
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Container;
import java.awt.Cursor;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.datatransfer.Clipboard;
import java.awt.datatransfer.ClipboardOwner;
import java.awt.datatransfer.DataFlavor;
import java.awt.datatransfer.StringSelection;
import java.awt.datatransfer.Transferable;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.FocusEvent;
import java.awt.event.FocusListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.Enumeration;
import java.util.Hashtable;
import java.util.Properties;
/**
* The terminal plugin represents the actual terminal where the
* data will be displayed and the gets the keyboard input to sent
* back to the remote host.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: Terminal.java 510 2005-10-28 06:46:44Z marcus $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class Terminal extends Plugin
implements FilterPlugin, VisualTransferPlugin, ClipboardOwner, Runnable {
private final static boolean personalJava = false;
private final static int debug = 0;
/** holds the actual terminal emulation */
protected SwingTerminal terminal;
protected vt320 emulation;
/**
* The default encoding is ISO 8859-1 (western).
* However, as you see the value is set to latin1 which is a value that
* is not even documented and thus incorrect, but it forces the default
* behaviour for western encodings. The correct value does not work in
* most available browsers.
*/
protected String encoding = "latin1"; // "ISO8859_1";
/** if we have a url to an audioclip use it as ping */
protected SoundRequest audioBeep = null;
/** the terminal panel that is displayed on-screen */
protected JPanel tPanel;
/** holds the terminal menu */
protected JMenu menu;
private Thread reader = null;
private Hashtable colors = new Hashtable();
private boolean localecho_overridden = false;
/** Access to the system clipboard */
private Clipboard clipboard = null;
private Color codeToColor(String code) {
if (colors.get(code) != null)
return (Color) colors.get(code);
else
try {
if (Color.getColor(code) != null)
return Color.getColor(code);
else
return Color.decode(code);
} catch (Exception e) {
try {
// try one last time
return Color.decode(code);
} catch(Exception ex) {
// ignore
}
error("ignoring unknown color code: " + code);
}
return null;
}
/**
* Create a new terminal plugin and initialize the terminal emulation.
*/
public Terminal(final PluginBus bus, final String id) {
super(bus, id);
// create the terminal emulation
emulation = new vt320() {
public void write(byte[] b) {
try {
Terminal.this.write(b);
} catch (IOException e) {
reader = null;
}
}
// provide audio feedback if that is configured
public void beep() {
if (audioBeep != null) bus.broadcast(audioBeep);
}
public void sendTelnetCommand(byte cmd) {
bus.broadcast(new TelnetCommandRequest(cmd));
}
public void setWindowSize(int c, int r) {
bus.broadcast(new SetWindowSizeRequest(c,r));
}
};
// create terminal
terminal = new SwingTerminal(emulation);
// initialize colors
colors.put("black", Color.black);
colors.put("red", Color.red);
colors.put("green", Color.green);
colors.put("yellow", Color.yellow);
colors.put("blue", Color.blue);
colors.put("magenta", Color.magenta);
colors.put("orange", Color.orange);
colors.put("pink", Color.pink);
colors.put("cyan", Color.cyan);
colors.put("white", Color.white);
colors.put("gray", Color.gray);
colors.put("darkgray", Color.darkGray);
if (!personalJava) {
menu = new JMenu("Terminal");
JMenuItem item;
JMenu fgm = new JMenu("Foreground");
JMenu bgm = new JMenu("Background");
Enumeration cols = colors.keys();
ActionListener fgl = new ActionListener() {
public void actionPerformed(ActionEvent e) {
terminal.setForeground((Color) colors.get(e.getActionCommand()));
tPanel.repaint();
}
};
ActionListener bgl = new ActionListener() {
public void actionPerformed(ActionEvent e) {
terminal.setBackground((Color) colors.get(e.getActionCommand()));
tPanel.repaint();
}
};
while (cols.hasMoreElements()) {
String color = (String) cols.nextElement();
fgm.add(item = new JMenuItem(color));
item.addActionListener(fgl);
bgm.add(item = new JMenuItem(color));
item.addActionListener(bgl);
}
menu.add(fgm);
menu.add(bgm);
menu.add(item = new JMenuItem("Smaller Font"));
item.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
Font font = terminal.getFont();
terminal.setFont(new Font(font.getName(),
font.getStyle(), font.getSize() - 1));
if (tPanel.getParent() != null) {
Container parent = tPanel;
do {
parent = parent.getParent();
} while(parent != null && !(parent instanceof JFrame));
if (parent instanceof JFrame)
((java.awt.Frame) parent).pack();
tPanel.getParent().doLayout();
tPanel.getParent().validate();
}
}
});
menu.add(item = new JMenuItem("Larger Font"));
item.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
Font font = terminal.getFont();
terminal.setFont(new Font(font.getName(),
font.getStyle(), font.getSize() + 1));
if (tPanel.getParent() != null) {
Container parent = tPanel;
do {
parent = parent.getParent();
} while(parent != null && !(parent instanceof JFrame));
if (parent instanceof JFrame)
((java.awt.Frame) parent).pack();
tPanel.getParent().doLayout();
tPanel.getParent().validate();
}
}
});
menu.add(item = new JMenuItem("Buffer +50"));
item.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
emulation.setBufferSize(emulation.getBufferSize() + 50);
}
});
menu.add(item = new JMenuItem("Buffer -50"));
item.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
emulation.setBufferSize(emulation.getBufferSize() - 50);
}
});
menu.addSeparator();
menu.add(item = new JMenuItem("Reset Terminal"));
item.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
emulation.reset();
}
});
} // !personalJava
// the container for our terminal must use double-buffering
// or at least reduce flicker by overloading update()
tPanel = new JPanel(new BorderLayout()) {
// reduce flickering
public void update(java.awt.Graphics g) {
paint(g);
}
// we don't want to print the container, just the terminal contents
public void print(java.awt.Graphics g) {
terminal.print(g);
}
};
tPanel.add("Center", terminal);
terminal.addFocusListener(new FocusListener() {
public void focusGained(FocusEvent evt) {
if (debug > 0)
System.err.println("Terminal: focus gained");
terminal.setCursor(Cursor.getPredefinedCursor(Cursor.TEXT_CURSOR));
bus.broadcast(new FocusStatus(Terminal.this, evt));
}
public void focusLost(FocusEvent evt) {
if (debug > 0)
System.err.println("Terminal: focus lost");
terminal.setCursor(Cursor.getDefaultCursor());
bus.broadcast(new FocusStatus(Terminal.this, evt));
}
});
// get a reference to the system clipboard.
try {
clipboard = tPanel.getToolkit().getSystemClipboard();
System.out.println("Got the clipboard reference ok - copy & paste enabled");
} catch(Exception ex) {
System.out.println("Failed to get clipboard - copy and paste will not work");
/* ex.printStackTrace(); */
}
//*******************************
//code to handle copy and paste
//from embeded terminal
//*******************************
terminal.addMouseListener(new MouseListener() {
public void mouseClicked(MouseEvent me) {
//make sure it only does the paste on button2(right mouse)
if (me.getButton() == me.BUTTON3 && clipboard != null) {
paste(clipboard);
}
}
public void mouseExited(MouseEvent arg0) {}
public void mousePressed(MouseEvent arg0) {
// System.out.println(">>>>MOUSE pressed");
}
public void mouseReleased(MouseEvent me) {
//make sure it only does the copy on button 1 (left mouse)
//System.out.println(">>>>MOUSE RELEASED");
if (me.getButton() == me.BUTTON1 && clipboard != null) {
String selection = terminal.getSelection();
// System.out.println(">>>>SELECTION = " + selection);
if (selection != null && selection.trim().length() > 0){
copy(clipboard);
}
} else {
//not left mouse
// System.out.println("NOT BUTTON 1(left mouse): " + me.getButton());
}
}
public void mouseEntered(MouseEvent arg0) {}
});
// register an online status listener
bus.registerPluginListener(new OnlineStatusListener() {
public void online() {
if (debug > 0) System.err.println("Terminal: online " + reader);
if (reader == null) {
reader = new Thread(Terminal.this);
reader.start();
}
}
public void offline() {
if (debug > 0) System.err.println("Terminal: offline");
if (reader != null)
reader = null;
}
});
bus.registerPluginListener(new TerminalTypeListener() {
public String getTerminalType() {
return emulation.getTerminalID();
}
});
bus.registerPluginListener(new WindowSizeListener() {
public Dimension getWindowSize() {
return new Dimension(emulation.getColumns(), emulation.getRows());
}
});
bus.registerPluginListener(new LocalEchoListener() {
public void setLocalEcho(boolean echo) {
if (!localecho_overridden)
emulation.setLocalEcho(echo);
}
});
bus.registerPluginListener(new ConfigurationListener() {
public void setConfiguration(PluginConfig config) {
configure(config);
}
});
bus.registerPluginListener(new ReturnFocusListener() {
public void returnFocus() {
terminal.requestFocus();
}
});
}
private void configure(PluginConfig cfg) {
String tmp;
if ((tmp = cfg.getProperty("Terminal", id, "foreground")) != null)
terminal.setForeground(Color.decode(tmp));
if ((tmp = cfg.getProperty("Terminal", id, "background")) != null)
terminal.setBackground(Color.decode(tmp));
if ((tmp = cfg.getProperty("Terminal", id, "print.color")) != null)
try {
terminal.setColorPrinting(Boolean.valueOf(tmp).booleanValue());
} catch (Exception e) {
error("Terminal.color.print: must be either true or false, not " + tmp);
}
System.err.print("colorSet: ");
if ((tmp = cfg.getProperty("Terminal", id, "colorSet")) != null) {
System.err.println(tmp);
Properties colorSet = new Properties();
try {
colorSet.load(getClass().getResourceAsStream(tmp));
} catch (Exception e) {
try {
colorSet.load(new URL(tmp).openStream());
} catch (Exception ue) {
error("cannot find colorSet: " + tmp);
error("resource access failed: " + e);
error("URL access failed: " + ue);
colorSet = null;
}
}
if (colorSet != null) {
Color set[] = terminal.getColorSet();
Color color = null;
for (int i = 0; i < 8; i++) {
if ((tmp = colorSet.getProperty("color" + i)) != null &&
(color = codeToColor(tmp)) != null) {
set[i] = color;
}
}
// special color for bold
if ((tmp = colorSet.getProperty("bold")) != null &&
(color = codeToColor(tmp)) != null) {
set[SwingTerminal.COLOR_BOLD] = color;
}
// special color for invert
if ((tmp = colorSet.getProperty("invert")) != null &&
(color = codeToColor(tmp)) != null) {
set[SwingTerminal.COLOR_INVERT] = color;
}
terminal.setColorSet(set);
}
}
String cFG = cfg.getProperty("Terminal", id, "cursor.foreground");
String cBG = cfg.getProperty("Terminal", id, "cursor.background");
if (cFG != null || cBG != null)
try {
Color fg = (cFG == null ?
terminal.getBackground() :
(Color.getColor(cFG) != null ? Color.getColor(cFG):Color.decode(cFG)));
Color bg = (cBG == null ?
terminal.getForeground() :
(Color.getColor(cBG) != null ? Color.getColor(cBG):Color.decode(cBG)));
terminal.setCursorColors(fg, bg);
} catch (Exception e) {
error("ignoring unknown cursor color code: " + tmp);
}
if ((tmp = cfg.getProperty("Terminal", id, "border")) != null) {
String size = tmp;
boolean raised = false;
if ((tmp = cfg.getProperty("Terminal", id, "borderRaised")) != null)
raised = Boolean.valueOf(tmp).booleanValue();
terminal.setBorder(Integer.parseInt(size), raised);
}
if ((tmp = cfg.getProperty("Terminal", id, "localecho")) != null) {
emulation.setLocalEcho(Boolean.valueOf(tmp).booleanValue());
localecho_overridden = true;
}
if ((tmp = cfg.getProperty("Terminal", id, "scrollBar")) != null &&
!personalJava) {
String direction = tmp;
if (!direction.equals("none")) {
if (!direction.equals("East") && !direction.equals("West"))
direction = "East";
JScrollBar scrollBar = new JScrollBar();
tPanel.add(direction, scrollBar);
terminal.setScrollbar(scrollBar);
}
}
if ((tmp = cfg.getProperty("Terminal", id, "id")) != null)
emulation.setTerminalID(tmp);
if ((tmp = cfg.getProperty("Terminal", id, "answerback")) != null)
emulation.setAnswerBack(tmp);
if ((tmp = cfg.getProperty("Terminal", id, "buffer")) != null)
emulation.setBufferSize(Integer.parseInt(tmp));
if ((tmp = cfg.getProperty("Terminal", id, "size")) != null)
try {
int idx = tmp.indexOf(',');
int width = Integer.parseInt(tmp.substring(1, idx).trim());
int height = Integer.parseInt(tmp.substring(idx + 1, tmp.length() - 1).trim());
emulation.setScreenSize(width, height, false);
} catch (Exception e) {
error("screen size is wrong: " + tmp);
error("error: " + e);
}
if ((tmp = cfg.getProperty("Terminal", id, "resize")) != null)
if (tmp.equals("font"))
terminal.setResizeStrategy(SwingTerminal.RESIZE_FONT);
else if (tmp.equals("screen"))
terminal.setResizeStrategy(SwingTerminal.RESIZE_SCREEN);
else
terminal.setResizeStrategy(SwingTerminal.RESIZE_NONE);
if ((tmp = cfg.getProperty("Terminal", id, "font")) != null) {
String font = tmp;
int style = Font.PLAIN, fsize = 12;
if ((tmp = cfg.getProperty("Terminal", id, "fontSize")) != null)
fsize = Integer.parseInt(tmp);
String fontStyle = cfg.getProperty("Terminal", id, "fontStyle");
if (fontStyle == null || fontStyle.equals("plain"))
style = Font.PLAIN;
else if (fontStyle.equals("bold"))
style = Font.BOLD;
else if (fontStyle.equals("italic"))
style = Font.ITALIC;
else if (fontStyle.equals("bold+italic"))
style = Font.BOLD | Font.ITALIC;
terminal.setFont(new Font(font, style, fsize));
}
if ((tmp = cfg.getProperty("Terminal", id, "keyCodes")) != null) {
Properties keyCodes = new Properties();
try {
keyCodes.load(getClass().getResourceAsStream(tmp));
} catch (Exception e) {
try {
keyCodes.load(new URL(tmp).openStream());
} catch (Exception ue) {
error("cannot find keyCodes: " + tmp);
error("resource access failed: " + e);
error("URL access failed: " + ue);
keyCodes = null;
}
}
// set the key codes if we got the properties
if (keyCodes != null)
emulation.setKeyCodes(keyCodes);
}
if ((tmp = cfg.getProperty("Terminal", id, "VMS")) != null)
emulation.setVMS((Boolean.valueOf(tmp)).booleanValue());
if ((tmp = cfg.getProperty("Terminal", id, "IBM")) != null)
emulation.setIBMCharset((Boolean.valueOf(tmp)).booleanValue());
if ((tmp = cfg.getProperty("Terminal", id, "encoding")) != null)
encoding = tmp;
if ((tmp = cfg.getProperty("Terminal", id, "beep")) != null)
try {
audioBeep = new SoundRequest(new URL(tmp));
} catch (MalformedURLException e) {
error("incorrect URL for audio ping: " + e);
}
tPanel.setBackground(terminal.getBackground());
}
/**
* Continuously read from our back end and display the data on screen.
*/
public void run() {
byte[] b = new byte[256];
int n = 0;
while (n >= 0)
try {
n = read(b);
if (debug > 1 && n > 0)
System.err.println("Terminal: \"" + (new String(b, 0, n, encoding)) + "\"");
if (n > 0) emulation.putString(new String(b, 0, n, encoding));
tPanel.repaint();
} catch (IOException e) {
reader = null;
break;
}
}
protected FilterPlugin source;
public void setFilterSource(FilterPlugin source) {
if (debug > 0) System.err.println("Terminal: connected to: " + source);
this.source = source;
}
public FilterPlugin getFilterSource() {
return source;
}
public int read(byte[] b) throws IOException {
return source.read(b);
}
public void write(byte[] b) throws IOException {
source.write(b);
}
public JComponent getPluginVisual() {
return tPanel;
}
public JMenu getPluginMenu() {
return menu;
}
public void copy(Clipboard clipboard) {
String data = terminal.getSelection();
// check due to a bug in the hotspot vm
if (data == null) return;
StringSelection selection = new StringSelection(data);
clipboard.setContents(selection, this);
}
public void paste(Clipboard clipboard) {
if (clipboard == null) return;
Transferable t = clipboard.getContents(this);
try {
/*
InputStream is =
(InputStream)t.getTransferData(DataFlavor.plainTextFlavor);
if(debug > 0)
System.out.println("Clipboard: available: "+is.available());
byte buffer[] = new byte[is.available()];
is.read(buffer);
is.close();
*/
byte buffer[] =
((String) t.getTransferData(DataFlavor.stringFlavor)).getBytes();
try {
write(buffer);
} catch (IOException e) {
reader = null;
}
} catch (Exception e) {
// ignore any clipboard errors
if (debug > 0) e.printStackTrace();
}
}
public void lostOwnership(Clipboard clipboard, Transferable contents) {
terminal.clearSelection();
}
}
jta_2.6+dfsg.orig/de/mud/jta/plugin/Status.java 0000644 0001750 0001750 00000015021 10610772601 020141 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
import de.mud.jta.Plugin;
import de.mud.jta.PluginBus;
import de.mud.jta.PluginConfig;
import de.mud.jta.VisualPlugin;
import de.mud.jta.event.ConfigurationListener;
import de.mud.jta.event.OnlineStatusListener;
import de.mud.jta.event.SocketListener;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JComponent;
import javax.swing.JMenu;
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Font;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.URL;
import java.util.Hashtable;
/**
* A simple plugin showing the current status of the application whether
* it is online or not.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: Status.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class Status extends Plugin implements VisualPlugin, Runnable {
private final static int debug = 0;
private JLabel status;
private JLabel host;
private JPanel sPanel;
private String address, port;
private String infoURL;
private int interval;
private Thread infoThread;
private Hashtable ports = new Hashtable();
public Status(PluginBus bus, final String id) {
super(bus, id);
// setup the info
bus.registerPluginListener(new ConfigurationListener() {
public void setConfiguration(PluginConfig config) {
infoURL = config.getProperty("Status", id, "info");
if (infoURL != null)
host.setAlignmentX(JLabel.CENTER);
String tmp;
if ((tmp = config.getProperty("Status", id, "font")) != null) {
String font = tmp;
int style = Font.PLAIN, fsize = 12;
if ((tmp = config.getProperty("Status", id, "fontSize")) != null)
fsize = Integer.parseInt(tmp);
String fontStyle = config.getProperty("Status", id, "fontStyle");
if (fontStyle == null || fontStyle.equals("plain"))
style = Font.PLAIN;
else if (fontStyle.equals("bold"))
style = Font.BOLD;
else if (fontStyle.equals("italic"))
style = Font.ITALIC;
else if (fontStyle.equals("bold+italic"))
style = Font.BOLD | Font.ITALIC;
host.setFont(new Font(font, style, fsize));
}
if ((tmp = config.getProperty("Status", id, "foreground")) != null)
host.setForeground(Color.decode(tmp));
if ((tmp = config.getProperty("Status", id, "background")) != null)
host.setBackground(Color.decode(tmp));
if (config.getProperty("Status", id, "interval") != null) {
try {
interval = Integer.parseInt(
config.getProperty("Status", id, "interval"));
infoThread = new Thread(Status.this);
infoThread.start();
} catch (NumberFormatException e) {
Status.this.error("interval is not a number");
}
}
}
});
// fill port hashtable
ports.put("22", "ssh");
ports.put("23", "telnet");
ports.put("25", "smtp");
sPanel = new JPanel(new BorderLayout());
host = new JLabel("Not connected.", JLabel.LEFT);
bus.registerPluginListener(new SocketListener() {
public void connect(String addr, int p) {
address = addr;
if (address == null || address.length() == 0)
address = "";
if (ports.get("" + p) != null)
port = (String) ports.get("" + p);
else
port = "" + p;
if (infoURL == null)
host.setText("Trying " + address + " " + port + " ...");
}
public void disconnect() {
if (infoURL == null)
host.setText("Not connected.");
}
});
sPanel.add("Center", host);
status = new JLabel("offline", JLabel.CENTER);
bus.registerPluginListener(new OnlineStatusListener() {
public void online() {
status.setText("online");
status.setForeground(Color.green);
if (infoURL == null)
host.setText("Connected to " + address + " " + port);
status.repaint();
}
public void offline() {
status.setText("offline");
status.setForeground(Color.red);
if (infoURL == null)
host.setText("Not connected.");
status.repaint();
}
});
sPanel.add("East", status);
}
public void run() {
URL url = null;
try {
url = new URL(infoURL);
} catch (Exception e) {
error("infoURL is not valid: " + e);
infoURL = null;
return;
}
while (url != null && infoThread != null) {
try {
BufferedReader content =
new BufferedReader(new InputStreamReader(url.openStream()));
try {
String line;
while ((line = content.readLine()) != null) {
if (line.startsWith("#")) {
String color = line.substring(1, 7);
line = line.substring(8);
host.setForeground(Color.decode("#" + color));
}
host.setText(line);
infoThread.sleep(10 * interval);
}
} catch (IOException e) {
error("error while loading info ...");
}
infoThread.sleep(100 * interval);
} catch (Exception e) {
error("error retrieving info content: " + e);
e.printStackTrace();
host.setForeground(Color.red);
host.setText("error retrieving info content");
infoURL = null;
return;
}
}
}
public JComponent getPluginVisual() {
return sPanel;
}
public JMenu getPluginMenu() {
return null;
}
}
jta_2.6+dfsg.orig/de/mud/jta/plugin/SSH.java 0000644 0001750 0001750 00000020202 10610772601 017310 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
import de.mud.jta.Plugin;
import de.mud.jta.FilterPlugin;
import de.mud.jta.PluginBus;
import de.mud.jta.PluginConfig;
import de.mud.jta.VisualPlugin;
import de.mud.jta.event.ConfigurationListener;
import de.mud.jta.event.SetWindowSizeListener;
import de.mud.jta.event.OnlineStatusListener;
import de.mud.jta.event.TerminalTypeRequest;
import de.mud.jta.event.WindowSizeRequest;
import de.mud.jta.event.LocalEchoRequest;
import de.mud.jta.event.SocketRequest;
import de.mud.ssh.SshIO;
import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;
import java.io.IOException;
/**
* Secure Shell plugin for the JTA. This is a plugin
* to be used instead of Telnet for secure remote terminal sessions over
* insecure networks.
* Take a look at the package de.mud.ssh for further information
* about ssh or look at the official ssh homepage:
* http://www.ssh.fi/.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: SSH.java 513 2005-12-19 07:59:45Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class SSH extends Plugin implements FilterPlugin, VisualPlugin {
protected FilterPlugin source;
protected SshIO handler;
protected String user, pass;
private final static int debug = 0;
private boolean auth = false;
/**
* Create a new ssh plugin.
*/
public SSH(final PluginBus bus, final String id) {
super(bus, id);
// create a new telnet protocol handler
handler = new SshIO() {
/** get the current terminal type */
public String getTerminalType() {
return (String)bus.broadcast(new TerminalTypeRequest());
}
/** get the current window size */
public Dimension getWindowSize() {
return (Dimension)bus.broadcast(new WindowSizeRequest());
}
/** notify about local echo */
public void setLocalEcho(boolean echo) {
bus.broadcast(new LocalEchoRequest(echo));
}
/** write data to our back end */
public void write(byte[] b) throws IOException {
source.write(b);
}
};
bus.registerPluginListener(new ConfigurationListener() {
public void setConfiguration(PluginConfig config) {
user = config.getProperty("SSH", id, "user");
pass = config.getProperty("SSH", id, "password");
}
});
bus.registerPluginListener(new SetWindowSizeListener() {
public void setWindowSize(int columns, int rows) {
try {
handler.setWindowSize(columns,rows);
} catch (java.io.IOException e) {
System.err.println("IO Exception in set window size");
}
}
});
// reset the protocol handler just in case :-)
bus.registerPluginListener(new OnlineStatusListener() {
public void online() {
if(pass == null) {
final Frame frame = new Frame("SSH User Authentication");
Panel panel = new Panel(new GridLayout(3,1));
panel.add(new Label("SSH Authorization required"));
frame.add("North", panel);
panel = new Panel(new GridLayout(2,2));
final TextField login = new TextField(user, 10);
final TextField passw = new TextField(10);
login.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
passw.requestFocus();
}
});
passw.setEchoChar('*');
panel.add(new Label("User name")); panel.add(login);
panel.add(new Label("Password")); panel.add(passw);
frame.add("Center", panel);
panel = new Panel();
Button cancel = new Button("Cancel");
Button ok = new Button("Login");
ActionListener enter = new ActionListener() {
public void actionPerformed(ActionEvent evt) {
handler.setLogin(login.getText());
handler.setPassword(passw.getText());
frame.dispose();
auth = true;
}
};
ok.addActionListener(enter);
passw.addActionListener(enter);
cancel.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
frame.dispose();
}
});
panel.add(cancel);
panel.add(ok);
frame.add("South", panel);
frame.pack();
frame.show();
frame.setLocation(frame.getToolkit().getScreenSize().width/2 -
frame.getSize().width/2,
frame.getToolkit().getScreenSize().height/2 -
frame.getSize().height/2);
if(user != null) {
passw.requestFocus();
}
} else {
error(user+":"+pass);
handler.setLogin(user);
handler.setPassword(pass);
auth = true;
}
}
public void offline() {
handler.disconnect();
auth=false;
bus.broadcast(new SocketRequest());
}
});
}
public void setFilterSource(FilterPlugin source) {
if(debug>0) System.err.println("ssh: connected to: "+source);
this.source = source;
}
public FilterPlugin getFilterSource() {
return source;
}
private byte buffer[];
private int pos;
/**
* Read data from the backend and decrypt it. This is a buffering read
* as the encrypted information is usually smaller than its decrypted
* pendant. So it will not read from the backend as long as there is
* data in the buffer.
* @param b the buffer where to read the decrypted data in
* @return the amount of bytes actually read.
*/
public int read(byte[] b) throws IOException {
// we don't want to read from the pipeline without authorization
while(!auth) try {
Thread.sleep(1000);
} catch(InterruptedException e) {
e.printStackTrace();
}
// Empty the buffer before we do anything else
if(buffer != null) {
int amount = ((buffer.length - pos) <= b.length) ?
buffer.length - pos : b.length;
System.arraycopy(buffer, pos, b, 0, amount);
if(pos + amount < buffer.length) {
pos += amount;
} else
buffer = null;
return amount;
}
// now that the buffer is empty let's read more data and decrypt it
int n = source.read(b);
if(n > 0) {
byte[] tmp = new byte[n];
System.arraycopy(b, 0, tmp, 0, n);
pos = 0;
buffer = handler.handleSSH(tmp);
if(debug > 0 && buffer != null && buffer.length > 0)
System.err.println("ssh: "+buffer);
if(buffer != null && buffer.length > 0) {
if(debug > 0)
System.err.println("ssh: incoming="+n+" now="+buffer.length);
int amount = buffer.length <= b.length ? buffer.length : b.length;
System.arraycopy(buffer, 0, b, 0, amount);
pos = n = amount;
if(amount == buffer.length) {
buffer = null;
pos = 0;
}
} else
return 0;
}
return n;
}
/**
* Write data to the back end. This hands the data over to the ssh
* protocol handler who encrypts the information and writes it to
* the actual back end pipe.
* @param b the unencrypted data to be encrypted and sent
*/
public void write(byte[] b) throws IOException {
// no write until authorization is done
if(!auth) return;
for (int i=0;i \r */
b[i] = 13;
break;
}
}
handler.sendData(new String(b));
}
public JComponent getPluginVisual() {
return null;
}
public JMenu getPluginMenu() {
return null;
}
}
jta_2.6+dfsg.orig/de/mud/jta/plugin/Sink.java 0000644 0001750 0001750 00000010060 10610772601 017560 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
import de.mud.jta.Plugin;
import de.mud.jta.PluginConfig;
import de.mud.jta.FilterPlugin;
import de.mud.jta.VisualTransferPlugin;
import de.mud.jta.PluginBus;
import de.mud.jta.event.ConfigurationListener;
import de.mud.jta.event.OnlineStatusListener;
import de.mud.jta.event.TerminalTypeListener;
import de.mud.jta.event.WindowSizeListener;
import de.mud.jta.event.LocalEchoListener;
import de.mud.jta.event.FocusStatus;
import de.mud.jta.event.ReturnFocusListener;
import de.mud.jta.event.AppletListener;
import de.mud.jta.event.SoundRequest;
import de.mud.jta.event.TelnetCommandRequest;
import java.awt.Component;
import java.awt.Panel;
import java.awt.BorderLayout;
import java.awt.Menu;
import java.awt.MenuItem;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.Color;
import java.awt.Scrollbar;
import java.awt.Cursor;
import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;
import java.awt.event.FocusListener;
import java.awt.event.FocusEvent;
import java.awt.datatransfer.Clipboard;
import java.awt.datatransfer.StringSelection;
import java.awt.datatransfer.ClipboardOwner;
import java.awt.datatransfer.Transferable;
import java.awt.datatransfer.DataFlavor;
import java.io.IOException;
import java.io.InputStream;
import java.net.URL;
import java.net.MalformedURLException;
import java.util.Properties;
import java.util.Hashtable;
import java.util.Enumeration;
/**
* The terminal plugin represents the actual terminal where the
* data will be displayed and the gets the keyboard input to sent
* back to the remote host.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: Sink.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class Sink extends Plugin
implements FilterPlugin, Runnable {
private final static int debug = 0;
private Thread reader = null;
public Sink(final PluginBus bus, final String id) {
super(bus, id);
// register an online status listener
bus.registerPluginListener(new OnlineStatusListener() {
public void online() {
if(debug > 0) System.err.println("Terminal: online "+reader);
if(reader == null) {
reader = new Thread();
reader.start();
}
}
public void offline() {
if(debug > 0) System.err.println("Terminal: offline");
if(reader != null)
reader = null;
}
});
}
/**
* Continuously read from our back end and drop the data.
*/
public void run() {
byte[] t, b = new byte[256];
int n = 0;
while(n >= 0) try {
n = read(b);
/* drop the bytes into the sink :) */
} catch(IOException e) {
reader = null;
break;
}
}
protected FilterPlugin source;
public void setFilterSource(FilterPlugin source) {
if(debug > 0) System.err.println("Terminal: connected to: "+source);
this.source = source;
}
public FilterPlugin getFilterSource() {
return source;
}
public int read(byte[] b) throws IOException {
return source.read(b);
}
public void write(byte[] b) throws IOException {
source.write(b);
}
}
jta_2.6+dfsg.orig/de/mud/jta/plugin/Timeout.java 0000644 0001750 0001750 00000011615 10610772601 020311 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
import de.mud.jta.Plugin;
import de.mud.jta.FilterPlugin;
import de.mud.jta.PluginBus;
import de.mud.jta.PluginConfig;
import de.mud.jta.event.ConfigurationListener;
import de.mud.jta.event.SocketListener;
import de.mud.jta.event.SocketRequest;
import java.io.IOException;
/**
* The timeout plugin looks at the incoming and outgoing data stream and
* tries to close the connection gracefully if the timeout occured or if
* not graceful exit command was configured simply closed the connection.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: Timeout.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class Timeout extends Plugin
implements FilterPlugin, SocketListener, Runnable {
private final static int debug = 0;
protected int timeout = 0;
protected String timeoutCommand = null;
protected String timeoutWarning = null;
protected Thread timeoutThread = null;
private PluginBus pluginBus;
/**
* Create the new timeout plugin.
*/
public Timeout(final PluginBus bus, final String id) {
super(bus, id);
// register socket listener
bus.registerPluginListener(this);
bus.registerPluginListener(new ConfigurationListener() {
public void setConfiguration(PluginConfig config) {
String tos = config.getProperty("Timeout", id, "seconds");
if(tos != null) {
try {
timeout = Integer.parseInt(tos);
} catch(Exception e) {
Timeout.this.error("timeout ("+timeout+") "
+"is not an integer, timeout disabled");
}
timeoutCommand =
config.getProperty("Timeout", id, "command");
timeoutWarning =
config.getProperty("Timeout", id, "warning");
}
}
});
pluginBus = bus;
}
/**
* Sleep for the timeout beeing. The thread gets interrupted if data
* is transmitted and will shutdown the connection as soon as the
* timeout wakes up normally.
*/
public void run() {
boolean ok = false;
// loop around until the thread is kicked down the stream ...
while(timeoutThread != null) {
try {
ok = false;
timeoutThread.sleep(1000*timeout);
} catch(InterruptedException e) {
ok = true;
}
// if the timeout finished sucessfully close the connection
if(!ok) {
error("data connection timeout, shutting down");
// first try it gracefully by sending the configured exit command
if(timeoutCommand != null) {
error("sending graceful exit command ...");
try {
write(timeoutCommand.getBytes());
} catch(IOException e) {
error("could not send exit command");
}
timeoutThread = null;
final Thread grace = new Thread(new Runnable() {
public void run() {
try {
Thread.currentThread().sleep(1000*timeout);
Timeout.this.pluginBus.broadcast(new SocketRequest());
} catch(InterruptedException e) {
// ignore exception
}
}
});
grace.start();
} else // if not graceful exit exists, be rude
bus.broadcast(new SocketRequest());
}
}
}
/** Start the timeout countdown. */
public void connect(String host, int port) throws IOException {
if(timeout > 0) {
timeoutThread = new Thread(Timeout.this);
timeoutThread.start();
}
}
/** Stop the timeout */
public void disconnect() throws IOException {
if(timeoutThread != null) {
Thread tmp = timeoutThread;
timeoutThread = null;
tmp.interrupt();
}
}
FilterPlugin source;
public void setFilterSource(FilterPlugin plugin) {
source = plugin;
}
public FilterPlugin getFilterSource() {
return source;
}
public int read(byte[] b) throws IOException {
int n = source.read(b);
if(n > 0 && timeoutThread != null) timeoutThread.interrupt();
return n;
}
public void write(byte[] b) throws IOException {
source.write(b);
if(timeoutThread != null) timeoutThread.interrupt();
}
}
jta_2.6+dfsg.orig/de/mud/jta/plugin/URLFilter.java 0000644 0001750 0001750 00000021054 10610772601 020471 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
import de.mud.jta.FilterPlugin;
import de.mud.jta.Plugin;
import de.mud.jta.PluginBus;
import de.mud.jta.PluginConfig;
import de.mud.jta.VisualPlugin;
import de.mud.jta.event.AppletListener;
import de.mud.jta.event.ConfigurationListener;
import javax.swing.JApplet;
import javax.swing.JButton;
import javax.swing.JComponent;
import javax.swing.JLabel;
import javax.swing.JList;
import javax.swing.JMenu;
import javax.swing.JPanel;
import javax.swing.ListSelectionModel;
import javax.swing.event.ListSelectionEvent;
import javax.swing.event.ListSelectionListener;
import java.applet.AppletContext;
import java.awt.BorderLayout;
import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.PipedInputStream;
import java.io.PipedOutputStream;
import java.io.StreamTokenizer;
import java.net.URL;
import java.util.Vector;
/**
*
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: URLFilter.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class URLFilter extends Plugin
implements FilterPlugin, VisualPlugin, Runnable {
/** debugging level */
private final static int debug = 0;
/* contains the recognized protocols */
protected Vector protocols = new Vector();
protected JList urlList = new JList();
protected JPanel urlPanel;
protected JMenu urlMenu;
protected PipedInputStream pin;
protected PipedOutputStream pout;
protected AppletContext context;
/**
* Create a new scripting plugin.
*/
public URLFilter(PluginBus bus, final String id) {
super(bus, id);
urlPanel = new JPanel(new BorderLayout());
urlList.setVisibleRowCount(4);
urlList.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
urlList.addListSelectionListener(new ListSelectionListener() {
public void valueChanged(ListSelectionEvent e) {
showURL((String) ((JList) e.getSource()).getSelectedValue());
}
});
urlPanel.add("Center", urlList);
JPanel p = new JPanel(new GridLayout(3, 1));
JButton b = new JButton("Clear List");
b.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
urlCache.removeAllElements();
urlList.removeAll();
}
});
p.add(b);
b = new JButton("Remove URL");
b.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
String item = (String) urlList.getSelectedValue();
if (item != null) {
urlCache.removeElement(item);
urlList.remove(urlList.getSelectedIndex());
}
}
});
p.add(b);
b = new JButton("Show URL");
b.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
String item = (String) urlList.getSelectedValue();
if (item != null) showURL(item);
}
});
p.add(b);
urlPanel.add("East", p);
bus.registerPluginListener(new AppletListener() {
public void setApplet(JApplet applet) {
context = applet.getAppletContext();
}
});
bus.registerPluginListener(new ConfigurationListener() {
public void setConfiguration(PluginConfig config) {
String s;
if ((s = config.getProperty("URLFilter", id, "protocols")) != null) {
int old = -1, idx = s.indexOf(',');
while (idx >= 0) {
System.out.println("URLFilter: adding protocol '" +
s.substring(old + 1, idx) + "'");
protocols.addElement(s.substring(old + 1, idx));
old = idx;
idx = s.indexOf(',', old + 1);
}
System.out.println("URLFilter: adding protocol '" +
s.substring(old + 1) + "'");
protocols.addElement(s.substring(old + 1));
} else {
protocols.addElement("http");
protocols.addElement("ftp");
protocols.addElement("gopher");
protocols.addElement("file");
}
}
});
// create the recognizer pipe
pin = new PipedInputStream();
pout = new PipedOutputStream();
try {
pout.connect(pin);
} catch (IOException e) {
System.err.println("URLFilter: error installing recognizer: " + e);
}
// start the recognizer
Thread recognizer = new Thread(this);
recognizer.start();
}
private Vector urlCache = new Vector();
public void run() {
try {
StreamTokenizer st =
new StreamTokenizer(new BufferedReader(new InputStreamReader(pin)));
st.eolIsSignificant(true);
st.slashSlashComments(false);
st.slashStarComments(false);
st.whitespaceChars(0, 31);
st.ordinaryChar('"');
st.ordinaryChar('<');
st.ordinaryChar('>');
st.ordinaryChar('/');
st.ordinaryChar(':');
int token;
while ((token = st.nextToken()) != StreamTokenizer.TT_EOF) {
if (token == StreamTokenizer.TT_WORD) {
String word = st.sval.toLowerCase();
// see if we have found a protocol
if (protocols.contains(word)) {
// check that the next chars are ":/"
if (st.nextToken() == ':' && st.nextToken() == '/') {
String url = word + ":/";
// collect the test of the url
while ((token = st.nextToken()) == StreamTokenizer.TT_WORD ||
token == '/')
if (token == StreamTokenizer.TT_WORD)
url += st.sval;
else
url += (char) token;
// urls that end with a dot are usually wrong, so cut it off
if (url.endsWith("."))
url = url.substring(0, url.length() - 1);
// check for duplicate urls by consulting the urlCache
if (!urlCache.contains(url)) {
urlCache.addElement(url);
urlList.add(url, new JLabel(url));
System.out.println("URLFilter: found \"" + url + "\"");
}
}
}
}
}
} catch (IOException e) {
System.err.println("URLFilter: recognition aborted: " + e);
}
}
/**
* Show a URL if the applet context is available.
* We may make it later able to run a web browser or use an HTML
* component.
* @param url the URL to display
*/
protected void showURL(String url) {
if (context == null) {
System.err.println("URLFilter: no url-viewer available\n");
return;
}
try {
context.showDocument(new URL(url), "URLFilter");
} catch (Exception e) {
System.err.println("URLFilter: cannot load url: " + e);
}
}
/** holds the data source for input and output */
protected FilterPlugin source;
/**
* Set the filter source where we can read data from and where to
* write the script answer to.
* @param plugin the filter plugin we use as source
*/
public void setFilterSource(FilterPlugin plugin) {
source = plugin;
}
public FilterPlugin getFilterSource() {
return source;
}
/**
* Read an array of bytes from the back end and send it to the
* url parser to see if it matches.
* @param b the array where to read the bytes in
* @return the amount of bytes actually read
*/
public int read(byte[] b) throws IOException {
int n = source.read(b);
if (n > 0) pout.write(b, 0, n);
return n;
}
public void write(byte[] b) throws IOException {
source.write(b);
}
public JComponent getPluginVisual() {
return urlPanel;
}
public JMenu getPluginMenu() {
return urlMenu;
}
}
jta_2.6+dfsg.orig/de/mud/jta/plugin/Socket.java 0000644 0001750 0001750 00000011417 10610772601 020113 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
import de.mud.jta.FilterPlugin;
import de.mud.jta.Plugin;
import de.mud.jta.PluginBus;
import de.mud.jta.PluginConfig;
import de.mud.jta.event.ConfigurationListener;
import de.mud.jta.event.OnlineStatus;
import de.mud.jta.event.SocketListener;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
/**
* The socket plugin acts as the data source for networked operations.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: Socket.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class Socket extends Plugin
implements FilterPlugin, SocketListener {
private final static int debug = 0;
protected java.net.Socket socket;
protected InputStream in;
protected OutputStream out;
protected String relay = null;
protected int relayPort = 31415;
/**
* Create a new socket plugin.
*/
public Socket(final PluginBus bus, final String id) {
super(bus, id);
// register socket listener
bus.registerPluginListener(this);
bus.registerPluginListener(new ConfigurationListener() {
public void setConfiguration(PluginConfig config) {
if ((relay = config.getProperty("Socket", id, "relay"))
!= null)
if (config.getProperty("Socket", id, "relayPort") != null)
try {
relayPort = Integer.parseInt(
config.getProperty("Socket", id, "relayPort"));
} catch (NumberFormatException e) {
Socket.this.error("relayPort is not a number");
}
}
});
}
private String error = null;
/**
* Connect to the host and port passed. If the multi relayd (mrelayd) is
* used to allow connections to any host and the Socket.relay property
* is configured this method will connect to the relay first, send
* off the string "relay host port\n" and then the real connection will
* be published to be online.
*/
public void connect(String host, int port) throws IOException {
if (host == null) return;
if (debug > 0) error("connect(" + host + "," + port + ")");
try {
// check the relay settings, this is for the mrelayd only!
if (relay == null)
socket = new java.net.Socket(host, port);
else
socket = new java.net.Socket(relay, relayPort);
in = socket.getInputStream();
out = socket.getOutputStream();
// send the string to relay to the target host, port
if (relay != null)
write(("relay " + host + " " + port + "\n").getBytes());
} catch (Exception e) {
error = "Sorry, Could not connect to: "+host+" "+port + "\r\n" +
"Reason: " + e + "\r\n\r\n";
error("can't connect: " + e);
}
bus.broadcast(new OnlineStatus(true));
}
/** Disconnect the socket and close the connection. */
public void disconnect() throws IOException {
if (debug > 0) error("disconnect()");
bus.broadcast(new OnlineStatus(false));
if (socket != null) {
socket.close();
in = null;
out = null;
}
}
public void setFilterSource(FilterPlugin plugin) {
// we do not have a source other than our socket
}
public FilterPlugin getFilterSource() {
return null;
}
public int read(byte[] b) throws IOException {
// send error messages upward
if (error != null && error.length() > 0) {
int n = error.length() < b.length ? error.length() : b.length;
System.arraycopy(error.getBytes(), 0, b, 0, n);
error = error.substring(n);
return n;
}
if (in == null) {
disconnect();
return -1;
}
int n = in.read(b);
if (n < 0) disconnect();
return n;
}
public void write(byte[] b) throws IOException {
if (out == null) return;
try {
out.write(b);
} catch (IOException e) {
disconnect();
}
}
}
jta_2.6+dfsg.orig/de/mud/jta/plugin/Script.java 0000644 0001750 0001750 00000016510 10610772601 020126 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
import de.mud.jta.Plugin;
import de.mud.jta.FilterPlugin;
import de.mud.jta.PluginBus;
import de.mud.jta.PluginConfig;
import de.mud.jta.event.ConfigurationListener;
import de.mud.jta.event.OnlineStatusListener;
import java.io.IOException;
import java.util.Vector;
/**
* The script plugin takes a series of match and answer pairs to compare
* the incoming data with the matches and if it succeeds writes the answers
* back. It then moves on to the next match until all script elements have
* matched.
* The script property Script.script should contain | separated strings
* where each two represent a match and answer pair. A newline will be appended
* to each answer!
* If the first matching string is empty, the answer string will be sent upon
* connect.
* The script is very basic but is a very good example how to
* write a plugin for JTA - Telnet/SSH for the JAVA(tm) platform.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: Script.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class Script extends Plugin implements FilterPlugin {
/** debugging level */
private final static int debug = 0;
/** the script after parsing, saved for reinitialization */
private Vector savedScript;
/**
* Create a new scripting plugin.
*/
public Script(PluginBus bus, final String id) {
super(bus, id);
bus.registerPluginListener(new OnlineStatusListener() {
public void online() {
setup(savedScript);
}
public void offline() {
// ignore disconnection
}
});
bus.registerPluginListener(new ConfigurationListener() {
public void setConfiguration(PluginConfig config) {
savedScript = new Vector();
String s = config.getProperty("Script", id, "script");
if(s != null) {
// check if the script is stored in a file
if(s.charAt(0) == '@') {
Script.this.error("@file not implemented yet");
}
// parse the script and set up
if(debug > 0) Script.this.error(s);
String pair[] = null;
int old = -1, idx = s.indexOf('|');
while(idx >= 0) {
if(pair == null) {
pair = new String[2];
pair[0] = s.substring(old + 1, idx);
if(debug > 0) System.out.print("match("+pair[0]+") -> ");
} else {
pair[1] = s.substring(old + 1, idx)+"\n";
if(debug > 0) System.out.print(pair[1]);
savedScript.addElement(pair);
pair = null;
}
old = idx;
idx = s.indexOf('|', old + 1);
}
if(pair != null) {
pair[1] = s.substring(old + 1)+"\n";
savedScript.addElement(pair);
if(debug > 0) System.out.print(pair[1]);
} else
Script.this.error("unmatched pairs of script elements");
// set up the script
// setup(savedScript);
}
}
});
}
/** holds the data source for input and output */
protected FilterPlugin source;
/**
* Set the filter source where we can read data from and where to
* write the script answer to.
* @param plugin the filter plugin we use as source
*/
public void setFilterSource(FilterPlugin plugin) {
source = plugin;
}
public FilterPlugin getFilterSource() {
return source;
}
/**
* Read an array of bytes from the back end and put it through the
* script parser to see if it matches. It will send the answer
* immediately to the filter source if a match occurs.
* @param b the array where to read the bytes in
* @return the amount of bytes actually read
*/
public int read(byte[] b) throws IOException {
int n = source.read(b);
if(n > 0) match(b, n);
return n;
}
public void write(byte[] b) throws IOException {
source.write(b);
}
// =================================================================
// the actual scripting code follows:
// =================================================================
private int matchPos; // current position in the match
private Vector script; // the actual script
private byte[] match; // the current bytes to look for
private boolean done = true; // no script!
/**
* Setup the parser using the passed script. The script contains for
* every element a two-element array of String where element zero
* contains the match and element one the answer.
* @param script the script
*/
private void setup(Vector script) {
// clone script to make sure we do not change the original
this.script = (Vector)script.clone();
if(debug > 0)
System.err.println("Script: script contains "+script.size()+" elements");
// If the first element is empty, just send the value string.
match = ((String[])this.script.firstElement())[0].getBytes();
if (match.length == 0) {
try {
write(found());
} catch (Exception e){
// Ignore any errors here
};
}
reset();
done = false;
}
/**
* Try to match the byte array s against the most current script match.
* It will write the answer immediatly if the script matches and
* will return instantly when all the script work is done.
* @param s the array of bytes to match against
* @param length the amount of bytes in the array
*/
private void match(byte[] s, int length) throws IOException {
for(int i = 0; !done && i < length; i++) {
if(s[i] == match[matchPos]) {
// the whole thing matched so, return the match answer
// and reset to use the next match
if(++matchPos >= match.length)
write(found());
} else // if the current character did not match reset
reset();
}
}
/**
* This method is called when a script match was found and will
* setup the next match to be used and return the answer for the
* just found one.
* @return the answer to the found match
*/
private byte[] found() {
if(debug > 0) System.err.println("Script: found '"+new String(match)+"'");
// we have matched the string, so remember the answer ...
byte[] answer = ((String[])script.firstElement())[1].getBytes();
// remove the matched element
script.removeElementAt(0);
// set the next match if applicable
if(!script.isEmpty()) {
match = ((String[])script.firstElement())[0].getBytes();
reset();
} else
done = true;
return answer;
}
/**
* Reset the match position counter.
*/
private void reset() {
matchPos = 0;
}
}
jta_2.6+dfsg.orig/de/mud/jta/plugin/Telnet.java 0000644 0001750 0001750 00000012727 10610772601 020123 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
import de.mud.jta.Plugin;
import de.mud.jta.PluginConfig;
import de.mud.jta.FilterPlugin;
import de.mud.jta.PluginBus;
import de.mud.jta.event.OnlineStatusListener;
import de.mud.jta.event.ConfigurationListener;
import de.mud.jta.event.TelnetCommandListener;
import de.mud.jta.event.SetWindowSizeListener;
import de.mud.jta.event.TerminalTypeRequest;
import de.mud.jta.event.WindowSizeRequest;
import de.mud.jta.event.LocalEchoRequest;
import de.mud.jta.event.EndOfRecordRequest;
import de.mud.jta.event.EndOfRecordRequest;
import de.mud.telnet.TelnetProtocolHandler;
import java.awt.Dimension;
import java.io.IOException;
/**
* The telnet plugin utilizes a telnet protocol handler to filter
* telnet negotiation requests from the data stream.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: Telnet.java 503 2005-10-24 07:34:13Z marcus $
* @author Matthias L. Jugel, Marcus Meissner
*/
public class Telnet extends Plugin implements FilterPlugin {
protected FilterPlugin source;
protected TelnetProtocolHandler handler;
private final static int debug = 0;
/**
* Create a new telnet plugin.
*/
public Telnet(final PluginBus bus, String id) {
super(bus, id);
// create a new telnet protocol handler
handler = new TelnetProtocolHandler() {
/** get the current terminal type */
public String getTerminalType() {
return (String)bus.broadcast(new TerminalTypeRequest());
}
/** get the current window size */
public Dimension getWindowSize() {
return (Dimension)bus.broadcast(new WindowSizeRequest());
}
/** notify about local echo */
public void setLocalEcho(boolean echo) {
bus.broadcast(new LocalEchoRequest(echo));
}
/** notify about EOR end of record */
public void notifyEndOfRecord() {
bus.broadcast(new EndOfRecordRequest());
}
/** write data to our back end */
public void write(byte[] b) throws IOException {
source.write(b);
}
};
// reset the telnet protocol handler just in case :-)
bus.registerPluginListener(new OnlineStatusListener() {
public void online() {
handler.reset();
try {
handler.startup();
} catch(java.io.IOException e) {
}
bus.broadcast(new LocalEchoRequest(true));
}
public void offline() {
handler.reset();
bus.broadcast(new LocalEchoRequest(true));
}
});
bus.registerPluginListener(new SetWindowSizeListener() {
public void setWindowSize(int columns, int rows) {
try {
handler.setWindowSize(columns,rows);
} catch (java.io.IOException e) {
System.err.println("IO Exception in set window size");
}
}
});
bus.registerPluginListener(new ConfigurationListener() {
public void setConfiguration(PluginConfig config) {
configure(config);
}
});
bus.registerPluginListener(new TelnetCommandListener() {
public void sendTelnetCommand(byte command) throws IOException {
handler.sendTelnetControl(command);
}
});
}
public void configure(PluginConfig cfg) {
String crlf = cfg.getProperty("Telnet",id,"crlf"); // on \n
if (crlf != null) handler.setCRLF(crlf);
String cr = cfg.getProperty("Telnet",id,"cr"); // on \r
if (cr != null) handler.setCR(cr);
}
public void setFilterSource(FilterPlugin source) {
if(debug>0) System.err.println("Telnet: connected to: "+source);
this.source = source;
}
public FilterPlugin getFilterSource() {
return source;
}
public int read(byte[] b) throws IOException {
/* We just don't pass read() down, since negotiate() might call other
* functions and we need transaction points.
*/
int n;
/* clear out the rest of the buffer.
* loop, in case we have negotiations (return 0) and
* date (return > 0) mixed ... until end of buffer or
* any data read.
*/
do {
n = handler.negotiate(b);
if (n>0)
return n;
} while (n==0);
/* try reading stuff until we get at least 1 byte of real data or are
* at the end of the buffer.
*/
while (true) {
n = source.read(b);
if (n <= 0 )
return n;
handler.inputfeed(b,n);
n = 0;
while (true) {
n = handler.negotiate(b);
if (n>0)
return n;
if (n==-1) // buffer empty.
break;
}
return 0;
}
}
public void write(byte[] b) throws IOException {
handler.transpose(b); // transpose 0xff or \n and send data
}
}
jta_2.6+dfsg.orig/de/mud/terminal/ 0000755 0001750 0001750 00000000000 10610772601 015553 5 ustar paul paul jta_2.6+dfsg.orig/de/mud/terminal/SoftFont.java 0000644 0001750 0001750 00000061220 10610772601 020161 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.terminal;
import java.awt.*;
import java.util.*;
/**
* Any characters that are not available in standard java fonts may be
* drawn using the softfont utility. This utility class was derived from
* the cpi fonts used in linux console drivers.
* Font file generated by cpi2fnt
*
* Maintainer: Marcus Meissner
*
* @version $Id: SoftFont.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Meissner
*/
public class SoftFont {
final static private char SF_BITMAP = 0;
final static private char SF_FILLRECT = 1;
final static private char SF_CHAR = 0;
final static private char SF_WIDTH= 1;
final static private char SF_HEIGHT= 2;
final static private char SF_TYPE = 3;
final static private char SF_DATA = 4;
java.util.Hashtable font;
/** softfont characterdata */
private static char[][] fontdata = {
{0x01,8,8,SF_BITMAP, /* 1 0x01 '^A' */
0x7e, /* 01111110 */
0x81, /* 10000001 */
0xa5, /* 10100101 */
0x81, /* 10000001 */
0xbd, /* 10111101 */
0x99, /* 10011001 */
0x81, /* 10000001 */
0x7e, /* 01111110 */
},{ 0x02,8,8,SF_BITMAP,/* 2 0x02 '^B' */
0x7e, /* 01111110 */
0xff, /* 11111111 */
0xdb, /* 11011011 */
0xff, /* 11111111 */
0xc3, /* 11000011 */
0xe7, /* 11100111 */
0xff, /* 11111111 */
0x7e, /* 01111110 */
},{ 0x03,8,8,SF_BITMAP,/* 3 0x03 '^C' */
0x6c, /* 01101100 */
0xfe, /* 11111110 */
0xfe, /* 11111110 */
0xfe, /* 11111110 */
0x7c, /* 01111100 */
0x38, /* 00111000 */
0x10, /* 00010000 */
0x00, /* 00000000 */
},{ 0x04,8,8,SF_BITMAP,/* 4 0x04 '^D' */
0x10, /* 00010000 */
0x38, /* 00111000 */
0x7c, /* 01111100 */
0xfe, /* 11111110 */
0x7c, /* 01111100 */
0x38, /* 00111000 */
0x10, /* 00010000 */
0x00, /* 00000000 */
},{ 0x05,8,8,SF_BITMAP,/* 5 0x05 '^E' */
0x38, /* 00111000 */
0x7c, /* 01111100 */
0x38, /* 00111000 */
0xfe, /* 11111110 */
0xfe, /* 11111110 */
0xd6, /* 11010110 */
0x10, /* 00010000 */
0x38, /* 00111000 */
},{ 0x06,8,8,SF_BITMAP,/* 6 0x06 '^F' */
0x10, /* 00010000 */
0x38, /* 00111000 */
0x7c, /* 01111100 */
0xfe, /* 11111110 */
0xfe, /* 11111110 */
0x7c, /* 01111100 */
0x10, /* 00010000 */
0x38, /* 00111000 */
},{ 0x2666,8,8,SF_BITMAP,/* 9830 0x2666 BLACK DIAMOND */
0x00, /* 00000000 */
0x00, /* 00000000 */
0x18, /* 00011000 */
0x3c, /* 00111100 */
0x3c, /* 00111100 */
0x18, /* 00011000 */
0x00, /* 00000000 */
0x00, /* 00000000 */
},{ 0x07,8,8,SF_BITMAP,/* 7 0x07 '^G' */
0x00, /* 00000000 */
0x00, /* 00000000 */
0x18, /* 00011000 */
0x3c, /* 00111100 */
0x3c, /* 00111100 */
0x18, /* 00011000 */
0x00, /* 00000000 */
0x00, /* 00000000 */
},{ 0x08,8,8,SF_BITMAP,/* 8 0x08 '^H' */
0xff, /* 11111111 */
0xff, /* 11111111 */
0xe7, /* 11100111 */
0xc3, /* 11000011 */
0xc3, /* 11000011 */
0xe7, /* 11100111 */
0xff, /* 11111111 */
0xff, /* 11111111 */
},{ 0x09,8,8,SF_BITMAP,/* 9 0x09 '^I' */
0x00, /* 00000000 */
0x3c, /* 00111100 */
0x66, /* 01100110 */
0x42, /* 01000010 */
0x42, /* 01000010 */
0x66, /* 01100110 */
0x3c, /* 00111100 */
0x00, /* 00000000 */
},{ 0x0a,8,8,SF_BITMAP,/* 10 0x0a '^J' */
0xff, /* 11111111 */
0xc3, /* 11000011 */
0x99, /* 10011001 */
0xbd, /* 10111101 */
0xbd, /* 10111101 */
0x99, /* 10011001 */
0xc3, /* 11000011 */
0xff, /* 11111111 */
},{ 0x0b,8,8,SF_BITMAP,/* 11 0x0b '^K' */
0x0f, /* 00001111 */
0x07, /* 00000111 */
0x0f, /* 00001111 */
0x7d, /* 01111101 */
0xcc, /* 11001100 */
0xcc, /* 11001100 */
0xcc, /* 11001100 */
0x78, /* 01111000 */
},{ 0x0c,8,8,SF_BITMAP,/* 12 0x0c '^L' */
0x3c, /* 00111100 */
0x66, /* 01100110 */
0x66, /* 01100110 */
0x66, /* 01100110 */
0x3c, /* 00111100 */
0x18, /* 00011000 */
0x7e, /* 01111110 */
0x18, /* 00011000 */
},{ 0x0d,8,8,SF_BITMAP,/* 13 0x0d '^M' */
0x3f, /* 00111111 */
0x33, /* 00110011 */
0x3f, /* 00111111 */
0x30, /* 00110000 */
0x30, /* 00110000 */
0x70, /* 01110000 */
0xf0, /* 11110000 */
0xe0, /* 11100000 */
},{ 0x0e,8,8,SF_BITMAP,/* 14 0x0e '^N' */
0x7f, /* 01111111 */
0x63, /* 01100011 */
0x7f, /* 01111111 */
0x63, /* 01100011 */
0x63, /* 01100011 */
0x67, /* 01100111 */
0xe6, /* 11100110 */
0xc0, /* 11000000 */
},{ 0x0f,8,8,SF_BITMAP,/* 15 0x0f '^O' */
0x18, /* 00011000 */
0xdb, /* 11011011 */
0x3c, /* 00111100 */
0xe7, /* 11100111 */
0xe7, /* 11100111 */
0x3c, /* 00111100 */
0xdb, /* 11011011 */
0x18, /* 00011000 */
},{ 0x10,8,8,SF_BITMAP,/* 16 0x10 '^P' */
0x80, /* 10000000 */
0xe0, /* 11100000 */
0xf8, /* 11111000 */
0xfe, /* 11111110 */
0xf8, /* 11111000 */
0xe0, /* 11100000 */
0x80, /* 10000000 */
0x00, /* 00000000 */
},{ 0x11,8,8,SF_BITMAP,/* 17 0x11 '^Q' */
0x02, /* 00000010 */
0x0e, /* 00001110 */
0x3e, /* 00111110 */
0xfe, /* 11111110 */
0x3e, /* 00111110 */
0x0e, /* 00001110 */
0x02, /* 00000010 */
0x00, /* 00000000 */
},{ 0x12,8,8,SF_BITMAP,/* 18 0x12 '^R' */
0x18, /* 00011000 */
0x3c, /* 00111100 */
0x7e, /* 01111110 */
0x18, /* 00011000 */
0x18, /* 00011000 */
0x7e, /* 01111110 */
0x3c, /* 00111100 */
0x18, /* 00011000 */
},{ 0x13,8,8,SF_BITMAP,/* 19 0x13 '^S' */
0x66, /* 01100110 */
0x66, /* 01100110 */
0x66, /* 01100110 */
0x66, /* 01100110 */
0x66, /* 01100110 */
0x00, /* 00000000 */
0x66, /* 01100110 */
0x00, /* 00000000 */
},{ 0x14,8,8,SF_BITMAP,/* 20 0x14 '^T' */
0x7f, /* 01111111 */
0xdb, /* 11011011 */
0xdb, /* 11011011 */
0x7b, /* 01111011 */
0x1b, /* 00011011 */
0x1b, /* 00011011 */
0x1b, /* 00011011 */
0x00, /* 00000000 */
},{ 0x15,8,8,SF_BITMAP,/* 21 0x15 '^U' */
0x3e, /* 00111110 */
0x61, /* 01100001 */
0x3c, /* 00111100 */
0x66, /* 01100110 */
0x66, /* 01100110 */
0x3c, /* 00111100 */
0x86, /* 10000110 */
0x7c, /* 01111100 */
},{ 0x16,8,8,SF_BITMAP,/* 22 0x16 '^V' */
0x00, /* 00000000 */
0x00, /* 00000000 */
0x00, /* 00000000 */
0x00, /* 00000000 */
0x7e, /* 01111110 */
0x7e, /* 01111110 */
0x7e, /* 01111110 */
0x00, /* 00000000 */
},{ 0x17,8,8,SF_BITMAP,/* 23 0x17 '^W' */
0x18, /* 00011000 */
0x3c, /* 00111100 */
0x7e, /* 01111110 */
0x18, /* 00011000 */
0x7e, /* 01111110 */
0x3c, /* 00111100 */
0x18, /* 00011000 */
0xff, /* 11111111 */
},{ 0x18,8,8,SF_BITMAP,/* 24 0x18 '^X' */
0x18, /* 00011000 */
0x3c, /* 00111100 */
0x7e, /* 01111110 */
0x18, /* 00011000 */
0x18, /* 00011000 */
0x18, /* 00011000 */
0x18, /* 00011000 */
0x00, /* 00000000 */
},{ 0x19,8,8,SF_BITMAP,/* 25 0x19 '^Y' */
0x18, /* 00011000 */
0x18, /* 00011000 */
0x18, /* 00011000 */
0x18, /* 00011000 */
0x7e, /* 01111110 */
0x3c, /* 00111100 */
0x18, /* 00011000 */
0x00, /* 00000000 */
},{ 0x1a,8,8,SF_BITMAP,/* 26 0x1a '^Z' */
0x00, /* 00000000 */
0x18, /* 00011000 */
0x0c, /* 00001100 */
0xfe, /* 11111110 */
0x0c, /* 00001100 */
0x18, /* 00011000 */
0x00, /* 00000000 */
0x00, /* 00000000 */
},{ 0x1b,8,8,SF_BITMAP,/* 27 0x1b '^[' */
0x00, /* 00000000 */
0x30, /* 00110000 */
0x60, /* 01100000 */
0xfe, /* 11111110 */
0x60, /* 01100000 */
0x30, /* 00110000 */
0x00, /* 00000000 */
0x00, /* 00000000 */
},{ 0x1c,8,8,SF_BITMAP,/* 28 0x1c '^\' */
0x00, /* 00000000 */
0x00, /* 00000000 */
0xc0, /* 11000000 */
0xc0, /* 11000000 */
0xc0, /* 11000000 */
0xfe, /* 11111110 */
0x00, /* 00000000 */
0x00, /* 00000000 */
},{ 0x1d,8,8,SF_BITMAP,/* 29 0x1d '^]' */
0x00, /* 00000000 */
0x24, /* 00100100 */
0x66, /* 01100110 */
0xff, /* 11111111 */
0x66, /* 01100110 */
0x24, /* 00100100 */
0x00, /* 00000000 */
0x00, /* 00000000 */
},{ 0x1e,8,8,SF_BITMAP,/* 30 0x1e '^^' */
0x00, /* 00000000 */
0x18, /* 00011000 */
0x3c, /* 00111100 */
0x7e, /* 01111110 */
0xff, /* 11111111 */
0xff, /* 11111111 */
0x00, /* 00000000 */
0x00, /* 00000000 */
},{ 0x1f,8,8,SF_BITMAP,/* 31 0x1f '^_' */
0x00, /* 00000000 */
0xff, /* 11111111 */
0xff, /* 11111111 */
0x7e, /* 01111110 */
0x3c, /* 00111100 */
0x18, /* 00011000 */
0x00, /* 00000000 */
0x00, /* 00000000 */
},{ 0x7f,8,8,SF_BITMAP,/* 127 0x7f '' */
0x00, /* 00000000 */
0x10, /* 00010000 */
0x38, /* 00111000 */
0x6c, /* 01101100 */
0xc6, /* 11000110 */
0xc6, /* 11000110 */
0xfe, /* 11111110 */
0x00, /* 00000000 */
},{ 0x2591,8,8,SF_BITMAP,/* LIGHT SHADE */
0x22, /* 00100010 */
0x88, /* 10001000 */
0x22, /* 00100010 */
0x88, /* 10001000 */
0x22, /* 00100010 */
0x88, /* 10001000 */
0x22, /* 00100010 */
0x88, /* 10001000 */
},{ 0x2592,8,8,SF_BITMAP,/* MEDIUM SHADE */
0x55, /* 01010101 */
0xaa, /* 10101010 */
0x55, /* 01010101 */
0xaa, /* 10101010 */
0x55, /* 01010101 */
0xaa, /* 10101010 */
0x55, /* 01010101 */
0xaa, /* 10101010 */
},{ 0x2593,8,8,SF_BITMAP,/* DARK SHADE */
0x77, /* 01110111 */
0xdd, /* 11011101 */
0x77, /* 01110111 */
0xdd, /* 11011101 */
0x77, /* 01110111 */
0xdd, /* 11011101 */
0x77, /* 01110111 */
0xdd, /* 11011101 */
},{ 0x221a,8,8,SF_BITMAP,/* SQUARE ROOT */
0x78, /* 01111000 */
0x0c, /* 00001100 */
0x18, /* 00011000 */
0x30, /* 00110000 */
0x7c, /* 01111100 */
0x00, /* 00000000 */
0x00, /* 00000000 */
0x00, /* 00000000 */
},{ 0x2320,8,8,SF_FILLRECT,/* UPPER INTERVAL*/
0x4031,
0x3127,
0x6122,
/* 00001110 */
/* 00011011 */
/* 00011011 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
},{ 0x2321,8,8,SF_FILLRECT,/* BOTTOM HALF INTEGRAL */
0x3027,
0x0522,
0x1731,
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 11011000 */
/* 11011000 */
/* 01110000 */
},{ 0x25a0,8,8,SF_FILLRECT,/* BLACK SQUARE */
0x2244,
/* 00000000 */
/* 00000000 */
/* 00111100 */
/* 00111100 */
/* 00111100 */
/* 00111100 */
/* 00000000 */
/* 00000000 */
},{ 0x2502,8,8,SF_FILLRECT,/*BOX DRAWINGS LIGHT VERTICAL*/
0x3028,
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
},{ 0x2524,8,8,SF_FILLRECT,/* BOX DRAWINGS LIGHT VERTICAL AND LEFT */
0x3028,
0x0431,
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 11111000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
},{ 0x2561,8,8,SF_FILLRECT,/*BOX DRAWINGS VERTICAL SINGLE AND LEFT DOUBLE*/
0x3028,
0x0231,
0x0431,
/* 00011000 */
/* 00011000 */
/* 11111000 */
/* 00011000 */
/* 11111000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
},{ 0x2562,8,8,SF_FILLRECT,/* BOX DRAWINGS VERTICAL DOUBLE AND LEFT SINGLE */
0x2028,
0x5028,
0x0421,
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 11110110 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
},{ 0x2556,8,8,SF_FILLRECT,/* BOX DRAWINGS DOWN DOUBLE AND LEFT SINGLE */
0x0471,
0x2523,
0x5523,
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 11111110 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
},{ 0x2555,8,8,SF_FILLRECT,/* BOX DRAWINGS DOWN SINGLE AND LEFT DOUBLE */
0x3226,
0x0231,
0x0431,
/* 00000000 */
/* 00000000 */
/* 11111000 */
/* 00011000 */
/* 11111000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
},{ 0x2563,8,8,SF_FILLRECT,/* BOX DRAWINGS DOUBLE VERTICAL AND LEFT*/
0x2022,
0x0221,
0x0421,
0x2424,
0x5028,
/* 00110110 */
/* 00110110 */
/* 11110110 */
/* 00000110 */
/* 11110110 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
},{ 0x2551,8,8,SF_FILLRECT,/* BOX DRAWINGS DOUBLE VERTICAL */
0x2028,
0x5028,
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
},{ 0x2557,8,8,SF_FILLRECT,/* BOX DRAWINGS DOUBLE DOWN AND LEFT */
0x0271,
0x5325,
0x0441,
0x2523,
/* 00000000 */
/* 00000000 */
/* 11111110 */
/* 00000110 */
/* 11110110 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
},{ 0x255d,8,8,SF_FILLRECT,/* BOX DRAWINGS DOUBLE UP AND LEFT */
0x2022,
0x0241,
0x5025,
0x0451,
/* 00110110 */
/* 00110110 */
/* 11110110 */
/* 00000110 */
/* 11111110 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x255c,8,8,SF_FILLRECT,/* BOX DRAWINGS UP DOUBLE AND LEFT SINGLE */
0x2024,
0x5024,
0x0471,
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 11111110 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x255b,8,8,SF_FILLRECT,/* BOX DRAWINGS UP SINGLE AND LEFT DOUBLE */
0x3025,
0x0231,
0x0431,
/* 00011000 */
/* 00011000 */
/* 11111000 */
/* 00011000 */
/* 11111000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x2510,8,8,SF_FILLRECT,/* BOX DRAWINGS LIGHT DOWN AND LEFT */
0x0451,
0x3523,
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 11111000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
},{ 0x2514,8,8,SF_FILLRECT,/* BOX DRAWINGS LIGHT UP AND RIGHT */
0x3025,
0x5431,
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011111 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x2534,8,8,SF_FILLRECT,/* BOX DRAWINGS LIGHT UP AND HORIZONTAL */
0x3024,
0x0481,
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 11111111 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x252c,8,8,SF_FILLRECT,/* BOX DRAWINGS LIGHT DOWN AND HORIZONTAL */
0x0481,
0x3523,
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 11111111 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
},{ 0x251c,8,8,SF_FILLRECT,/* BOX DRAWINGS LIGHT VERTICAL AND RIGHT */
0x3028,
0x5431,
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011111 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
},{ 0x2500,8,8,SF_FILLRECT,/* BOX DRAWINGS LIGHT HORIZONTAL */
0x0481,
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 11111111 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x2594,8,8,SF_FILLRECT,/* UPPER 1/8 (1st scanline) */
0x0081,
/* 11111111 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x25ac,8,8,SF_FILLRECT,/* LOWER 1/8 (7nd scanline) */
0x0781,
/* 11111111 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x253c,8,8,SF_FILLRECT,/* BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL */
0x3028,
0x0481,
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 11111111 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
},{ 0x255e,8,8,SF_FILLRECT,/* BOX DRAWINGS VERTICAL SINGLE AND RIGHT DOUBLE */
0x3028,
0x5231,
0x5431,
/* 00011000 */
/* 00011000 */
/* 00011111 */
/* 00011000 */
/* 00011111 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
},{ 0x255f,8,8,SF_FILLRECT,/* BOX DRAWINGS VERTICAL DOUBLE AND RIGHT SINGLE */
0x2028,
0x5028,
0x7411,
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 00110111 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
},{ 0x255a,8,8,SF_FILLRECT,/* BOX DRAWINGS DOUBLE UP AND RIGHT */
0x2025,
0x5023,
0x7211,
0x4441,
/* 00110110 */
/* 00110110 */
/* 00110111 */
/* 00110000 */
/* 00111111 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x2554,8,8,SF_FILLRECT,/* BOX DRAWINGS DOUBLE DOWN AND RIGHT */
0x2261,
0x2325,
0x5424,
0x7411,
/* 00000000 */
/* 00000000 */
/* 00111111 */
/* 00110000 */
/* 00110111 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
},{ 0x2569,8,8,SF_FILLRECT,/* BOX DRAWINGS DOUBLE UP AND HORIZONTAL */
0x2022,
0x0241,
0x5022,
0x5231,
0x0481,
/* 00110110 */
/* 00110110 */
/* 11110111 */
/* 00000000 */
/* 11111111 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x2566,8,8,SF_FILLRECT,/* BOX DRAWINGS DOUBLE DOWN AND HORIZONTAL */
0x0281,
0x0441,
0x2523,
0x5431,
0x5523,
/* 00000000 */
/* 00000000 */
/* 11111111 */
/* 00000000 */
/* 11110111 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
},{ 0x2560,8,8,SF_FILLRECT,/* BOX DRAWINGS DOUBLE VERTICAL AND RIGHT */
0x2028,
0x5022,
0x5231,
0x5431,
0x5623,
/* 00110110 */
/* 00110110 */
/* 00110111 */
/* 00110000 */
/* 00110111 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
},{ 0x2550,8,8,SF_FILLRECT,/* BOX DRAWINGS DOUBLE HORIZONTAL */
0x0281,
0x0481,
/* 00000000 */
/* 00000000 */
/* 11111111 */
/* 00000000 */
/* 11111111 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x256c,8,8,SF_FILLRECT,/* BOX DRAWINGS DOUBLE VERTICAL AND HORIZONTAL */
0x2022,
0x0241,
0x5022,
0x5231,
0x0441,
0x2523,
0x5431,
0x5523,
/* 00110110 */
/* 00110110 */
/* 11110111 */
/* 00000000 */
/* 11110111 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
},{ 0x2567,8,8,SF_FILLRECT,/* BOX DRAWINGS UP SINGLE AND HORIZONTAL DOUBLE */
0x3022,
0x0281,
0x0481,
/* 00011000 */
/* 00011000 */
/* 11111111 */
/* 00000000 */
/* 11111111 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x2568,8,8,SF_FILLRECT,/* BOX DRAWINGS UP DOUBLE AND HORIZONTAL SINGLE */
0x2024,
0x5024,
0x0481,
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 11111111 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x2564,8,8,SF_FILLRECT,/* BOX DRAWINGS DOWN SINGLE AND HORIZONTAL DOUBLE */
0x0281,
0x0481,
0x3523,
/* 00000000 */
/* 00000000 */
/* 11111111 */
/* 00000000 */
/* 11111111 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
},{ 0x2565,8,8,SF_FILLRECT,/* BOX DRAWINGS DOWN DOUBLE AND HORIZONTAL SINGLE */
0x0481,
0x2523,
0x5523,
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 11111111 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
},{ 0x2559,8,8,SF_FILLRECT,/* BOX DRAWINGS UP DOUBLE AND RIGHT SINGLE */
0x2024,
0x5024,
0x2461,
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 00111111 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x2558,8,8,SF_FILLRECT,/* BOX DRAWINGS UP SINGLE AND RIGHT DOUBLE */
0x3025,
0x5231,
0x5431,
/* 00011000 */
/* 00011000 */
/* 00011111 */
/* 00011000 */
/* 00011111 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x2552,8,8,SF_FILLRECT,/* BOX DRAWINGS DOWN SINGLE AND RIGHT DOUBLE */
0x3226,
0x5231,
0x5431,
/* 00000000 */
/* 00000000 */
/* 00011111 */
/* 00011000 */
/* 00011111 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
},{ 0x2553,8,8,SF_FILLRECT,/* BOX DRAWINGS DOWN DOUBLE AND RIGHT SINGLE */
0x2461,
0x2523,
0x5523,
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00111111 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
},{ 0x256b,8,8,SF_FILLRECT,/* BOX DRAWINGS VERTICAL DOUBLE AND HORIZONTAL SINGLE */
0x2028,
0x5028,
0x0481,
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
/* 11111111 */
/* 00110110 */
/* 00110110 */
/* 00110110 */
},{ 0x256a,8,8,SF_FILLRECT,/* BOX DRAWINGS VERTICAL SINGLE AND HORIZONTAL DOUBLE */
0x3028,
0x0281,
0x0481,
/* 00011000 */
/* 00011000 */
/* 11111111 */
/* 00011000 */
/* 11111111 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
},{ 0x2518,8,8,SF_FILLRECT,/* BOX DRAWINGS LIGHT UP AND LEFT */
0x3025,
0x0431,
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
/* 11111000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x250c,8,8,SF_FILLRECT,/* BOX DRAWINGS LIGHT DOWN AND RIGHT */
0x3451,
0x3523,
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00011111 */
/* 00011000 */
/* 00011000 */
/* 00011000 */
},{ 0x2588,8,8,SF_FILLRECT,/* FULL BLOCK */
0x0088,
/* 11111111 */
/* 11111111 */
/* 11111111 */
/* 11111111 */
/* 11111111 */
/* 11111111 */
/* 11111111 */
/* 11111111 */
},{ 0x2584,8,8,SF_FILLRECT,/* LOWER HALF BLOCK */
0x0484,
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 11111111 */
/* 11111111 */
/* 11111111 */
/* 11111111 */
},{ 0x258c,8,8,SF_FILLRECT,/* LEFT HALF BLOCK */
0x0048,
/* 11110000 */
/* 11110000 */
/* 11110000 */
/* 11110000 */
/* 11110000 */
/* 11110000 */
/* 11110000 */
/* 11110000 */
},{ 0x2590,8,8,SF_FILLRECT,/* RIGHT HALF BLOCK */
0x4048,
/* 00001111 */
/* 00001111 */
/* 00001111 */
/* 00001111 */
/* 00001111 */
/* 00001111 */
/* 00001111 */
/* 00001111 */
},{ 0x2580,8,8,SF_FILLRECT,/* UPPER HALF BLOCK */
0x0084,
/* 11111111 */
/* 11111111 */
/* 11111111 */
/* 11111111 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x2261,8,8,SF_FILLRECT,/* EQUIVALENT SIGN */
0x2081,
0x4081,
0x6081,
/* 00000000 */
/* 00000000 */
/* 11111111 */
/* 00000000 */
/* 11111111 */
/* 00000000 */
/* 11111111 */
/* 00000000 */
},{ 0x221e,8,8,SF_BITMAP,/* INFINITY */
0x00,
0x00,
0x7e,
0xdb,
0xdb,
0x7e,
0x00,
0x00,
/* 00000000 */
/* 00000000 */
/* 01111110 */
/* 11011011 */
/* 11011011 */
/* 01111110 */
/* 00000000 */
/* 00000000 */
},{ 0x207f,8,8,SF_FILLRECT,/* small superscript n */
0x1041,
0x1124,
0x4124,
/* 01111000 */
/* 01101100 */
/* 01101100 */
/* 01101100 */
/* 01101100 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x00b2,8,8,SF_BITMAP,/* small superscript 2 */
0x70, /* 01110000 */
0x1c, /* 00011100 */
0x38, /* 00111000 */
0x60, /* 01100000 */
0x78, /* 01111000 */
0x00, /* 00000000 */
0x00, /* 00000000 */
0x00, /* 00000000 */
},{ 0x2219,8,8,SF_FILLRECT,/* BULLET OPERATOR */
0x3322,
/* 00000000 */
/* 00000000 */
/* 00000000 */
/* 00011000 */
/* 00011000 */
/* 00000000 */
/* 00000000 */
/* 00000000 */
},{ 0x2191,8,8,SF_BITMAP,/* UP ARROW */
0x08, /* 00001000 */
0x1c, /* 00011100 */
0x3e, /* 00111110 */
0x7f, /* 01111111 */
0x1c, /* 00011100 */
0x1c, /* 00011100 */
0x1c, /* 00011100 */
0x1c, /* 00011100 */
},{ 0x2193,8,8,SF_BITMAP,/* DOWN ARROW */
0x1c, /* 00011100 */
0x1c, /* 00011100 */
0x1c, /* 00011100 */
0x1c, /* 00011100 */
0x7f, /* 01111111 */
0x3e, /* 00111110 */
0x1c, /* 00011100 */
0x08, /* 00001000 */
},{ 0x25ba,8,8,SF_BITMAP,/* RIGHT ARROW (TRIANGLE ONLY) */
0x00, /* 00000000 */
0x40, /* 01000000 */
0x60, /* 01100000 */
0x7c, /* 01111100 */
0x70, /* 01110000 */
0x60, /* 01100000 */
0x40, /* 01000000 */
0x00, /* 00000000 */
},{ 0x25c4,8,8,SF_BITMAP,/* LEFT ARROW (TRIANGLE ONLY) */
0x00, /* 00000000 */
0x02, /* 00000010 */
0x06, /* 00000110 */
0x3e, /* 00111110 */
0x0e, /* 00001110 */
0x06, /* 00000110 */
0x02, /* 00000010 */
0x00, /* 00000000 */
}};
public SoftFont() {
font = new java.util.Hashtable();
for (int i=0;i=0x100) {
System.out.println("Character "+((int)c)+" not in softfont");
}
return insoftfont;
}
public void drawChar(Graphics g,char c,int x,int y,int cw,int ch) {
double dw,dh;
Object Ientry;
int w,h,entry,i,fontwidth,fontheight;
Ientry = font.get(new Integer(c));
if (Ientry == null)
return;
entry = ((Integer)Ientry).intValue();
fontwidth = fontdata[entry][SF_WIDTH];
fontheight = fontdata[entry][SF_HEIGHT];
dw = cw*1.0/fontwidth;
dh = ch*1.0/fontheight;
switch (fontdata[entry][SF_TYPE]) {
case SF_BITMAP:
for (h=0;h>12;
h=(fontdata[entry][i]&0x0F00)>>8;
xw = (fontdata[entry][i]&0x00F0)>>4;
xh = (fontdata[entry][i]&0x000F);
g.fillRect(
x+(int)(w*dw),
y+(int)(h*dh),
((int)((w+xw)*dw))-(int)(w*dw),
((int)((h+xh)*dh))-(int)(h*dh)
);
i++;
}
break;
default:
break;
}
}
}
jta_2.6+dfsg.orig/de/mud/terminal/colorSet.conf 0000644 0001750 0001750 00000000166 10610772601 020217 0 ustar paul paul color0 = black
color1 = red
color2 = green
color3 = yellow
color4 = blue
color5 = magenta
color6 = cyan
color7 = white jta_2.6+dfsg.orig/de/mud/terminal/SwingTerminal.java 0000644 0001750 0001750 00000103025 10610772601 021202 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.terminal;
import javax.swing.JScrollBar;
import java.awt.AWTEvent;
import java.awt.AWTEventMulticaster;
import java.awt.Color;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.FontMetrics;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.Insets;
import java.awt.Point;
import java.awt.event.AdjustmentEvent;
import java.awt.event.AdjustmentListener;
import java.awt.event.FocusEvent;
import java.awt.event.FocusListener;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.event.MouseMotionListener;
/**
* Video Display Unit emulation for Swing/AWT. This class implements all necessary
* features of a character display unit, but not the actual terminal emulation.
* It can be used as the base for terminal emulations of any kind.
*
* This is a lightweight component. It will render very badly if used
* in standard AWT components without overloaded update() method. The
* update() method must call paint() immediately without clearing the
* components graphics context or parts of the screen will simply
* disappear.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: SwingTerminal.java 511 2005-11-18 19:36:06Z marcus $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class SwingTerminal extends Component
implements VDUDisplay, KeyListener, MouseListener, MouseMotionListener {
private final static int debug = 0;
/** the VDU buffer */
private VDUBuffer buffer;
/** lightweight component definitions */
private final static long VDU_EVENTS = AWTEvent.KEY_EVENT_MASK
| AWTEvent.FOCUS_EVENT_MASK
| AWTEvent.ACTION_EVENT_MASK
| AWTEvent.MOUSE_MOTION_EVENT_MASK
| AWTEvent.MOUSE_EVENT_MASK;
private Insets insets; /* size of the border */
private boolean raised; /* indicator if the border is raised */
private Font normalFont; /* normal font */
private FontMetrics fm; /* current font metrics */
private int charWidth; /* current width of a char */
private int charHeight; /* current height of a char */
private int charDescent; /* base line descent */
private int resizeStrategy; /* current resizing strategy */
private Point selectBegin, selectEnd; /* selection coordinates */
private String selection; /* contains the selected text */
private JScrollBar scrollBar;
private SoftFont sf = new SoftFont();
private boolean colorPrinting = false; /* print display in color */
private Image backingStore = null;
/**
* Create a color representation that is brighter than the standard
* color but not what we would like to use for bold characters.
* @param clr the standard color
* @return the new brighter color
*/
private Color brighten(Color clr) {
int r,g,b;
r = (int) min(clr.getRed() * 1.2, 255.0);
g = (int) min(clr.getGreen() * 1.2, 255.0);
b = (int) min(clr.getBlue() * 1.2, 255.0);
return new Color(r, g, b);
}
/**
* Create a color representation that is darker than the standard
* color but not what we would like to use for bold characters.
* @param clr the standard color
* @return the new darker color
*/
private Color darken(Color clr) {
int r,g,b;
r = (int) max(clr.getRed() * 0.8, 0.0);
g = (int) max(clr.getGreen() * 0.8, 0.0);
b = (int) max(clr.getBlue() * 0.8, 0.0);
return new Color(r, g, b);
}
/** A list of colors used for representation of the display */
private Color color[] = {Color.black,
Color.red,
Color.green,
Color.yellow,
Color.blue,
Color.magenta,
Color.cyan,
Color.white,
null, // bold color
null, // inverted color
};
public final static int RESIZE_NONE = 0;
public final static int RESIZE_FONT = 1;
public final static int RESIZE_SCREEN = 2;
public final static int COLOR_BOLD = 8;
public final static int COLOR_INVERT = 9;
/* definitions of standards for the display unit */
private final static int COLOR_FG_STD = 7;
private final static int COLOR_BG_STD = 0;
/** User defineable cursor colors */
private Color cursorColorFG = null;
private Color cursorColorBG = null;
protected double max(double f1, double f2) {
return (f1 < f2) ? f2 : f1;
}
protected double min(double f1, double f2) {
return (f1 < f2) ? f1 : f2;
}
/**
* Create a new video display unit with the passed width and height in
* characters using a special font and font size. These features can
* be set independently using the appropriate properties.
* @param buffer a VDU buffer to be associated with the display
* @param font the font to be used (usually Monospaced)
*/
public SwingTerminal(VDUBuffer buffer, Font font) {
setVDUBuffer(buffer);
addKeyListener(this);
/* we have to make sure the tab key stays within the component */
String version = System.getProperty("java.version");
String versionStart = version.substring(0,3);
double ver = Double.parseDouble(versionStart);
if (ver >= 1.4) {
//if (version.startsWith("1.5")) {
try {
Class params[] = new Class[]{boolean.class};
SwingTerminal.class.getMethod("setFocusable", params).invoke(this, new Object[]{new Boolean(true)});
SwingTerminal.class.getMethod("setFocusTraversalKeysEnabled", params).invoke(this, new Object[]{new Boolean(false)});
} catch (Exception e) {
System.err.println("vt320: unable to reset focus handling for java version " + version);
e.printStackTrace();
}
}
// lightweight component handling
enableEvents(VDU_EVENTS);
// set the normal font to use
setFont(font);
// set the standard resize strategy
setResizeStrategy(RESIZE_FONT);
setForeground(Color.white);
setBackground(Color.black);
cursorColorFG = color[COLOR_FG_STD];
cursorColorBG = color[COLOR_BG_STD];
clearSelection();
addMouseListener(this);
addMouseMotionListener(this);
selection = null;
}
/**
* Create a display unit with size 80x24 and Font "Monospaced", size 12.
*/
public SwingTerminal(VDUBuffer buffer) {
this(buffer, new Font("Monospaced", Font.PLAIN, 11));
}
/**
* Set a new terminal (VDU) buffer.
* @param buffer new buffer
*/
public void setVDUBuffer(VDUBuffer buffer) {
this.buffer = buffer;
buffer.setDisplay(this);
}
/**
* Return the currently associated VDUBuffer.
* @return the current buffer
*/
public VDUBuffer getVDUBuffer() {
return buffer;
}
/**
* Set new color set for the display.
* @param colorset new color set
*/
public void setColorSet(Color[] colorset) {
System.arraycopy(colorset, 0, color, 0, 10);
buffer.update[0] = true;
redraw();
}
/**
* Get current color set.
* @return the color set currently associated
*/
public Color[] getColorSet() {
return color;
}
/**
* Set the font to be used for rendering the characters on screen.
* @param font the new font to be used.
*/
public void setFont(Font font) {
super.setFont(normalFont = font);
fm = getFontMetrics(font);
if (fm != null) {
charWidth = fm.charWidth('@');
charHeight = fm.getHeight();
charDescent = fm.getDescent();
}
if (buffer.update != null) buffer.update[0] = true;
redraw();
}
/**
* Set the strategy when window is resized.
* RESIZE_FONT is default.
* @param strategy the strategy
* @see #RESIZE_NONE
* @see #RESIZE_FONT
* @see #RESIZE_SCREEN
*/
public void setResizeStrategy(int strategy) {
resizeStrategy = strategy;
}
/**
* Set the border thickness and the border type.
* @param thickness border thickness in pixels, zero means no border
* @param raised a boolean indicating a raised or embossed border
*/
public void setBorder(int thickness, boolean raised) {
if (thickness == 0)
insets = null;
else
insets = new Insets(thickness + 1, thickness + 1,
thickness + 1, thickness + 1);
this.raised = raised;
}
/**
* Connect a scrollbar to the VDU. This should be done differently
* using a property change listener.
* @param scrollBar the scroll bar
*/
public void setScrollbar(JScrollBar scrollBar) {
if (scrollBar == null) return;
this.scrollBar = scrollBar;
this.scrollBar.setValues(buffer.windowBase, buffer.height, 0, buffer.bufSize - buffer.height);
this.scrollBar.addAdjustmentListener(new AdjustmentListener() {
public void adjustmentValueChanged(AdjustmentEvent evt) {
buffer.setWindowBase(evt.getValue());
}
});
}
/**
* Redraw marked lines.
*/
public void redraw() {
if (backingStore != null) {
redraw(backingStore.getGraphics());
repaint();
}
}
public void updateScrollBar() {
if (scrollBar == null) return;
scrollBar.setValues(buffer.windowBase, buffer.height, 0, buffer.bufSize);
}
protected void redraw(Graphics g) {
if (debug > 0) System.err.println("redraw()");
int xoffset = (super.getSize().width - buffer.width * charWidth) / 2;
int yoffset = (super.getSize().height - buffer.height * charHeight) / 2;
int selectStartLine = selectBegin.y - buffer.windowBase;
int selectEndLine = selectEnd.y - buffer.windowBase;
Color fg = darken(color[COLOR_FG_STD]);
Color bg = darken(color[COLOR_BG_STD]);
g.setFont(normalFont);
/* for debug only
if (update[0]) {
System.err.println("Redrawing all");
} else {
for (int l = 1; l < size.height+1; l++) {
if (update[l]) {
for (int c = 0; c < size.height-l;c++) {
if (!update[c+l]) {
System.err.println("Redrawing "+(l-1)+" - "+(l+c-2));
l=l+c;
break;
}
}
}
}
}
*/
for (int l = 0; l < buffer.height; l++) {
if (!buffer.update[0] && !buffer.update[l + 1]) continue;
buffer.update[l + 1] = false;
if (debug > 2) System.err.println("redraw(): line " + l);
for (int c = 0; c < buffer.width; c++) {
int addr = 0;
int currAttr = buffer.charAttributes[buffer.windowBase + l][c];
fg = darken(getForeground());
bg = darken(getBackground());
if ((currAttr & buffer.COLOR_FG) != 0)
fg = darken(color[((currAttr & buffer.COLOR_FG) >> buffer.COLOR_FG_SHIFT) - 1]);
if ((currAttr & buffer.COLOR_BG) != 0)
bg = darken(darken(color[((currAttr & buffer.COLOR_BG) >> buffer.COLOR_BG_SHIFT) - 1]));
if ((currAttr & VDUBuffer.BOLD) != 0) {
g.setFont(new Font(normalFont.getName(), Font.BOLD, normalFont.getSize()));
// does not work with IE6: g.setFont(normalFont.deriveFont(Font.BOLD));
if (null != color[COLOR_BOLD]) {
fg = color[COLOR_BOLD];
}
/*
if(fg.equals(Color.black)) {
fg = Color.gray;
} else {
fg = brighten(fg);
// bg = bg.brighter(); -- make some programs ugly
}
*/
} else {
g.setFont(normalFont);
}
if ((currAttr & VDUBuffer.LOW) != 0) {
fg = darken(fg);
}
if ((currAttr & VDUBuffer.INVERT) != 0) {
if (null == color[COLOR_INVERT]) {
Color swapc = bg;
bg = fg;
fg = swapc;
} else {
if (null == color[COLOR_BOLD]) {
fg = bg;
} else {
fg = color[COLOR_BOLD];
}
bg = color[COLOR_INVERT];
}
}
if (sf.inSoftFont(buffer.charArray[buffer.windowBase + l][c])) {
g.setColor(bg);
g.fillRect(c * charWidth + xoffset, l * charHeight + yoffset,
charWidth, charHeight);
g.setColor(fg);
if ((currAttr & VDUBuffer.INVISIBLE) == 0)
sf.drawChar(g, buffer.charArray[buffer.windowBase + l][c], xoffset + c * charWidth,
l * charHeight + yoffset, charWidth, charHeight);
if ((currAttr & VDUBuffer.UNDERLINE) != 0)
g.drawLine(c * charWidth + xoffset,
(l + 1) * charHeight - charDescent / 2 + yoffset,
c * charWidth + charWidth + xoffset,
(l + 1) * charHeight - charDescent / 2 + yoffset);
continue;
}
// determine the maximum of characters we can print in one go
while ((c + addr < buffer.width) &&
((buffer.charArray[buffer.windowBase + l][c + addr] < ' ') ||
(buffer.charAttributes[buffer.windowBase + l][c + addr] == currAttr)) &&
!sf.inSoftFont(buffer.charArray[buffer.windowBase + l][c + addr])) {
if (buffer.charArray[buffer.windowBase + l][c + addr] < ' ') {
buffer.charArray[buffer.windowBase + l][c + addr] = ' ';
buffer.charAttributes[buffer.windowBase + l][c + addr] = 0;
continue;
}
addr++;
}
// clear the part of the screen we want to change (fill rectangle)
g.setColor(bg);
g.fillRect(c * charWidth + xoffset, l * charHeight + yoffset,
addr * charWidth, charHeight);
g.setColor(fg);
// draw the characters, if not invisible.
if ((currAttr & VDUBuffer.INVISIBLE) == 0)
g.drawChars(buffer.charArray[buffer.windowBase + l], c, addr,
c * charWidth + xoffset,
(l + 1) * charHeight - charDescent + yoffset);
if ((currAttr & VDUBuffer.UNDERLINE) != 0)
g.drawLine(c * charWidth + xoffset,
(l + 1) * charHeight - charDescent / 2 + yoffset,
c * charWidth + addr * charWidth + xoffset,
(l + 1) * charHeight - charDescent / 2 + yoffset);
c += addr - 1;
}
// selection code, highlites line or part of it when it was
// selected previously
if (l >= selectStartLine && l <= selectEndLine) {
int selectStartColumn = (l == selectStartLine ? selectBegin.x : 0);
int selectEndColumn =
(l == selectEndLine ?
(l == selectStartLine ? selectEnd.x - selectStartColumn :
selectEnd.x) : buffer.width);
if (selectStartColumn != selectEndColumn) {
if (debug > 0)
System.err.println("select(" + selectStartColumn + "-"
+ selectEndColumn + ")");
g.setXORMode(bg);
g.fillRect(selectStartColumn * charWidth + xoffset,
l * charHeight + yoffset,
selectEndColumn * charWidth,
charHeight);
g.setPaintMode();
}
}
}
// draw cursor
if (buffer.showcursor && (
buffer.screenBase + buffer.cursorY >= buffer.windowBase &&
buffer.screenBase + buffer.cursorY < buffer.windowBase + buffer.height)
) {
g.setColor(cursorColorFG);
g.setXORMode(cursorColorBG);
g.fillRect(buffer.cursorX * charWidth + xoffset,
(buffer.cursorY + buffer.screenBase - buffer.windowBase) * charHeight + yoffset,
charWidth, charHeight);
g.setPaintMode();
g.setColor(color[COLOR_FG_STD]);
}
// draw border
if (insets != null) {
g.setColor(getBackground());
xoffset--;
yoffset--;
for (int i = insets.top - 1; i >= 0; i--)
g.draw3DRect(xoffset - i, yoffset - i,
charWidth * buffer.width + 1 + i * 2,
charHeight * buffer.height + 1 + i * 2,
raised);
}
buffer.update[0] = false;
}
/**
* Paint the current screen using the backing store image.
*/
public void paint(Graphics g) {
if (backingStore == null) {
Dimension size = super.getSize();
backingStore = createImage(size.width, size.height);
buffer.update[0] = true;
redraw();
}
if (debug > 1)
System.err.println("Clip region: " + g.getClipBounds());
g.drawImage(backingStore, 0, 0, this);
}
/*
public int print(Graphics g, PageFormat pf, int pi) throws PrinterException {
if(pi >= 1) {
return Printable.NO_SUCH_PAGE;
}
paint(g);
return Printable.PAGE_EXISTS;
}
*/
/**
* Set default for printing black&white or colorized as displayed on
* screen.
* @param colorPrint true = print in full color, default b&w only
*/
public void setColorPrinting(boolean colorPrint) {
colorPrinting = colorPrint;
}
public void print(Graphics g) {
if (debug > 0) System.err.println("DEBUG: print()");
for (int i = 0; i <= buffer.height; i++) buffer.update[i] = true;
Color fg = null, bg = null, colorSave[] = null;
if (!colorPrinting) {
fg = getForeground();
bg = getBackground();
setForeground(Color.black);
setBackground(Color.white);
colorSave = color;
color = new Color[]{Color.black,
Color.black,
Color.black,
Color.black,
Color.black,
Color.black,
Color.black,
Color.white,
null,
null,
};
}
redraw(g);
if (!colorPrinting) {
color = colorSave;
setForeground(fg);
setBackground(bg);
}
}
/**
* Convert Mouse Event coordinates into character cell coordinates
* @param evtpt the mouse point to be converted
* @return Character cell coordinate of passed point
*/
public Point mouseGetPos(Point evtpt) {
Point mousepos;
mousepos = new Point(0, 0);
int xoffset = (super.getSize().width - buffer.width * charWidth) / 2;
int yoffset = (super.getSize().height - buffer.height * charHeight) / 2;
mousepos.x = (evtpt.x - xoffset) / charWidth;
if (mousepos.x < 0) mousepos.x = 0;
if (mousepos.x >= buffer.width) mousepos.x = buffer.width - 1;
mousepos.y = (evtpt.y - yoffset) / charHeight;
if (mousepos.y < 0) mousepos.y = 0;
if (mousepos.y >= buffer.height) mousepos.y = buffer.height - 1;
return mousepos;
}
/**
* Set cursor FG and BG colors
* @param fg foreground color or null
* @param bg background color or null
*/
public void setCursorColors(Color fg, Color bg) {
if (fg == null)
cursorColorFG = color[COLOR_FG_STD];
else
cursorColorFG = fg;
if (bg == null)
cursorColorBG = color[COLOR_BG_STD];
else
cursorColorBG = bg;
repaint();
}
/**
* Reshape character display according to resize strategy.
* @see #setResizeStrategy
*/
public void setBounds(int x, int y, int w, int h) {
if (debug > 0)
System.err.println("VDU: setBounds(" + x + "," + y + "," + w + "," + h + ")");
super.setBounds(x, y, w, h);
// ignore zero bounds
if (x == 00 && y == 0 && w == 0 && h == 0) {
return;
}
if (insets != null) {
w -= insets.left + insets.right;
h -= insets.top + insets.bottom;
}
if (debug > 0)
System.err.println("VDU: looking for better match for " + normalFont);
Font tmpFont = normalFont;
String fontName = tmpFont.getName();
int fontStyle = tmpFont.getStyle();
fm = getFontMetrics(normalFont);
if (fm != null) {
charWidth = fm.charWidth('@');
charHeight = fm.getHeight();
}
switch (resizeStrategy) {
case RESIZE_SCREEN:
buffer.setScreenSize(w / charWidth, buffer.height = h / charHeight, true);
break;
case RESIZE_FONT:
int height = h / buffer.height;
int width = w / buffer.width;
fm = getFontMetrics(normalFont = new Font(fontName, fontStyle,
charHeight));
// adapt current font size (from small up to best fit)
if (fm.getHeight() < height || fm.charWidth('@') < width)
do {
fm = getFontMetrics(normalFont = new Font(fontName, fontStyle,
++charHeight));
} while (fm.getHeight() < height || fm.charWidth('@') < width);
// now check if we got a font that is too large
if (fm.getHeight() > height || fm.charWidth('@') > width)
do {
fm = getFontMetrics(normalFont = new Font(fontName, fontStyle,
--charHeight));
} while (charHeight > 1 &&
(fm.getHeight() > height ||
fm.charWidth('@') > width));
if (charHeight <= 1) {
System.err.println("VDU: error during resize, resetting");
normalFont = tmpFont;
System.err.println("VDU: disabling font/screen resize");
resizeStrategy = RESIZE_NONE;
}
setFont(normalFont);
fm = getFontMetrics(normalFont);
charWidth = fm.charWidth('@');
charHeight = fm.getHeight();
charDescent = fm.getDescent();
break;
case RESIZE_NONE:
default:
break;
}
if (debug > 0) {
System.err.println("VDU: charWidth=" + charWidth + ", " +
"charHeight=" + charHeight + ", " +
"charDescent=" + charDescent);
}
// delete the double buffer image and mark all lines
backingStore = null;
buffer.markLine(0, buffer.height);
}
/**
* Return the real size in points of the character display.
* @return Dimension the dimension of the display
* @see java.awt.Dimension
*/
public Dimension getSize() {
int xborder = 0, yborder = 0;
if (insets != null) {
xborder = insets.left + insets.right;
yborder = insets.top + insets.bottom;
}
return new Dimension(buffer.width * charWidth + xborder,
buffer.height * charHeight + yborder);
}
/**
* Return the preferred Size of the character display.
* This turns out to be the actual size.
* @return Dimension dimension of the display
* @see #size
*/
public Dimension getPreferredSize() {
return getSize();
}
/**
* The insets of the character display define the border.
* @return Insets border thickness in pixels
*/
public Insets getInsets() {
return insets;
}
public void clearSelection() {
selectBegin = new Point(0, 0);
selectEnd = new Point(0, 0);
selection = null;
}
public String getSelection() {
return selection;
}
private boolean buttonCheck(int modifiers, int mask) {
return (modifiers & mask) == mask;
}
public void mouseMoved(MouseEvent evt) {
/* nothing yet we do here */
}
public void mouseDragged(MouseEvent evt) {
if (buttonCheck(evt.getModifiers(), MouseEvent.BUTTON1_MASK) ||
// Windows NT/95 etc: returns 0, which is a bug
evt.getModifiers() == 0) {
int xoffset = (super.getSize().width - buffer.width * charWidth) / 2;
int yoffset = (super.getSize().height - buffer.height * charHeight) / 2;
int x = (evt.getX() - xoffset) / charWidth;
int y = (evt.getY() - yoffset) / charHeight + buffer.windowBase;
int oldx = selectEnd.x, oldy = selectEnd.y;
if ((x <= selectBegin.x && y <= selectBegin.y)) {
selectBegin.x = x;
selectBegin.y = y;
} else {
selectEnd.x = x;
selectEnd.y = y;
}
if (oldx != x || oldy != y) {
buffer.update[0] = true;
if (debug > 0)
System.err.println("select([" + selectBegin.x + "," + selectBegin.y + "]," +
"[" + selectEnd.x + "," + selectEnd.y + "])");
redraw();
}
}
}
public void mouseClicked(MouseEvent evt) {
/* nothing yet we do here */
}
public void mouseEntered(MouseEvent evt) {
/* nothing yet we do here */
}
public void mouseExited(MouseEvent evt) {
/* nothing yet we do here */
}
/**
* Handle mouse pressed events for copy & paste.
* @param evt the event that occured
* @see java.awt.event.MouseEvent
*/
public void mousePressed(MouseEvent evt) {
requestFocus();
int xoffset = (super.getSize().width - buffer.width * charWidth) / 2;
int yoffset = (super.getSize().height - buffer.height * charHeight) / 2;
if (buffer instanceof VDUInput) {
((VDUInput) buffer).mousePressed(xoffset, yoffset, evt.getModifiers());
}
// looks like we get no modifiers here ... ... We do? -Marcus
if (buttonCheck(evt.getModifiers(), MouseEvent.BUTTON1_MASK)) {
selectBegin.x = (evt.getX() - xoffset) / charWidth;
selectBegin.y = (evt.getY() - yoffset) / charHeight + buffer.windowBase;
selectEnd.x = selectBegin.x;
selectEnd.y = selectBegin.y;
}
}
/**
* Handle mouse released events for copy & paste.
* @param evt the mouse event
*/
public void mouseReleased(MouseEvent evt) {
int xoffset = (super.getSize().width - buffer.width * charWidth) / 2;
int yoffset = (super.getSize().height - buffer.height * charHeight) / 2;
if (buffer instanceof VDUInput) {
((VDUInput) buffer).mousePressed(xoffset, yoffset, evt.getModifiers());
}
if (buttonCheck(evt.getModifiers(), MouseEvent.BUTTON1_MASK)) {
mouseDragged(evt);
if (selectBegin.x == selectEnd.x && selectBegin.y == selectEnd.y) {
buffer.update[0] = true;
redraw();
return;
}
selection = "";
// fix end.x and end.y, they can get over the border
if (selectEnd.x < 0) selectEnd.x = 0;
if (selectEnd.y < 0) selectEnd.y = 0;
if (selectEnd.y >= buffer.charArray.length)
selectEnd.y = buffer.charArray.length - 1;
if (selectEnd.x > buffer.charArray[0].length)
selectEnd.x = buffer.charArray[0].length;
// Initial buffer space for selectEnd - selectBegin + 1 lines
// NOTE: Selection includes invisible text as spaces!
// (also leaves invisible non-whitespace selection ending as spaces)
StringBuffer selectionBuf =
new StringBuffer(buffer.charArray[0].length * (selectEnd.y - selectBegin.y + 1));
for (int l = selectBegin.y; l <= selectEnd.y; l++) {
int start, end;
start = (l == selectBegin.y ? start = selectBegin.x : 0);
end = (l == selectEnd.y ? end = selectEnd.x : buffer.charArray[l].length);
boolean newlineFound = false;
char ch = ' ';
for (int i = start; i < end; i++) {
if ((buffer.charAttributes[l][i] & VDUBuffer.INVISIBLE) != 0)
ch = ' ';
else
ch = buffer.charArray[l][i];
if (ch == '\n')
newlineFound = true;
selectionBuf.append(ch);
}
if (!newlineFound)
selectionBuf.append('\n');
// Trim all spaces from end of line, like xterm does.
selection += ("-" + (selectionBuf.toString())).trim().substring(1);
if (end == buffer.charArray[l].length)
selection += "\n";
}
}
}
public void keyTyped(KeyEvent e) {
if (buffer != null && buffer instanceof VDUInput)
((VDUInput) buffer).keyTyped(e.getKeyCode(), e.getKeyChar(), getModifiers(e));
}
public void keyPressed(KeyEvent e) {
if (buffer != null && buffer instanceof VDUInput)
((VDUInput) buffer).keyPressed(e.getKeyCode(), e.getKeyChar(), getModifiers(e));
}
public void keyReleased(KeyEvent e) {
// ignore
}
// lightweight component event handling
private MouseListener mouseListener;
/**
* Add a mouse listener to the VDU. This is the implementation for
* the lightweight event handling.
* @param listener the new mouse listener
*/
public void addMouseListener(MouseListener listener) {
mouseListener = AWTEventMulticaster.add(mouseListener, listener);
enableEvents(AWTEvent.MOUSE_EVENT_MASK);
}
/**
* Remove a mouse listener to the VDU. This is the implementation for
* the lightweight event handling.
* @param listener the mouse listener to remove
*/
public void removeMouseListener(MouseListener listener) {
mouseListener = AWTEventMulticaster.remove(mouseListener, listener);
}
private MouseMotionListener mouseMotionListener;
/**
* Add a mouse motion listener to the VDU. This is the implementation for
* the lightweight event handling.
* @param listener the mouse motion listener
*/
public void addMouseMotionListener(MouseMotionListener listener) {
mouseMotionListener = AWTEventMulticaster.add(mouseMotionListener, listener);
enableEvents(AWTEvent.MOUSE_EVENT_MASK);
}
/**
* Remove a mouse motion listener to the VDU. This is the implementation for
* the lightweight event handling.
* @param listener the mouse motion listener to remove
*/
public void removeMouseMotionListener(MouseMotionListener listener) {
mouseMotionListener =
AWTEventMulticaster.remove(mouseMotionListener, listener);
}
/**
* Process mouse events for this component. It will call the
* methods (mouseClicked() etc) in the added mouse listeners.
* @param evt the dispatched mouse event
*/
public void processMouseEvent(MouseEvent evt) {
// handle simple mouse events
if (mouseListener != null)
switch (evt.getID()) {
case MouseEvent.MOUSE_CLICKED:
mouseListener.mouseClicked(evt);
break;
case MouseEvent.MOUSE_ENTERED:
mouseListener.mouseEntered(evt);
break;
case MouseEvent.MOUSE_EXITED:
mouseListener.mouseExited(evt);
break;
case MouseEvent.MOUSE_PRESSED:
mouseListener.mousePressed(evt);
break;
case MouseEvent.MOUSE_RELEASED:
mouseListener.mouseReleased(evt);
break;
}
super.processMouseEvent(evt);
}
/**
* Process mouse motion events for this component. It will call the
* methods (mouseDragged() etc) in the added mouse motion listeners.
* @param evt the dispatched mouse event
*/
public void processMouseMotionEvent(MouseEvent evt) {
// handle mouse motion events
if (mouseMotionListener != null)
switch (evt.getID()) {
case MouseEvent.MOUSE_DRAGGED:
mouseMotionListener.mouseDragged(evt);
break;
case MouseEvent.MOUSE_MOVED:
mouseMotionListener.mouseMoved(evt);
break;
}
super.processMouseMotionEvent(evt);
}
private KeyListener keyListener;
/**
* Add a key listener to the VDU. This is necessary to be able to receive
* keyboard input from this component. It is a prerequisite for a
* lightweigh component.
* @param listener the key listener
*/
public void addKeyListener(KeyListener listener) {
keyListener = AWTEventMulticaster.add(keyListener, listener);
enableEvents(AWTEvent.KEY_EVENT_MASK);
}
/**
* Remove key listener from the VDU. It is a prerequisite for a
* lightweigh component.
* @param listener the key listener to remove
*/
public void removeKeyListener(KeyListener listener) {
keyListener = AWTEventMulticaster.remove(keyListener, listener);
}
/**
* Process key events for this component.
* @param evt the dispatched key event
*/
public void processKeyEvent(KeyEvent evt) {
if (keyListener != null)
switch (evt.getID()) {
case KeyEvent.KEY_PRESSED:
keyListener.keyPressed(evt);
break;
case KeyEvent.KEY_RELEASED:
keyListener.keyReleased(evt);
break;
case KeyEvent.KEY_TYPED:
keyListener.keyTyped(evt);
break;
}
// consume TAB keys if they originate from our component
if (evt.getKeyCode() == KeyEvent.VK_TAB && evt.getSource() == this)
evt.consume();
super.processKeyEvent(evt);
}
FocusListener focusListener;
public void addFocusListener(FocusListener listener) {
focusListener = AWTEventMulticaster.add(focusListener, listener);
}
public void removeFocusListener(FocusListener listener) {
focusListener = AWTEventMulticaster.remove(focusListener, listener);
}
public void processFocusEvent(FocusEvent evt) {
if (focusListener != null)
switch (evt.getID()) {
case FocusEvent.FOCUS_GAINED:
focusListener.focusGained(evt);
break;
case FocusEvent.FOCUS_LOST:
focusListener.focusLost(evt);
break;
}
super.processFocusEvent(evt);
}
private int getModifiers(KeyEvent e) {
return
(e.isControlDown() ? VDUInput.KEY_CONTROL : 0) |
(e.isShiftDown() ? VDUInput.KEY_SHIFT : 0) |
(e.isAltDown() ? VDUInput.KEY_ALT : 0) |
(e.isActionKey() ? VDUInput.KEY_ACTION : 0);
}
}
jta_2.6+dfsg.orig/de/mud/terminal/VDUInput.java 0000644 0001750 0001750 00000005266 10610772601 020105 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.terminal;
import java.util.Properties;
/**
* An interface for a terminal that accepts input from keyboard and mouse.
*
* @author Matthias L. Jugel, Marcus Mei�ner
* @version $Id: VDUInput.java 499 2005-09-29 08:24:54Z leo $
*/
public interface VDUInput {
public final static int KEY_CONTROL = 0x01;
public final static int KEY_SHIFT = 0x02;
public final static int KEY_ALT = 0x04;
public final static int KEY_ACTION = 0x08;
/**
* Direct access to writing data ...
* @param b
*/
void write(byte b[]);
/**
* Terminal is mouse-aware and requires (x,y) coordinates of
* on the terminal (character coordinates) and the button clicked.
* @param x
* @param y
* @param modifiers
*/
void mousePressed(int x, int y, int modifiers);
/**
* Terminal is mouse-aware and requires the coordinates and button
* of the release.
* @param x
* @param y
* @param modifiers
*/
void mouseReleased(int x, int y, int modifiers);
/**
* Override the standard key codes used by the terminal emulation.
* @param codes a properties object containing key code definitions
*/
void setKeyCodes(Properties codes);
/**
* main keytyping event handler...
* @param keyCode the key code
* @param keyChar the character represented by the key
* @param modifiers shift/alt/control modifiers
*/
void keyPressed(int keyCode, char keyChar, int modifiers);
/**
* Handle key Typed events for the terminal, this will get
* all normal key types, but no shift/alt/control/numlock.
* @param keyCode the key code
* @param keyChar the character represented by the key
* @param modifiers shift/alt/control modifiers
*/
void keyTyped(int keyCode, char keyChar, int modifiers);
}
jta_2.6+dfsg.orig/de/mud/terminal/VDUBuffer.java 0000644 0001750 0001750 00000057702 10610772601 020221 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.terminal;
/**
* Implementation of a Video Display Unit (VDU) buffer. This class contains
* all methods to manipulate the buffer that stores characters and their
* attributes as well as the regions displayed.
*
* @author Matthias L. Jugel, Marcus Mei�ner
* @version $Id: VDUBuffer.java 503 2005-10-24 07:34:13Z marcus $
*/
public class VDUBuffer {
/** The current version id tag */
public final static String ID = "$Id: VDUBuffer.java 503 2005-10-24 07:34:13Z marcus $";
/** Enable debug messages. */
public final static int debug = 0;
public int height, width; /* rows and columns */
public boolean[] update; /* contains the lines that need update */
public char[][] charArray; /* contains the characters */
public int[][] charAttributes; /* contains character attrs */
public int bufSize;
public int maxBufSize; /* buffer sizes */
public int screenBase; /* the actual screen start */
public int windowBase; /* where the start displaying */
public int scrollMarker; /* marks the last line inserted */
private int topMargin; /* top scroll margin */
private int bottomMargin; /* bottom scroll margin */
// cursor variables
protected boolean showcursor = true;
protected int cursorX, cursorY;
/** Scroll up when inserting a line. */
public final static boolean SCROLL_UP = false;
/** Scroll down when inserting a line. */
public final static boolean SCROLL_DOWN = true;
/** Make character normal. */
public final static int NORMAL = 0x00;
/** Make character bold. */
public final static int BOLD = 0x01;
/** Underline character. */
public final static int UNDERLINE = 0x02;
/** Invert character. */
public final static int INVERT = 0x04;
/** Lower intensity character. */
public final static int LOW = 0x08;
/** Invisible character. */
public final static int INVISIBLE = 0x10;
/** how much to left shift the foreground color */
public final static int COLOR_FG_SHIFT = 5;
/** how much to left shift the background color */
public final static int COLOR_BG_SHIFT = 9;
/** color mask */
public final static int COLOR = 0x1fe0;
/** foreground color mask */
public final static int COLOR_FG = 0x1e0;
/** background color mask */
public final static int COLOR_BG = 0x1e00;
/**
* Create a new video display buffer with the passed width and height in
* characters.
* @param width the length of the character lines
* @param height the amount of lines on the screen
*/
public VDUBuffer(int width, int height) {
// set the display screen size
setScreenSize(width, height, false);
}
/**
* Create a standard video display buffer with 80 columns and 24 lines.
*/
public VDUBuffer() {
this(80, 24);
}
/**
* Put a character on the screen with normal font and outline.
* The character previously on that position will be overwritten.
* You need to call redraw() to update the screen.
* @param c x-coordinate (column)
* @param l y-coordinate (line)
* @param ch the character to show on the screen
* @see #insertChar
* @see #deleteChar
* @see #redraw
*/
public void putChar(int c, int l, char ch) {
putChar(c, l, ch, NORMAL);
}
/**
* Put a character on the screen with specific font and outline.
* The character previously on that position will be overwritten.
* You need to call redraw() to update the screen.
* @param c x-coordinate (column)
* @param l y-coordinate (line)
* @param ch the character to show on the screen
* @param attributes the character attributes
* @see #BOLD
* @see #UNDERLINE
* @see #INVERT
* @see #INVISIBLE
* @see #NORMAL
* @see #LOW
* @see #insertChar
* @see #deleteChar
* @see #redraw
*/
public void putChar(int c, int l, char ch, int attributes) {
c = checkBounds(c, 0, width - 1);
l = checkBounds(l, 0, height - 1);
charArray[screenBase + l][c] = ch;
charAttributes[screenBase + l][c] = attributes;
markLine(l, 1);
}
/**
* Get the character at the specified position.
* @param c x-coordinate (column)
* @param l y-coordinate (line)
* @see #putChar
*/
public char getChar(int c, int l) {
c = checkBounds(c, 0, width - 1);
l = checkBounds(l, 0, height - 1);
return charArray[screenBase + l][c];
}
/**
* Get the attributes for the specified position.
* @param c x-coordinate (column)
* @param l y-coordinate (line)
* @see #putChar
*/
public int getAttributes(int c, int l) {
c = checkBounds(c, 0, width - 1);
l = checkBounds(l, 0, height - 1);
return charAttributes[screenBase + l][c];
}
/**
* Insert a character at a specific position on the screen.
* All character right to from this position will be moved one to the right.
* You need to call redraw() to update the screen.
* @param c x-coordinate (column)
* @param l y-coordinate (line)
* @param ch the character to insert
* @param attributes the character attributes
* @see #BOLD
* @see #UNDERLINE
* @see #INVERT
* @see #INVISIBLE
* @see #NORMAL
* @see #LOW
* @see #putChar
* @see #deleteChar
* @see #redraw
*/
public void insertChar(int c, int l, char ch, int attributes) {
c = checkBounds(c, 0, width - 1);
l = checkBounds(l, 0, height - 1);
System.arraycopy(charArray[screenBase + l], c,
charArray[screenBase + l], c + 1, width - c - 1);
System.arraycopy(charAttributes[screenBase + l], c,
charAttributes[screenBase + l], c + 1, width - c - 1);
putChar(c, l, ch, attributes);
}
/**
* Delete a character at a given position on the screen.
* All characters right to the position will be moved one to the left.
* You need to call redraw() to update the screen.
* @param c x-coordinate (column)
* @param l y-coordinate (line)
* @see #putChar
* @see #insertChar
* @see #redraw
*/
public void deleteChar(int c, int l) {
c = checkBounds(c, 0, width - 1);
l = checkBounds(l, 0, height - 1);
if (c < width - 1) {
System.arraycopy(charArray[screenBase + l], c + 1,
charArray[screenBase + l], c, width - c - 1);
System.arraycopy(charAttributes[screenBase + l], c + 1,
charAttributes[screenBase + l], c, width - c - 1);
}
putChar(width - 1, l, (char) 0);
}
/**
* Put a String at a specific position. Any characters previously on that
* position will be overwritten. You need to call redraw() for screen update.
* @param c x-coordinate (column)
* @param l y-coordinate (line)
* @param s the string to be shown on the screen
* @see #BOLD
* @see #UNDERLINE
* @see #INVERT
* @see #INVISIBLE
* @see #NORMAL
* @see #LOW
* @see #putChar
* @see #insertLine
* @see #deleteLine
* @see #redraw
*/
public void putString(int c, int l, String s) {
putString(c, l, s, NORMAL);
}
/**
* Put a String at a specific position giving all characters the same
* attributes. Any characters previously on that position will be
* overwritten. You need to call redraw() to update the screen.
* @param c x-coordinate (column)
* @param l y-coordinate (line)
* @param s the string to be shown on the screen
* @param attributes character attributes
* @see #BOLD
* @see #UNDERLINE
* @see #INVERT
* @see #INVISIBLE
* @see #NORMAL
* @see #LOW
* @see #putChar
* @see #insertLine
* @see #deleteLine
* @see #redraw
*/
public void putString(int c, int l, String s, int attributes) {
for (int i = 0; i < s.length() && c + i < width; i++)
putChar(c + i, l, s.charAt(i), attributes);
}
/**
* Insert a blank line at a specific position.
* The current line and all previous lines are scrolled one line up. The
* top line is lost. You need to call redraw() to update the screen.
* @param l the y-coordinate to insert the line
* @see #deleteLine
* @see #redraw
*/
public void insertLine(int l) {
insertLine(l, 1, SCROLL_UP);
}
/**
* Insert blank lines at a specific position.
* You need to call redraw() to update the screen
* @param l the y-coordinate to insert the line
* @param n amount of lines to be inserted
* @see #deleteLine
* @see #redraw
*/
public void insertLine(int l, int n) {
insertLine(l, n, SCROLL_UP);
}
/**
* Insert a blank line at a specific position. Scroll text according to
* the argument.
* You need to call redraw() to update the screen
* @param l the y-coordinate to insert the line
* @param scrollDown scroll down
* @see #deleteLine
* @see #SCROLL_UP
* @see #SCROLL_DOWN
* @see #redraw
*/
public void insertLine(int l, boolean scrollDown) {
insertLine(l, 1, scrollDown);
}
/**
* Insert blank lines at a specific position.
* The current line and all previous lines are scrolled one line up. The
* top line is lost. You need to call redraw() to update the screen.
* @param l the y-coordinate to insert the line
* @param n number of lines to be inserted
* @param scrollDown scroll down
* @see #deleteLine
* @see #SCROLL_UP
* @see #SCROLL_DOWN
* @see #redraw
*/
public synchronized void insertLine(int l, int n, boolean scrollDown) {
l = checkBounds(l, 0, height - 1);
char cbuf[][] = null;
int abuf[][] = null;
int offset = 0;
int oldBase = screenBase;
if (l > bottomMargin) /* We do not scroll below bottom margin (below the scrolling region). */
return;
int top = (l < topMargin ?
0 : (l > bottomMargin ?
(bottomMargin + 1 < height ?
bottomMargin + 1 : height - 1) : topMargin));
int bottom = (l > bottomMargin ?
height - 1 : (l < topMargin ?
(topMargin > 0 ?
topMargin - 1 : 0) : bottomMargin));
// System.out.println("l is "+l+", top is "+top+", bottom is "+bottom+", bottomargin is "+bottomMargin+", topMargin is "+topMargin);
if (scrollDown) {
if (n > (bottom - top)) n = (bottom - top);
cbuf = new char[bottom - l - (n - 1)][width];
abuf = new int[bottom - l - (n - 1)][width];
System.arraycopy(charArray, oldBase + l, cbuf, 0, bottom - l - (n - 1));
System.arraycopy(charAttributes, oldBase + l,
abuf, 0, bottom - l - (n - 1));
System.arraycopy(cbuf, 0, charArray, oldBase + l + n,
bottom - l - (n - 1));
System.arraycopy(abuf, 0, charAttributes, oldBase + l + n,
bottom - l - (n - 1));
cbuf = charArray;
abuf = charAttributes;
} else {
try {
if (n > (bottom - top) + 1) n = (bottom - top) + 1;
if (bufSize < maxBufSize) {
if (bufSize + n > maxBufSize) {
offset = n - (maxBufSize - bufSize);
scrollMarker += offset;
bufSize = maxBufSize;
screenBase = maxBufSize - height - 1;
windowBase = screenBase;
} else {
scrollMarker += n;
screenBase += n;
windowBase += n;
bufSize += n;
}
cbuf = new char[bufSize][width];
abuf = new int[bufSize][width];
} else {
offset = n;
cbuf = charArray;
abuf = charAttributes;
}
// copy anything from the top of the buffer (+offset) to the new top
// up to the screenBase.
if (oldBase > 0) {
System.arraycopy(charArray, offset,
cbuf, 0,
oldBase - offset);
System.arraycopy(charAttributes, offset,
abuf, 0,
oldBase - offset);
}
// copy anything from the top of the screen (screenBase) up to the
// topMargin to the new screen
if (top > 0) {
System.arraycopy(charArray, oldBase,
cbuf, screenBase,
top);
System.arraycopy(charAttributes, oldBase,
abuf, screenBase,
top);
}
// copy anything from the topMargin up to the amount of lines inserted
// to the gap left over between scrollback buffer and screenBase
if (oldBase > 0) {
System.arraycopy(charArray, oldBase + top,
cbuf, oldBase - offset,
n);
System.arraycopy(charAttributes, oldBase + top,
abuf, oldBase - offset,
n);
}
// copy anything from topMargin + n up to the line linserted to the
// topMargin
System.arraycopy(charArray, oldBase + top + n,
cbuf, screenBase + top,
l - top - (n - 1));
System.arraycopy(charAttributes, oldBase + top + n,
abuf, screenBase + top,
l - top - (n - 1));
//
// copy the all lines next to the inserted to the new buffer
if (l < height - 1) {
System.arraycopy(charArray, oldBase + l + 1,
cbuf, screenBase + l + 1,
(height - 1) - l);
System.arraycopy(charAttributes, oldBase + l + 1,
abuf, screenBase + l + 1,
(height - 1) - l);
}
} catch (ArrayIndexOutOfBoundsException e) {
// this should not happen anymore, but I will leave the code
// here in case something happens anyway. That code above is
// so complex I always have a hard time understanding what
// I did, even though there are comments
System.err.println("*** Error while scrolling up:");
System.err.println("--- BEGIN STACK TRACE ---");
e.printStackTrace();
System.err.println("--- END STACK TRACE ---");
System.err.println("bufSize=" + bufSize + ", maxBufSize=" + maxBufSize);
System.err.println("top=" + top + ", bottom=" + bottom);
System.err.println("n=" + n + ", l=" + l);
System.err.println("screenBase=" + screenBase + ", windowBase=" + windowBase);
System.err.println("oldBase=" + oldBase);
System.err.println("size.width=" + width + ", size.height=" + height);
System.err.println("abuf.length=" + abuf.length + ", cbuf.length=" + cbuf.length);
System.err.println("*** done dumping debug information");
}
}
// this is a little helper to mark the scrolling
scrollMarker -= n;
for (int i = 0; i < n; i++) {
cbuf[(screenBase + l) + (scrollDown ? i : -i)] = new char[width];
abuf[(screenBase + l) + (scrollDown ? i : -i)] = new int[width];
}
charArray = cbuf;
charAttributes = abuf;
if (scrollDown)
markLine(l, bottom - l + 1);
else
markLine(top, l - top + 1);
display.updateScrollBar();
}
/**
* Delete a line at a specific position. Subsequent lines will be scrolled
* up to fill the space and a blank line is inserted at the end of the
* screen.
* @param l the y-coordinate to insert the line
* @see #deleteLine
*/
public void deleteLine(int l) {
l = checkBounds(l, 0, height - 1);
int bottom = (l > bottomMargin ? height - 1:
(l < topMargin?topMargin:bottomMargin + 1));
System.arraycopy(charArray, screenBase + l + 1,
charArray, screenBase + l, bottom - l - 1);
System.arraycopy(charAttributes, screenBase + l + 1,
charAttributes, screenBase + l, bottom - l - 1);
charArray[screenBase + bottom - 1] = new char[width];
charAttributes[screenBase + bottom - 1] = new int[width];
markLine(l, bottom - l);
}
/**
* Delete a rectangular portion of the screen.
* You need to call redraw() to update the screen.
* @param c x-coordinate (column)
* @param l y-coordinate (row)
* @param w with of the area in characters
* @param h height of the area in characters
* @param curAttr attribute to fill
* @see #deleteChar
* @see #deleteLine
* @see #redraw
*/
public void deleteArea(int c, int l, int w, int h, int curAttr) {
c = checkBounds(c, 0, width - 1);
l = checkBounds(l, 0, height - 1);
char cbuf[] = new char[w];
int abuf[] = new int[w];
for (int i = 0; i < w; i++) abuf[i] = curAttr;
for (int i = 0; i < h && l + i < height; i++) {
System.arraycopy(cbuf, 0, charArray[screenBase + l + i], c, w);
System.arraycopy(abuf, 0, charAttributes[screenBase + l + i], c, w);
}
markLine(l, h);
}
/**
* Delete a rectangular portion of the screen.
* You need to call redraw() to update the screen.
* @param c x-coordinate (column)
* @param l y-coordinate (row)
* @param w with of the area in characters
* @param h height of the area in characters
* @see #deleteChar
* @see #deleteLine
* @see #redraw
*/
public void deleteArea(int c, int l, int w, int h) {
c = checkBounds(c, 0, width - 1);
l = checkBounds(l, 0, height - 1);
char cbuf[] = new char[w];
int abuf[] = new int[w];
for (int i = 0; i < h && l + i < height; i++) {
System.arraycopy(cbuf, 0, charArray[screenBase + l + i], c, w);
System.arraycopy(abuf, 0, charAttributes[screenBase + l + i], c, w);
}
markLine(l, h);
}
/**
* Sets whether the cursor is visible or not.
* @param doshow
*/
public void showCursor(boolean doshow) {
if (doshow != showcursor)
markLine(cursorY, 1);
showcursor = doshow;
}
/**
* Puts the cursor at the specified position.
* @param c column
* @param l line
*/
public void setCursorPosition(int c, int l) {
cursorX = checkBounds(c, 0, width - 1);
cursorY = checkBounds(l, 0, height - 1);
markLine(cursorY, 1);
}
/**
* Get the current column of the cursor position.
*/
public int getCursorColumn() {
return cursorX;
}
/**
* Get the current line of the cursor position.
*/
public int getCursorRow() {
return cursorY;
}
/**
* Set the current window base. This allows to view the scrollback buffer.
* @param line the line where the screen window starts
* @see #setBufferSize
* @see #getBufferSize
*/
public void setWindowBase(int line) {
if (line > screenBase)
line = screenBase;
else if (line < 0) line = 0;
windowBase = line;
update[0] = true;
redraw();
}
/**
* Get the current window base.
* @see #setWindowBase
*/
public int getWindowBase() {
return windowBase;
}
/**
* Set the top scroll margin for the screen. If the current bottom margin
* is smaller it will become the top margin and the line will become the
* bottom margin.
* @param l line that is the margin
*/
public void setTopMargin(int l) {
if (l > bottomMargin) {
topMargin = bottomMargin;
bottomMargin = l;
} else
topMargin = l;
if (topMargin < 0) topMargin = 0;
if (bottomMargin > height - 1) bottomMargin = height - 1;
}
/**
* Get the top scroll margin.
*/
public int getTopMargin() {
return topMargin;
}
/**
* Set the bottom scroll margin for the screen. If the current top margin
* is bigger it will become the bottom margin and the line will become the
* top margin.
* @param l line that is the margin
*/
public void setBottomMargin(int l) {
if (l < topMargin) {
bottomMargin = topMargin;
topMargin = l;
} else
bottomMargin = l;
if (topMargin < 0) topMargin = 0;
if (bottomMargin > height - 1) bottomMargin = height - 1;
}
/**
* Get the bottom scroll margin.
*/
public int getBottomMargin() {
return bottomMargin;
}
/**
* Set scrollback buffer size.
* @param amount new size of the buffer
*/
public void setBufferSize(int amount) {
if (amount < height) amount = height;
if (amount < maxBufSize) {
char cbuf[][] = new char[amount][width];
int abuf[][] = new int[amount][width];
int copyStart = bufSize - amount < 0 ? 0 : bufSize - amount;
int copyCount = bufSize - amount < 0 ? bufSize : amount;
if (charArray != null)
System.arraycopy(charArray, copyStart, cbuf, 0, copyCount);
if (charAttributes != null)
System.arraycopy(charAttributes, copyStart, abuf, 0, copyCount);
charArray = cbuf;
charAttributes = abuf;
bufSize = copyCount;
screenBase = bufSize - height;
windowBase = screenBase;
}
maxBufSize = amount;
update[0] = true;
redraw();
}
/**
* Retrieve current scrollback buffer size.
* @see #setBufferSize
*/
public int getBufferSize() {
return bufSize;
}
/**
* Retrieve maximum buffer Size.
* @see #getBufferSize
*/
public int getMaxBufferSize() {
return maxBufSize;
}
/**
* Change the size of the screen. This will include adjustment of the
* scrollback buffer.
* @param w of the screen
* @param h of the screen
*/
public void setScreenSize(int w, int h, boolean broadcast) {
char cbuf[][];
int abuf[][];
int bsize = bufSize;
if (w < 1 || h < 1) return;
if (debug > 0)
System.err.println("VDU: screen size [" + w + "," + h + "]");
if (h > maxBufSize)
maxBufSize = h;
if (h > bufSize) {
bufSize = h;
screenBase = 0;
windowBase = 0;
}
if (windowBase + h >= bufSize)
windowBase = bufSize - h;
if (screenBase + h >= bufSize)
screenBase = bufSize - h;
cbuf = new char[bufSize][w];
abuf = new int[bufSize][w];
if (charArray != null && charAttributes != null) {
for (int i = 0; i < bsize && i < bufSize; i++) {
System.arraycopy(charArray[i], 0, cbuf[i], 0,
w < width ? w : width);
System.arraycopy(charAttributes[i], 0, abuf[i], 0,
w < width ? w : width);
}
}
charArray = cbuf;
charAttributes = abuf;
width = w;
height = h;
topMargin = 0;
bottomMargin = h - 1;
update = new boolean[h + 1];
update[0] = true;
/* FIXME: ???
if(resizeStrategy == RESIZE_FONT)
setBounds(getBounds());
*/
}
/**
* Get amount of rows on the screen.
*/
public int getRows() {
return height;
}
/**
* Get amount of columns on the screen.
*/
public int getColumns() {
return width;
}
/**
* Mark lines to be updated with redraw().
* @param l starting line
* @param n amount of lines to be updated
* @see #redraw
*/
public void markLine(int l, int n) {
l = checkBounds(l, 0, height - 1);
for (int i = 0; (i < n) && (l + i < height); i++)
update[l + i + 1] = true;
}
private int checkBounds(int value, int lower, int upper) {
if (value < lower) return lower;
if (value > upper) return upper;
return value;
}
/** a generic display that should redraw on demand */
protected VDUDisplay display;
public void setDisplay(VDUDisplay display) {
this.display = display;
}
/**
* Trigger a redraw on the display.
*/
protected void redraw() {
if (display != null)
display.redraw();
}
}
jta_2.6+dfsg.orig/de/mud/terminal/vt320.java 0000644 0001750 0001750 00000251444 10610772601 017306 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.terminal;
import java.util.Properties;
import java.awt.event.KeyEvent;
/**
* Implementation of a VT terminal emulation plus ANSI compatible.
*
* Maintainer: Marcus Mei\u00dfner
*
* @version $Id: vt320.java 507 2005-10-25 10:14:52Z marcus $
* @author Matthias L. Jugel, Marcus Mei\u00dfner
*/
public abstract class vt320 extends VDUBuffer implements VDUInput {
/** The current version id tag.
* $Id: vt320.java 507 2005-10-25 10:14:52Z marcus $
*/
public final static String ID = "$Id: vt320.java 507 2005-10-25 10:14:52Z marcus $";
/** the debug level */
private final static int debug = 0;
/**
* Write an answer back to the remote host. This is needed to be able to
* send terminal answers requests like status and type information.
* @param b the array of bytes to be sent
*/
public abstract void write(byte[] b);
/**
* Play the beep sound ...
*/
public void beep() { /* do nothing by default */
}
/**
* Put string at current cursor position. Moves cursor
* according to the String. Does NOT wrap.
* @param s the string
*/
public void putString(String s) {
int len = s.length();
// System.err.println("'"+s+"'");
if (len > 0) {
markLine(R, 1);
for (int i = 0; i < len; i++) {
// System.err.print(s.charAt(i)+"("+(int)s.charAt(i)+")");
putChar(s.charAt(i), false);
}
setCursorPosition(C, R);
redraw();
}
}
protected void sendTelnetCommand(byte cmd) {
}
/**
* Sent the changed window size from the terminal to all listeners.
*/
protected void setWindowSize(int c, int r) {
/* To be overridden by Terminal.java */
}
public void setScreenSize(int c, int r, boolean broadcast) {
int oldrows = getRows(), oldcols = getColumns();
if (debug>2) System.err.println("setscreensize ("+c+","+r+","+broadcast+")");
super.setScreenSize(c,r,false);
/* Tricky, since the VDUBuffer works strangely. */
if (r > oldrows) {
setCursorPosition(C, R + (r-oldrows));
redraw();
}
if (broadcast) {
setWindowSize(c, r); /* broadcast up */
}
}
/**
* Create a new vt320 terminal and intialize it with useful settings.
*/
public vt320(int width, int height) {
super(width, height);
setVMS(false);
setIBMCharset(false);
setTerminalID("vt320");
setBufferSize(100);
//setBorder(2, false);
int nw = getColumns();
if (nw < 132) nw = 132; //catch possible later 132/80 resizes
Tabs = new byte[nw];
for (int i = 0; i < nw; i += 8) {
Tabs[i] = 1;
}
/* top row of numpad */
PF1 = "\u001bOP";
PF2 = "\u001bOQ";
PF3 = "\u001bOR";
PF4 = "\u001bOS";
/* the 3x2 keyblock on PC keyboards */
Insert = new String[4];
Remove = new String[4];
KeyHome = new String[4];
KeyEnd = new String[4];
NextScn = new String[4];
PrevScn = new String[4];
Escape = new String[4];
BackSpace = new String[4];
TabKey = new String[4];
Insert[0] = Insert[1] = Insert[2] = Insert[3] = "\u001b[2~";
Remove[0] = Remove[1] = Remove[2] = Remove[3] = "\u001b[3~";
PrevScn[0] = PrevScn[1] = PrevScn[2] = PrevScn[3] = "\u001b[5~";
NextScn[0] = NextScn[1] = NextScn[2] = NextScn[3] = "\u001b[6~";
KeyHome[0] = KeyHome[1] = KeyHome[2] = KeyHome[3] = "\u001b[H";
KeyEnd[0] = KeyEnd[1] = KeyEnd[2] = KeyEnd[3] = "\u001b[F";
Escape[0] = Escape[1] = Escape[2] = Escape[3] = "\u001b";
if (vms) {
BackSpace[1] = "" + (char) 10; // VMS shift deletes word back
BackSpace[2] = "\u0018"; // VMS control deletes line back
BackSpace[0] = BackSpace[3] = "\u007f"; // VMS other is delete
} else {
BackSpace[0] = BackSpace[1] = BackSpace[2] = BackSpace[3] = "\b";
}
/* some more VT100 keys */
Find = "\u001b[1~";
Select = "\u001b[4~";
Help = "\u001b[28~";
Do = "\u001b[29~";
FunctionKey = new String[21];
FunctionKey[0] = "";
FunctionKey[1] = PF1;
FunctionKey[2] = PF2;
FunctionKey[3] = PF3;
FunctionKey[4] = PF4;
/* following are defined differently for vt220 / vt132 ... */
FunctionKey[5] = "\u001b[15~";
FunctionKey[6] = "\u001b[17~";
FunctionKey[7] = "\u001b[18~";
FunctionKey[8] = "\u001b[19~";
FunctionKey[9] = "\u001b[20~";
FunctionKey[10] = "\u001b[21~";
FunctionKey[11] = "\u001b[23~";
FunctionKey[12] = "\u001b[24~";
FunctionKey[13] = "\u001b[25~";
FunctionKey[14] = "\u001b[26~";
FunctionKey[15] = Help;
FunctionKey[16] = Do;
FunctionKey[17] = "\u001b[31~";
FunctionKey[18] = "\u001b[32~";
FunctionKey[19] = "\u001b[33~";
FunctionKey[20] = "\u001b[34~";
FunctionKeyShift = new String[21];
FunctionKeyAlt = new String[21];
FunctionKeyCtrl = new String[21];
for (int i = 0; i < 20; i++) {
FunctionKeyShift[i] = "";
FunctionKeyAlt[i] = "";
FunctionKeyCtrl[i] = "";
}
FunctionKeyShift[15] = Find;
FunctionKeyShift[16] = Select;
TabKey[0] = "\u0009";
TabKey[1] = "\u001bOP\u0009";
TabKey[2] = TabKey[3] = "";
KeyUp = new String[4];
KeyUp[0] = "\u001b[A";
KeyDown = new String[4];
KeyDown[0] = "\u001b[B";
KeyRight = new String[4];
KeyRight[0] = "\u001b[C";
KeyLeft = new String[4];
KeyLeft[0] = "\u001b[D";
Numpad = new String[10];
Numpad[0] = "\u001bOp";
Numpad[1] = "\u001bOq";
Numpad[2] = "\u001bOr";
Numpad[3] = "\u001bOs";
Numpad[4] = "\u001bOt";
Numpad[5] = "\u001bOu";
Numpad[6] = "\u001bOv";
Numpad[7] = "\u001bOw";
Numpad[8] = "\u001bOx";
Numpad[9] = "\u001bOy";
KPMinus = PF4;
KPComma = "\u001bOl";
KPPeriod = "\u001bOn";
KPEnter = "\u001bOM";
NUMPlus = new String[4];
NUMPlus[0] = "+";
NUMDot = new String[4];
NUMDot[0] = ".";
}
/**
* Create a default vt320 terminal with 80 columns and 24 lines.
*/
public vt320() {
this(80, 24);
}
/**
* Terminal is mouse-aware and requires (x,y) coordinates of
* on the terminal (character coordinates) and the button clicked.
* @param x
* @param y
* @param modifiers
*/
public void mousePressed(int x, int y, int modifiers) {
if (mouserpt == 0)
return;
int mods = modifiers;
mousebut = 3;
if ((mods & 16) == 16) mousebut = 0;
if ((mods & 8) == 8) mousebut = 1;
if ((mods & 4) == 4) mousebut = 2;
int mousecode;
if (mouserpt == 9) /* X10 Mouse */
mousecode = 0x20 | mousebut;
else /* normal xterm mouse reporting */
mousecode = mousebut | 0x20 | ((mods & 7) << 2);
byte b[] = new byte[6];
b[0] = 27;
b[1] = (byte) '[';
b[2] = (byte) 'M';
b[3] = (byte) mousecode;
b[4] = (byte) (0x20 + x + 1);
b[5] = (byte) (0x20 + y + 1);
write(b); // FIXME: writeSpecial here
}
/**
* Terminal is mouse-aware and requires the coordinates and button
* of the release.
* @param x
* @param y
* @param modifiers
*/
public void mouseReleased(int x, int y, int modifiers) {
if (mouserpt == 0)
return;
/* problem is tht modifiers still have the released button set in them.
int mods = modifiers;
mousebut = 3;
if ((mods & 16)==16) mousebut=0;
if ((mods & 8)==8 ) mousebut=1;
if ((mods & 4)==4 ) mousebut=2;
*/
int mousecode;
if (mouserpt == 9)
mousecode = 0x20 + mousebut; /* same as press? appears so. */
else
mousecode = '#';
byte b[] = new byte[6];
b[0] = 27;
b[1] = (byte) '[';
b[2] = (byte) 'M';
b[3] = (byte) mousecode;
b[4] = (byte) (0x20 + x + 1);
b[5] = (byte) (0x20 + y + 1);
write(b); // FIXME: writeSpecial here
mousebut = 0;
}
/** we should do localecho (passed from other modules). false is default */
private boolean localecho = false;
/**
* Enable or disable the local echo property of the terminal.
* @param echo true if the terminal should echo locally
*/
public void setLocalEcho(boolean echo) {
localecho = echo;
}
/**
* Enable the VMS mode of the terminal to handle some things differently
* for VMS hosts.
* @param vms true for vms mode, false for normal mode
*/
public void setVMS(boolean vms) {
this.vms = vms;
}
/**
* Enable the usage of the IBM character set used by some BBS's. Special
* graphical character are available in this mode.
* @param ibm true to use the ibm character set
*/
public void setIBMCharset(boolean ibm) {
useibmcharset = ibm;
}
/**
* Override the standard key codes used by the terminal emulation.
* @param codes a properties object containing key code definitions
*/
public void setKeyCodes(Properties codes) {
String res, prefixes[] = {"", "S", "C", "A"};
int i;
for (i = 0; i < 10; i++) {
res = codes.getProperty("NUMPAD" + i);
if (res != null) Numpad[i] = unEscape(res);
}
for (i = 1; i < 20; i++) {
res = codes.getProperty("F" + i);
if (res != null) FunctionKey[i] = unEscape(res);
res = codes.getProperty("SF" + i);
if (res != null) FunctionKeyShift[i] = unEscape(res);
res = codes.getProperty("CF" + i);
if (res != null) FunctionKeyCtrl[i] = unEscape(res);
res = codes.getProperty("AF" + i);
if (res != null) FunctionKeyAlt[i] = unEscape(res);
}
for (i = 0; i < 4; i++) {
res = codes.getProperty(prefixes[i] + "PGUP");
if (res != null) PrevScn[i] = unEscape(res);
res = codes.getProperty(prefixes[i] + "PGDOWN");
if (res != null) NextScn[i] = unEscape(res);
res = codes.getProperty(prefixes[i] + "END");
if (res != null) KeyEnd[i] = unEscape(res);
res = codes.getProperty(prefixes[i] + "HOME");
if (res != null) KeyHome[i] = unEscape(res);
res = codes.getProperty(prefixes[i] + "INSERT");
if (res != null) Insert[i] = unEscape(res);
res = codes.getProperty(prefixes[i] + "REMOVE");
if (res != null) Remove[i] = unEscape(res);
res = codes.getProperty(prefixes[i] + "UP");
if (res != null) KeyUp[i] = unEscape(res);
res = codes.getProperty(prefixes[i] + "DOWN");
if (res != null) KeyDown[i] = unEscape(res);
res = codes.getProperty(prefixes[i] + "LEFT");
if (res != null) KeyLeft[i] = unEscape(res);
res = codes.getProperty(prefixes[i] + "RIGHT");
if (res != null) KeyRight[i] = unEscape(res);
res = codes.getProperty(prefixes[i] + "ESCAPE");
if (res != null) Escape[i] = unEscape(res);
res = codes.getProperty(prefixes[i] + "BACKSPACE");
if (res != null) BackSpace[i] = unEscape(res);
res = codes.getProperty(prefixes[i] + "TAB");
if (res != null) TabKey[i] = unEscape(res);
res = codes.getProperty(prefixes[i] + "NUMPLUS");
if (res != null) NUMPlus[i] = unEscape(res);
res = codes.getProperty(prefixes[i] + "NUMDECIMAL");
if (res != null) NUMDot[i] = unEscape(res);
}
}
/**
* Set the terminal id used to identify this terminal.
* @param terminalID the id string
*/
public void setTerminalID(String terminalID) {
this.terminalID = terminalID;
if (terminalID.equals("scoansi")) {
FunctionKey[1] = "\u001b[M"; FunctionKey[2] = "\u001b[N";
FunctionKey[3] = "\u001b[O"; FunctionKey[4] = "\u001b[P";
FunctionKey[5] = "\u001b[Q"; FunctionKey[6] = "\u001b[R";
FunctionKey[7] = "\u001b[S"; FunctionKey[8] = "\u001b[T";
FunctionKey[9] = "\u001b[U"; FunctionKey[10] = "\u001b[V";
FunctionKey[11] = "\u001b[W"; FunctionKey[12] = "\u001b[X";
FunctionKey[13] = "\u001b[Y"; FunctionKey[14] = "?";
FunctionKey[15] = "\u001b[a"; FunctionKey[16] = "\u001b[b";
FunctionKey[17] = "\u001b[c"; FunctionKey[18] = "\u001b[d";
FunctionKey[19] = "\u001b[e"; FunctionKey[20] = "\u001b[f";
PrevScn[0] = PrevScn[1] = PrevScn[2] = PrevScn[3] = "\u001b[I";
NextScn[0] = NextScn[1] = NextScn[2] = NextScn[3] = "\u001b[G";
// more theoretically.
}
}
public void setAnswerBack(String ab) {
this.answerBack = unEscape(ab);
}
/**
* Get the terminal id used to identify this terminal.
*/
public String getTerminalID() {
return terminalID;
}
/**
* A small conveniance method thar converts the string to a byte array
* for sending.
* @param s the string to be sent
*/
private boolean write(String s, boolean doecho) {
if (debug > 2) System.out.println("write(|" + s + "|," + doecho);
if (s == null) // aka the empty string.
return true;
/* NOTE: getBytes() honours some locale, it *CONVERTS* the string.
* However, we output only 7bit stuff towards the target, and *some*
* 8 bit control codes. We must not mess up the latter, so we do hand
* by hand copy.
*/
byte arr[] = new byte[s.length()];
for (int i = 0; i < s.length(); i++) {
arr[i] = (byte) s.charAt(i);
}
write(arr);
if (doecho)
putString(s);
return true;
}
private boolean write(String s) {
return write(s, localecho);
}
// ===================================================================
// the actual terminal emulation code comes here:
// ===================================================================
private String terminalID = "vt320";
private String answerBack = "Use Terminal.answerback to set ...\n";
// X - COLUMNS, Y - ROWS
int R,C;
int attributes = 0;
int Sc,Sr,Sa,Stm,Sbm;
char Sgr,Sgl;
char Sgx[];
int insertmode = 0;
int statusmode = 0;
boolean vt52mode = false;
boolean keypadmode = false; /* false - numeric, true - application */
boolean output8bit = false;
int normalcursor = 0;
boolean moveoutsidemargins = true;
boolean wraparound = true;
boolean sendcrlf = true;
boolean capslock = false;
boolean numlock = false;
int mouserpt = 0;
byte mousebut = 0;
boolean useibmcharset = false;
int lastwaslf = 0;
boolean usedcharsets = false;
private final static char ESC = 27;
private final static char IND = 132;
private final static char NEL = 133;
private final static char RI = 141;
private final static char SS2 = 142;
private final static char SS3 = 143;
private final static char DCS = 144;
private final static char HTS = 136;
private final static char CSI = 155;
private final static char OSC = 157;
private final static int TSTATE_DATA = 0;
private final static int TSTATE_ESC = 1; /* ESC */
private final static int TSTATE_CSI = 2; /* ESC [ */
private final static int TSTATE_DCS = 3; /* ESC P */
private final static int TSTATE_DCEQ = 4; /* ESC [? */
private final static int TSTATE_ESCSQUARE = 5; /* ESC # */
private final static int TSTATE_OSC = 6; /* ESC ] */
private final static int TSTATE_SETG0 = 7; /* ESC (? */
private final static int TSTATE_SETG1 = 8; /* ESC )? */
private final static int TSTATE_SETG2 = 9; /* ESC *? */
private final static int TSTATE_SETG3 = 10; /* ESC +? */
private final static int TSTATE_CSI_DOLLAR = 11; /* ESC [ Pn $ */
private final static int TSTATE_CSI_EX = 12; /* ESC [ ! */
private final static int TSTATE_ESCSPACE = 13; /* ESC */
private final static int TSTATE_VT52X = 14;
private final static int TSTATE_VT52Y = 15;
private final static int TSTATE_CSI_TICKS = 16;
private final static int TSTATE_CSI_EQUAL = 17; /* ESC [ = */
/* The graphics charsets
* B - default ASCII
* A - ISO Latin 1
* 0 - DEC SPECIAL
* < - User defined
* ....
*/
char gx[] = {// same initial set as in XTERM.
'B', // g0
'0', // g1
'B', // g2
'B', // g3
};
char gl = 0; // default GL to G0
char gr = 2; // default GR to G2
int onegl = -1; // single shift override for GL.
// Map from scoansi linedrawing to DEC _and_ unicode (for the stuff which
// is not in linedrawing). Got from experimenting with scoadmin.
private final static String scoansi_acs = "Tm7k3x4u?kZl@mYjEnB\u2566DqCtAvM\u2550:\u2551N\u2557I\u2554;\u2557H\u255a0a<\u255d";
// array to store DEC Special -> Unicode mapping
// Unicode DEC Unicode name (DEC name)
private static char DECSPECIAL[] = {
'\u0040', //5f blank
'\u2666', //60 black diamond
'\u2592', //61 grey square
'\u2409', //62 Horizontal tab (ht) pict. for control
'\u240c', //63 Form Feed (ff) pict. for control
'\u240d', //64 Carriage Return (cr) pict. for control
'\u240a', //65 Line Feed (lf) pict. for control
'\u00ba', //66 Masculine ordinal indicator
'\u00b1', //67 Plus or minus sign
'\u2424', //68 New Line (nl) pict. for control
'\u240b', //69 Vertical Tab (vt) pict. for control
'\u2518', //6a Forms light up and left
'\u2510', //6b Forms light down and left
'\u250c', //6c Forms light down and right
'\u2514', //6d Forms light up and right
'\u253c', //6e Forms light vertical and horizontal
'\u2594', //6f Upper 1/8 block (Scan 1)
'\u2580', //70 Upper 1/2 block (Scan 3)
'\u2500', //71 Forms light horizontal or ?em dash? (Scan 5)
'\u25ac', //72 \u25ac black rect. or \u2582 lower 1/4 (Scan 7)
'\u005f', //73 \u005f underscore or \u2581 lower 1/8 (Scan 9)
'\u251c', //74 Forms light vertical and right
'\u2524', //75 Forms light vertical and left
'\u2534', //76 Forms light up and horizontal
'\u252c', //77 Forms light down and horizontal
'\u2502', //78 vertical bar
'\u2264', //79 less than or equal
'\u2265', //7a greater than or equal
'\u00b6', //7b paragraph
'\u2260', //7c not equal
'\u00a3', //7d Pound Sign (british)
'\u00b7' //7e Middle Dot
};
/** Strings to send on function key pressing */
private String Numpad[];
private String FunctionKey[];
private String FunctionKeyShift[];
private String FunctionKeyCtrl[];
private String FunctionKeyAlt[];
private String TabKey[];
private String KeyUp[],KeyDown[],KeyLeft[],KeyRight[];
private String KPMinus, KPComma, KPPeriod, KPEnter;
private String PF1, PF2, PF3, PF4;
private String Help, Do, Find, Select;
private String KeyHome[], KeyEnd[], Insert[], Remove[], PrevScn[], NextScn[];
private String Escape[], BackSpace[], NUMDot[], NUMPlus[];
private String osc,dcs; /* to memorize OSC & DCS control sequence */
/** vt320 state variable (internal) */
private int term_state = TSTATE_DATA;
/** in vms mode, set by Terminal.VMS property */
private boolean vms = false;
/** Tabulators */
private byte[] Tabs;
/** The list of integers as used by CSI */
private int[] DCEvars = new int[30];
private int DCEvar;
/**
* Replace escape code characters (backslash + identifier) with their
* respective codes.
* @param tmp the string to be parsed
* @return a unescaped string
*/
static String unEscape(String tmp) {
int idx = 0, oldidx = 0;
String cmd;
// System.err.println("unescape("+tmp+")");
cmd = "";
while ((idx = tmp.indexOf('\\', oldidx)) >= 0 &&
++idx <= tmp.length()) {
cmd += tmp.substring(oldidx, idx - 1);
if (idx == tmp.length()) return cmd;
switch (tmp.charAt(idx)) {
case 'b':
cmd += "\b";
break;
case 'e':
cmd += "\u001b";
break;
case 'n':
cmd += "\n";
break;
case 'r':
cmd += "\r";
break;
case 't':
cmd += "\t";
break;
case 'v':
cmd += "\u000b";
break;
case 'a':
cmd += "\u0012";
break;
default :
if ((tmp.charAt(idx) >= '0') && (tmp.charAt(idx) <= '9')) {
int i;
for (i = idx; i < tmp.length(); i++)
if ((tmp.charAt(i) < '0') || (tmp.charAt(i) > '9'))
break;
cmd += (char) Integer.parseInt(tmp.substring(idx, i));
idx = i - 1;
} else
cmd += tmp.substring(idx, ++idx);
break;
}
oldidx = ++idx;
}
if (oldidx <= tmp.length()) cmd += tmp.substring(oldidx);
return cmd;
}
/**
* A small conveniance method thar converts a 7bit string to the 8bit
* version depending on VT52/Output8Bit mode.
*
* @param s the string to be sent
*/
private boolean writeSpecial(String s) {
if (s == null)
return true;
if (((s.length() >= 3) && (s.charAt(0) == 27) && (s.charAt(1) == 'O'))) {
if (vt52mode) {
if ((s.charAt(2) >= 'P') && (s.charAt(2) <= 'S')) {
s = "\u001b" + s.substring(2); /* ESC x */
} else {
s = "\u001b?" + s.substring(2); /* ESC ? x */
}
} else {
if (output8bit) {
s = "\u008f" + s.substring(2); /* SS3 x */
} /* else keep string as it is */
}
}
if (((s.length() >= 3) && (s.charAt(0) == 27) && (s.charAt(1) == '['))) {
if (output8bit) {
s = "\u009b" + s.substring(2); /* CSI ... */
} /* else keep */
}
return write(s, false);
}
/**
* main keytyping event handler...
*/
public void keyPressed(int keyCode, char keyChar, int modifiers) {
boolean control = (modifiers & VDUInput.KEY_CONTROL) != 0;
boolean shift = (modifiers & VDUInput.KEY_SHIFT) != 0;
boolean alt = (modifiers & VDUInput.KEY_ALT) != 0;
if (debug > 1) System.out.println("keyPressed("+keyCode+", "+(int)keyChar+", "+modifiers+")");
int xind;
String fmap[];
xind = 0;
fmap = FunctionKey;
if (shift) {
fmap = FunctionKeyShift;
xind = 1;
}
if (control) {
fmap = FunctionKeyCtrl;
xind = 2;
}
if (alt) {
fmap = FunctionKeyAlt;
xind = 3;
}
switch (keyCode) {
case KeyEvent.VK_PAUSE:
if (shift || control)
sendTelnetCommand((byte) 243); // BREAK
break;
case KeyEvent.VK_F1:
writeSpecial(fmap[1]);
break;
case KeyEvent.VK_F2:
writeSpecial(fmap[2]);
break;
case KeyEvent.VK_F3:
writeSpecial(fmap[3]);
break;
case KeyEvent.VK_F4:
writeSpecial(fmap[4]);
break;
case KeyEvent.VK_F5:
writeSpecial(fmap[5]);
break;
case KeyEvent.VK_F6:
writeSpecial(fmap[6]);
break;
case KeyEvent.VK_F7:
writeSpecial(fmap[7]);
break;
case KeyEvent.VK_F8:
writeSpecial(fmap[8]);
break;
case KeyEvent.VK_F9:
writeSpecial(fmap[9]);
break;
case KeyEvent.VK_F10:
writeSpecial(fmap[10]);
break;
case KeyEvent.VK_F11:
writeSpecial(fmap[11]);
break;
case KeyEvent.VK_F12:
writeSpecial(fmap[12]);
break;
case KeyEvent.VK_UP:
writeSpecial(KeyUp[xind]);
break;
case KeyEvent.VK_DOWN:
writeSpecial(KeyDown[xind]);
break;
case KeyEvent.VK_LEFT:
writeSpecial(KeyLeft[xind]);
break;
case KeyEvent.VK_RIGHT:
writeSpecial(KeyRight[xind]);
break;
case KeyEvent.VK_PAGE_DOWN:
writeSpecial(NextScn[xind]);
break;
case KeyEvent.VK_PAGE_UP:
writeSpecial(PrevScn[xind]);
break;
case KeyEvent.VK_INSERT:
writeSpecial(Insert[xind]);
break;
case KeyEvent.VK_DELETE:
writeSpecial(Remove[xind]);
break;
case KeyEvent.VK_BACK_SPACE:
writeSpecial(BackSpace[xind]);
if (localecho) {
if (BackSpace[xind] == "\b") {
putString("\b \b"); // make the last char 'deleted'
} else {
putString(BackSpace[xind]); // echo it
}
}
break;
case KeyEvent.VK_HOME:
writeSpecial(KeyHome[xind]);
break;
case KeyEvent.VK_END:
writeSpecial(KeyEnd[xind]);
break;
case KeyEvent.VK_NUM_LOCK:
if (vms && control) {
writeSpecial(PF1);
}
if (!control)
numlock = !numlock;
break;
case KeyEvent.VK_CAPS_LOCK:
capslock = !capslock;
return;
case KeyEvent.VK_SHIFT:
case KeyEvent.VK_CONTROL:
case KeyEvent.VK_ALT:
return;
default:
break;
}
}
public void keyReleased(KeyEvent evt) {
if (debug > 1) System.out.println("keyReleased("+evt+")");
// ignore
}
/**
* Handle key Typed events for the terminal, this will get
* all normal key types, but no shift/alt/control/numlock.
*/
public void keyTyped(int keyCode, char keyChar, int modifiers) {
boolean control = (modifiers & VDUInput.KEY_CONTROL) != 0;
boolean shift = (modifiers & VDUInput.KEY_SHIFT) != 0;
boolean alt = (modifiers & VDUInput.KEY_ALT) != 0;
if (debug > 1) System.out.println("keyTyped("+keyCode+", "+(int)keyChar+", "+modifiers+")");
if (keyChar == '\t') {
if (shift) {
write(TabKey[1], false);
} else {
if (control) {
write(TabKey[2], false);
} else {
if (alt) {
write(TabKey[3], false);
} else {
write(TabKey[0], false);
}
}
}
return;
}
if (alt) {
write("" + ((char) (keyChar | 0x80)));
return;
}
if (((keyCode == KeyEvent.VK_ENTER) || (keyChar == 10))
&& !control) {
write("\r", false);
if (localecho) putString("\r\n"); // bad hack
return;
}
if ((keyCode == 10) && !control) {
System.out.println("Sending \\r");
write("\r", false);
return;
}
// FIXME: on german PC keyboards you have to use Alt-Ctrl-q to get an @,
// so we can't just use it here... will probably break some other VMS
// codes. -Marcus
// if(((!vms && keyChar == '2') || keyChar == '@' || keyChar == ' ')
// && control)
if (((!vms && keyChar == '2') || keyChar == ' ') && control)
write("" + (char) 0);
if (vms) {
if (keyChar == 127 && !control) {
if (shift)
writeSpecial(Insert[0]); // VMS shift delete = insert
else
writeSpecial(Remove[0]); // VMS delete = remove
return;
} else if (control)
switch (keyChar) {
case '0':
writeSpecial(Numpad[0]);
return;
case '1':
writeSpecial(Numpad[1]);
return;
case '2':
writeSpecial(Numpad[2]);
return;
case '3':
writeSpecial(Numpad[3]);
return;
case '4':
writeSpecial(Numpad[4]);
return;
case '5':
writeSpecial(Numpad[5]);
return;
case '6':
writeSpecial(Numpad[6]);
return;
case '7':
writeSpecial(Numpad[7]);
return;
case '8':
writeSpecial(Numpad[8]);
return;
case '9':
writeSpecial(Numpad[9]);
return;
case '.':
writeSpecial(KPPeriod);
return;
case '-':
case 31:
writeSpecial(KPMinus);
return;
case '+':
writeSpecial(KPComma);
return;
case 10:
writeSpecial(KPEnter);
return;
case '/':
writeSpecial(PF2);
return;
case '*':
writeSpecial(PF3);
return;
/* NUMLOCK handled in keyPressed */
default:
break;
}
/* Now what does this do and how did it get here. -Marcus
if (shift && keyChar < 32) {
write(PF1+(char)(keyChar + 64));
return;
}
*/
}
// FIXME: not used?
String fmap[];
int xind;
xind = 0;
fmap = FunctionKey;
if (shift) {
fmap = FunctionKeyShift;
xind = 1;
}
if (control) {
fmap = FunctionKeyCtrl;
xind = 2;
}
if (alt) {
fmap = FunctionKeyAlt;
xind = 3;
}
if (keyCode == KeyEvent.VK_ESCAPE) {
writeSpecial(Escape[xind]);
return;
}
if ((modifiers & VDUInput.KEY_ACTION) != 0)
switch (keyCode) {
case KeyEvent.VK_NUMPAD0:
writeSpecial(Numpad[0]);
return;
case KeyEvent.VK_NUMPAD1:
writeSpecial(Numpad[1]);
return;
case KeyEvent.VK_NUMPAD2:
writeSpecial(Numpad[2]);
return;
case KeyEvent.VK_NUMPAD3:
writeSpecial(Numpad[3]);
return;
case KeyEvent.VK_NUMPAD4:
writeSpecial(Numpad[4]);
return;
case KeyEvent.VK_NUMPAD5:
writeSpecial(Numpad[5]);
return;
case KeyEvent.VK_NUMPAD6:
writeSpecial(Numpad[6]);
return;
case KeyEvent.VK_NUMPAD7:
writeSpecial(Numpad[7]);
return;
case KeyEvent.VK_NUMPAD8:
writeSpecial(Numpad[8]);
return;
case KeyEvent.VK_NUMPAD9:
writeSpecial(Numpad[9]);
return;
case KeyEvent.VK_DECIMAL:
writeSpecial(NUMDot[xind]);
return;
case KeyEvent.VK_ADD:
writeSpecial(NUMPlus[xind]);
return;
}
if (!((keyChar == 8) || (keyChar == 127) || (keyChar == '\r') || (keyChar == '\n'))) {
write("" + keyChar);
return;
}
}
private void handle_dcs(String dcs) {
System.out.println("DCS: " + dcs);
}
private void handle_osc(String osc) {
System.out.println("OSC: " + osc);
}
private final static char unimap[] = {
//#
//# Name: cp437_DOSLatinUS to Unicode table
//# Unicode version: 1.1
//# Table version: 1.1
//# Table format: Format A
//# Date: 03/31/95
//# Authors: Michel Suignard
//# Lori Hoerth
//# General notes: none
//#
//# Format: Three tab-separated columns
//# Column #1 is the cp1255_WinHebrew code (in hex)
//# Column #2 is the Unicode (in hex as 0xXXXX)
//# Column #3 is the Unicode name (follows a comment sign, '#')
//#
//# The entries are in cp437_DOSLatinUS order
//#
0x0000, // #NULL
0x0001, // #START OF HEADING
0x0002, // #START OF TEXT
0x0003, // #END OF TEXT
0x0004, // #END OF TRANSMISSION
0x0005, // #ENQUIRY
0x0006, // #ACKNOWLEDGE
0x0007, // #BELL
0x0008, // #BACKSPACE
0x0009, // #HORIZONTAL TABULATION
0x000a, // #LINE FEED
0x000b, // #VERTICAL TABULATION
0x000c, // #FORM FEED
0x000d, // #CARRIAGE RETURN
0x000e, // #SHIFT OUT
0x000f, // #SHIFT IN
0x0010, // #DATA LINK ESCAPE
0x0011, // #DEVICE CONTROL ONE
0x0012, // #DEVICE CONTROL TWO
0x0013, // #DEVICE CONTROL THREE
0x0014, // #DEVICE CONTROL FOUR
0x0015, // #NEGATIVE ACKNOWLEDGE
0x0016, // #SYNCHRONOUS IDLE
0x0017, // #END OF TRANSMISSION BLOCK
0x0018, // #CANCEL
0x0019, // #END OF MEDIUM
0x001a, // #SUBSTITUTE
0x001b, // #ESCAPE
0x001c, // #FILE SEPARATOR
0x001d, // #GROUP SEPARATOR
0x001e, // #RECORD SEPARATOR
0x001f, // #UNIT SEPARATOR
0x0020, // #SPACE
0x0021, // #EXCLAMATION MARK
0x0022, // #QUOTATION MARK
0x0023, // #NUMBER SIGN
0x0024, // #DOLLAR SIGN
0x0025, // #PERCENT SIGN
0x0026, // #AMPERSAND
0x0027, // #APOSTROPHE
0x0028, // #LEFT PARENTHESIS
0x0029, // #RIGHT PARENTHESIS
0x002a, // #ASTERISK
0x002b, // #PLUS SIGN
0x002c, // #COMMA
0x002d, // #HYPHEN-MINUS
0x002e, // #FULL STOP
0x002f, // #SOLIDUS
0x0030, // #DIGIT ZERO
0x0031, // #DIGIT ONE
0x0032, // #DIGIT TWO
0x0033, // #DIGIT THREE
0x0034, // #DIGIT FOUR
0x0035, // #DIGIT FIVE
0x0036, // #DIGIT SIX
0x0037, // #DIGIT SEVEN
0x0038, // #DIGIT EIGHT
0x0039, // #DIGIT NINE
0x003a, // #COLON
0x003b, // #SEMICOLON
0x003c, // #LESS-THAN SIGN
0x003d, // #EQUALS SIGN
0x003e, // #GREATER-THAN SIGN
0x003f, // #QUESTION MARK
0x0040, // #COMMERCIAL AT
0x0041, // #LATIN CAPITAL LETTER A
0x0042, // #LATIN CAPITAL LETTER B
0x0043, // #LATIN CAPITAL LETTER C
0x0044, // #LATIN CAPITAL LETTER D
0x0045, // #LATIN CAPITAL LETTER E
0x0046, // #LATIN CAPITAL LETTER F
0x0047, // #LATIN CAPITAL LETTER G
0x0048, // #LATIN CAPITAL LETTER H
0x0049, // #LATIN CAPITAL LETTER I
0x004a, // #LATIN CAPITAL LETTER J
0x004b, // #LATIN CAPITAL LETTER K
0x004c, // #LATIN CAPITAL LETTER L
0x004d, // #LATIN CAPITAL LETTER M
0x004e, // #LATIN CAPITAL LETTER N
0x004f, // #LATIN CAPITAL LETTER O
0x0050, // #LATIN CAPITAL LETTER P
0x0051, // #LATIN CAPITAL LETTER Q
0x0052, // #LATIN CAPITAL LETTER R
0x0053, // #LATIN CAPITAL LETTER S
0x0054, // #LATIN CAPITAL LETTER T
0x0055, // #LATIN CAPITAL LETTER U
0x0056, // #LATIN CAPITAL LETTER V
0x0057, // #LATIN CAPITAL LETTER W
0x0058, // #LATIN CAPITAL LETTER X
0x0059, // #LATIN CAPITAL LETTER Y
0x005a, // #LATIN CAPITAL LETTER Z
0x005b, // #LEFT SQUARE BRACKET
0x005c, // #REVERSE SOLIDUS
0x005d, // #RIGHT SQUARE BRACKET
0x005e, // #CIRCUMFLEX ACCENT
0x005f, // #LOW LINE
0x0060, // #GRAVE ACCENT
0x0061, // #LATIN SMALL LETTER A
0x0062, // #LATIN SMALL LETTER B
0x0063, // #LATIN SMALL LETTER C
0x0064, // #LATIN SMALL LETTER D
0x0065, // #LATIN SMALL LETTER E
0x0066, // #LATIN SMALL LETTER F
0x0067, // #LATIN SMALL LETTER G
0x0068, // #LATIN SMALL LETTER H
0x0069, // #LATIN SMALL LETTER I
0x006a, // #LATIN SMALL LETTER J
0x006b, // #LATIN SMALL LETTER K
0x006c, // #LATIN SMALL LETTER L
0x006d, // #LATIN SMALL LETTER M
0x006e, // #LATIN SMALL LETTER N
0x006f, // #LATIN SMALL LETTER O
0x0070, // #LATIN SMALL LETTER P
0x0071, // #LATIN SMALL LETTER Q
0x0072, // #LATIN SMALL LETTER R
0x0073, // #LATIN SMALL LETTER S
0x0074, // #LATIN SMALL LETTER T
0x0075, // #LATIN SMALL LETTER U
0x0076, // #LATIN SMALL LETTER V
0x0077, // #LATIN SMALL LETTER W
0x0078, // #LATIN SMALL LETTER X
0x0079, // #LATIN SMALL LETTER Y
0x007a, // #LATIN SMALL LETTER Z
0x007b, // #LEFT CURLY BRACKET
0x007c, // #VERTICAL LINE
0x007d, // #RIGHT CURLY BRACKET
0x007e, // #TILDE
0x007f, // #DELETE
0x00c7, // #LATIN CAPITAL LETTER C WITH CEDILLA
0x00fc, // #LATIN SMALL LETTER U WITH DIAERESIS
0x00e9, // #LATIN SMALL LETTER E WITH ACUTE
0x00e2, // #LATIN SMALL LETTER A WITH CIRCUMFLEX
0x00e4, // #LATIN SMALL LETTER A WITH DIAERESIS
0x00e0, // #LATIN SMALL LETTER A WITH GRAVE
0x00e5, // #LATIN SMALL LETTER A WITH RING ABOVE
0x00e7, // #LATIN SMALL LETTER C WITH CEDILLA
0x00ea, // #LATIN SMALL LETTER E WITH CIRCUMFLEX
0x00eb, // #LATIN SMALL LETTER E WITH DIAERESIS
0x00e8, // #LATIN SMALL LETTER E WITH GRAVE
0x00ef, // #LATIN SMALL LETTER I WITH DIAERESIS
0x00ee, // #LATIN SMALL LETTER I WITH CIRCUMFLEX
0x00ec, // #LATIN SMALL LETTER I WITH GRAVE
0x00c4, // #LATIN CAPITAL LETTER A WITH DIAERESIS
0x00c5, // #LATIN CAPITAL LETTER A WITH RING ABOVE
0x00c9, // #LATIN CAPITAL LETTER E WITH ACUTE
0x00e6, // #LATIN SMALL LIGATURE AE
0x00c6, // #LATIN CAPITAL LIGATURE AE
0x00f4, // #LATIN SMALL LETTER O WITH CIRCUMFLEX
0x00f6, // #LATIN SMALL LETTER O WITH DIAERESIS
0x00f2, // #LATIN SMALL LETTER O WITH GRAVE
0x00fb, // #LATIN SMALL LETTER U WITH CIRCUMFLEX
0x00f9, // #LATIN SMALL LETTER U WITH GRAVE
0x00ff, // #LATIN SMALL LETTER Y WITH DIAERESIS
0x00d6, // #LATIN CAPITAL LETTER O WITH DIAERESIS
0x00dc, // #LATIN CAPITAL LETTER U WITH DIAERESIS
0x00a2, // #CENT SIGN
0x00a3, // #POUND SIGN
0x00a5, // #YEN SIGN
0x20a7, // #PESETA SIGN
0x0192, // #LATIN SMALL LETTER F WITH HOOK
0x00e1, // #LATIN SMALL LETTER A WITH ACUTE
0x00ed, // #LATIN SMALL LETTER I WITH ACUTE
0x00f3, // #LATIN SMALL LETTER O WITH ACUTE
0x00fa, // #LATIN SMALL LETTER U WITH ACUTE
0x00f1, // #LATIN SMALL LETTER N WITH TILDE
0x00d1, // #LATIN CAPITAL LETTER N WITH TILDE
0x00aa, // #FEMININE ORDINAL INDICATOR
0x00ba, // #MASCULINE ORDINAL INDICATOR
0x00bf, // #INVERTED QUESTION MARK
0x2310, // #REVERSED NOT SIGN
0x00ac, // #NOT SIGN
0x00bd, // #VULGAR FRACTION ONE HALF
0x00bc, // #VULGAR FRACTION ONE QUARTER
0x00a1, // #INVERTED EXCLAMATION MARK
0x00ab, // #LEFT-POINTING DOUBLE ANGLE QUOTATION MARK
0x00bb, // #RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK
0x2591, // #LIGHT SHADE
0x2592, // #MEDIUM SHADE
0x2593, // #DARK SHADE
0x2502, // #BOX DRAWINGS LIGHT VERTICAL
0x2524, // #BOX DRAWINGS LIGHT VERTICAL AND LEFT
0x2561, // #BOX DRAWINGS VERTICAL SINGLE AND LEFT DOUBLE
0x2562, // #BOX DRAWINGS VERTICAL DOUBLE AND LEFT SINGLE
0x2556, // #BOX DRAWINGS DOWN DOUBLE AND LEFT SINGLE
0x2555, // #BOX DRAWINGS DOWN SINGLE AND LEFT DOUBLE
0x2563, // #BOX DRAWINGS DOUBLE VERTICAL AND LEFT
0x2551, // #BOX DRAWINGS DOUBLE VERTICAL
0x2557, // #BOX DRAWINGS DOUBLE DOWN AND LEFT
0x255d, // #BOX DRAWINGS DOUBLE UP AND LEFT
0x255c, // #BOX DRAWINGS UP DOUBLE AND LEFT SINGLE
0x255b, // #BOX DRAWINGS UP SINGLE AND LEFT DOUBLE
0x2510, // #BOX DRAWINGS LIGHT DOWN AND LEFT
0x2514, // #BOX DRAWINGS LIGHT UP AND RIGHT
0x2534, // #BOX DRAWINGS LIGHT UP AND HORIZONTAL
0x252c, // #BOX DRAWINGS LIGHT DOWN AND HORIZONTAL
0x251c, // #BOX DRAWINGS LIGHT VERTICAL AND RIGHT
0x2500, // #BOX DRAWINGS LIGHT HORIZONTAL
0x253c, // #BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL
0x255e, // #BOX DRAWINGS VERTICAL SINGLE AND RIGHT DOUBLE
0x255f, // #BOX DRAWINGS VERTICAL DOUBLE AND RIGHT SINGLE
0x255a, // #BOX DRAWINGS DOUBLE UP AND RIGHT
0x2554, // #BOX DRAWINGS DOUBLE DOWN AND RIGHT
0x2569, // #BOX DRAWINGS DOUBLE UP AND HORIZONTAL
0x2566, // #BOX DRAWINGS DOUBLE DOWN AND HORIZONTAL
0x2560, // #BOX DRAWINGS DOUBLE VERTICAL AND RIGHT
0x2550, // #BOX DRAWINGS DOUBLE HORIZONTAL
0x256c, // #BOX DRAWINGS DOUBLE VERTICAL AND HORIZONTAL
0x2567, // #BOX DRAWINGS UP SINGLE AND HORIZONTAL DOUBLE
0x2568, // #BOX DRAWINGS UP DOUBLE AND HORIZONTAL SINGLE
0x2564, // #BOX DRAWINGS DOWN SINGLE AND HORIZONTAL DOUBLE
0x2565, // #BOX DRAWINGS DOWN DOUBLE AND HORIZONTAL SINGLE
0x2559, // #BOX DRAWINGS UP DOUBLE AND RIGHT SINGLE
0x2558, // #BOX DRAWINGS UP SINGLE AND RIGHT DOUBLE
0x2552, // #BOX DRAWINGS DOWN SINGLE AND RIGHT DOUBLE
0x2553, // #BOX DRAWINGS DOWN DOUBLE AND RIGHT SINGLE
0x256b, // #BOX DRAWINGS VERTICAL DOUBLE AND HORIZONTAL SINGLE
0x256a, // #BOX DRAWINGS VERTICAL SINGLE AND HORIZONTAL DOUBLE
0x2518, // #BOX DRAWINGS LIGHT UP AND LEFT
0x250c, // #BOX DRAWINGS LIGHT DOWN AND RIGHT
0x2588, // #FULL BLOCK
0x2584, // #LOWER HALF BLOCK
0x258c, // #LEFT HALF BLOCK
0x2590, // #RIGHT HALF BLOCK
0x2580, // #UPPER HALF BLOCK
0x03b1, // #GREEK SMALL LETTER ALPHA
0x00df, // #LATIN SMALL LETTER SHARP S
0x0393, // #GREEK CAPITAL LETTER GAMMA
0x03c0, // #GREEK SMALL LETTER PI
0x03a3, // #GREEK CAPITAL LETTER SIGMA
0x03c3, // #GREEK SMALL LETTER SIGMA
0x00b5, // #MICRO SIGN
0x03c4, // #GREEK SMALL LETTER TAU
0x03a6, // #GREEK CAPITAL LETTER PHI
0x0398, // #GREEK CAPITAL LETTER THETA
0x03a9, // #GREEK CAPITAL LETTER OMEGA
0x03b4, // #GREEK SMALL LETTER DELTA
0x221e, // #INFINITY
0x03c6, // #GREEK SMALL LETTER PHI
0x03b5, // #GREEK SMALL LETTER EPSILON
0x2229, // #INTERSECTION
0x2261, // #IDENTICAL TO
0x00b1, // #PLUS-MINUS SIGN
0x2265, // #GREATER-THAN OR EQUAL TO
0x2264, // #LESS-THAN OR EQUAL TO
0x2320, // #TOP HALF INTEGRAL
0x2321, // #BOTTOM HALF INTEGRAL
0x00f7, // #DIVISION SIGN
0x2248, // #ALMOST EQUAL TO
0x00b0, // #DEGREE SIGN
0x2219, // #BULLET OPERATOR
0x00b7, // #MIDDLE DOT
0x221a, // #SQUARE ROOT
0x207f, // #SUPERSCRIPT LATIN SMALL LETTER N
0x00b2, // #SUPERSCRIPT TWO
0x25a0, // #BLACK SQUARE
0x00a0, // #NO-BREAK SPACE
};
public char map_cp850_unicode(char x) {
if (x >= 0x100)
return x;
return unimap[x];
}
private void _SetCursor(int row, int col) {
int maxr = getRows();
int tm = getTopMargin();
R = (row < 0)?0:row;
C = (col < 0)?0:col;
if (!moveoutsidemargins) {
R += tm;
maxr = getBottomMargin();
}
if (R > maxr) R = maxr;
}
private void putChar(char c, boolean doshowcursor) {
int rows = getRows(); //statusline
int columns = getColumns();
int tm = getTopMargin();
int bm = getBottomMargin();
// byte msg[];
boolean mapped = false;
if (debug > 4) System.out.println("putChar(" + c + " [" + ((int) c) + "]) at R=" + R + " , C=" + C + ", columns=" + columns + ", rows=" + rows);
markLine(R, 1);
if (c > 255) {
if (debug > 0)
System.out.println("char > 255:" + (int) c);
//return;
}
switch (term_state) {
case TSTATE_DATA:
/* FIXME: we shouldn't use chars with bit 8 set if ibmcharset.
* probably... but some BBS do anyway...
*/
if (!useibmcharset) {
boolean doneflag = true;
switch (c) {
case OSC:
osc = "";
term_state = TSTATE_OSC;
break;
case RI:
if (R > tm)
R--;
else
insertLine(R, 1, SCROLL_DOWN);
if (debug > 1)
System.out.println("RI");
break;
case IND:
if (debug > 2)
System.out.println("IND at " + R + ", tm is " + tm + ", bm is " + bm);
if (R == bm || R == rows - 1)
insertLine(R, 1, SCROLL_UP);
else
R++;
if (debug > 1)
System.out.println("IND (at " + R + " )");
break;
case NEL:
if (R == bm || R == rows - 1)
insertLine(R, 1, SCROLL_UP);
else
R++;
C = 0;
if (debug > 1)
System.out.println("NEL (at " + R + " )");
break;
case HTS:
Tabs[C] = 1;
if (debug > 1)
System.out.println("HTS");
break;
case DCS:
dcs = "";
term_state = TSTATE_DCS;
break;
default:
doneflag = false;
break;
}
if (doneflag) break;
}
switch (c) {
case SS3:
onegl = 3;
break;
case SS2:
onegl = 2;
break;
case CSI: // should be in the 8bit section, but some BBS use this
DCEvar = 0;
DCEvars[0] = 0;
DCEvars[1] = 0;
DCEvars[2] = 0;
DCEvars[3] = 0;
term_state = TSTATE_CSI;
break;
case ESC:
term_state = TSTATE_ESC;
lastwaslf = 0;
break;
case 5: /* ENQ */
write(answerBack, false);
break;
case 12:
/* FormFeed, Home for the BBS world */
deleteArea(0, 0, columns, rows, attributes);
C = R = 0;
break;
case '\b': /* 8 */
C--;
if (C < 0)
C = 0;
lastwaslf = 0;
break;
case '\t':
do {
// Don't overwrite or insert! TABS are not destructive, but movement!
C++;
} while (C < columns && (Tabs[C] == 0));
lastwaslf = 0;
break;
case '\r':
C = 0;
break;
case '\n':
if (debug > 3)
System.out.println("R= " + R + ", bm " + bm + ", tm=" + tm + ", rows=" + rows);
if (!vms) {
if (lastwaslf != 0 && lastwaslf != c) // Ray: I do not understand this logic.
break;
lastwaslf = c;
/*C = 0;*/
}
if (R == bm || R >= rows - 1)
insertLine(R, 1, SCROLL_UP);
else
R++;
break;
case 7:
beep();
break;
case '\016': /* SMACS , as */
/* ^N, Shift out - Put G1 into GL */
gl = 1;
usedcharsets = true;
break;
case '\017': /* RMACS , ae */
/* ^O, Shift in - Put G0 into GL */
gl = 0;
usedcharsets = true;
break;
default:
{
int thisgl = gl;
if (onegl >= 0) {
thisgl = onegl;
onegl = -1;
}
lastwaslf = 0;
if (c < 32) {
if (c != 0)
if (debug > 0)
System.out.println("TSTATE_DATA char: " + ((int) c));
/*break; some BBS really want those characters, like hearst etc. */
if (c == 0) /* print 0 ... you bet */
break;
}
if (C >= columns) {
if (wraparound) {
if (R < rows - 1)
R++;
else
insertLine(R, 1, SCROLL_UP);
C = 0;
} else {
// cursor stays on last character.
C = columns - 1;
}
}
// Mapping if DEC Special is chosen charset
if (usedcharsets) {
if (c >= '\u0020' && c <= '\u007f') {
switch (gx[thisgl]) {
case '0':
// Remap SCOANSI line drawing to VT100 line drawing chars
// for our SCO using customers.
if (terminalID.equals("scoansi") || terminalID.equals("ansi")) {
for (int i = 0; i < scoansi_acs.length(); i += 2) {
if (c == scoansi_acs.charAt(i)) {
c = scoansi_acs.charAt(i + 1);
break;
}
}
}
if (c >= '\u005f' && c <= '\u007e') {
c = DECSPECIAL[(short) c - 0x5f];
mapped = true;
}
break;
case '<': // 'user preferred' is currently 'ISO Latin-1 suppl
c = (char) (((int) c & 0x7f) | 0x80);
mapped = true;
break;
case 'A':
case 'B': // Latin-1 , ASCII -> fall through
mapped = true;
break;
default:
System.out.println("Unsupported GL mapping: " + gx[thisgl]);
break;
}
}
if (!mapped && (c >= '\u0080' && c <= '\u00ff')) {
switch (gx[gr]) {
case '0':
if (c >= '\u00df' && c <= '\u00fe') {
c = DECSPECIAL[c - '\u00df'];
mapped = true;
}
break;
case '<':
case 'A':
case 'B':
mapped = true;
break;
default:
System.out.println("Unsupported GR mapping: " + gx[gr]);
break;
}
}
}
if (!mapped && useibmcharset)
c = map_cp850_unicode(c);
/*if(true || (statusmode == 0)) { */
if (insertmode == 1) {
insertChar(C, R, c, attributes);
} else {
putChar(C, R, c, attributes);
}
/*
} else {
if (insertmode==1) {
insertChar(C, rows, c, attributes);
} else {
putChar(C, rows, c, attributes);
}
}
*/
C++;
break;
}
} /* switch(c) */
break;
case TSTATE_OSC:
if ((c < 0x20) && (c != ESC)) {// NP - No printing character
handle_osc(osc);
term_state = TSTATE_DATA;
break;
}
//but check for vt102 ESC \
if (c == '\\' && osc.charAt(osc.length() - 1) == ESC) {
handle_osc(osc);
term_state = TSTATE_DATA;
break;
}
osc = osc + c;
break;
case TSTATE_ESCSPACE:
term_state = TSTATE_DATA;
switch (c) {
case 'F': /* S7C1T, Disable output of 8-bit controls, use 7-bit */
output8bit = false;
break;
case 'G': /* S8C1T, Enable output of 8-bit control codes*/
output8bit = true;
break;
default:
System.out.println("ESC " + c + " unhandled.");
}
break;
case TSTATE_ESC:
term_state = TSTATE_DATA;
switch (c) {
case ' ':
term_state = TSTATE_ESCSPACE;
break;
case '#':
term_state = TSTATE_ESCSQUARE;
break;
case 'c':
/* Hard terminal reset */
/* reset character sets */
gx[0] = 'B';
gx[1] = '0';
gx[2] = 'B';
gx[3] = 'B';
gl = 0; // default GL to G0
gr = 1; // default GR to G1
/* reset tabs */
int nw = getColumns();
if (nw < 132) nw = 132;
Tabs = new byte[nw];
for (int i = 0; i < nw; i += 8) {
Tabs[i] = 1;
}
/*FIXME:*/
break;
case '[':
DCEvar = 0;
DCEvars[0] = 0;
DCEvars[1] = 0;
DCEvars[2] = 0;
DCEvars[3] = 0;
term_state = TSTATE_CSI;
break;
case ']':
osc = "";
term_state = TSTATE_OSC;
break;
case 'P':
dcs = "";
term_state = TSTATE_DCS;
break;
case 'A': /* CUU */
R--;
if (R < 0) R = 0;
break;
case 'B': /* CUD */
R++;
if (R > rows - 1) R = rows - 1;
break;
case 'C':
C++;
if (C >= columns) C = columns - 1;
break;
case 'I': // RI
insertLine(R, 1, SCROLL_DOWN);
break;
case 'E': /* NEL */
if (R == bm || R == rows - 1)
insertLine(R, 1, SCROLL_UP);
else
R++;
C = 0;
if (debug > 1)
System.out.println("ESC E (at " + R + ")");
break;
case 'D': /* IND */
if (R == bm || R == rows - 1)
insertLine(R, 1, SCROLL_UP);
else
R++;
if (debug > 1)
System.out.println("ESC D (at " + R + " )");
break;
case 'J': /* erase to end of screen */
if (R < rows - 1)
deleteArea(0, R + 1, columns, rows - R - 1, attributes);
if (C < columns - 1)
deleteArea(C, R, columns - C, 1, attributes);
break;
case 'K':
if (C < columns - 1)
deleteArea(C, R, columns - C, 1, attributes);
break;
case 'M': // RI
System.out.println("ESC M : R is "+R+", tm is "+tm+", bm is "+bm);
if (R > bm) // outside scrolling region
break;
if (R > tm) { // just go up 1 line.
R--;
} else { // scroll down
insertLine(R, 1, SCROLL_DOWN);
}
/* else do nothing ; */
if (debug > 2)
System.out.println("ESC M ");
break;
case 'H':
if (debug > 1)
System.out.println("ESC H at " + C);
/* right border probably ...*/
if (C >= columns)
C = columns - 1;
Tabs[C] = 1;
break;
case 'N': // SS2
onegl = 2;
break;
case 'O': // SS3
onegl = 3;
break;
case '=':
/*application keypad*/
if (debug > 0)
System.out.println("ESC =");
keypadmode = true;
break;
case '<': /* vt52 mode off */
vt52mode = false;
break;
case '>': /*normal keypad*/
if (debug > 0)
System.out.println("ESC >");
keypadmode = false;
break;
case '7': /*save cursor, attributes, margins */
Sc = C;
Sr = R;
Sgl = gl;
Sgr = gr;
Sa = attributes;
Sgx = new char[4];
for (int i = 0; i < 4; i++) Sgx[i] = gx[i];
Stm = getTopMargin();
Sbm = getBottomMargin();
if (debug > 1)
System.out.println("ESC 7");
break;
case '8': /*restore cursor, attributes, margins */
C = Sc;
R = Sr;
gl = Sgl;
gr = Sgr;
for (int i = 0; i < 4; i++) gx[i] = Sgx[i];
setTopMargin(Stm);
setBottomMargin(Sbm);
attributes = Sa;
if (debug > 1)
System.out.println("ESC 8");
break;
case '(': /* Designate G0 Character set (ISO 2022) */
term_state = TSTATE_SETG0;
usedcharsets = true;
break;
case ')': /* Designate G1 character set (ISO 2022) */
term_state = TSTATE_SETG1;
usedcharsets = true;
break;
case '*': /* Designate G2 Character set (ISO 2022) */
term_state = TSTATE_SETG2;
usedcharsets = true;
break;
case '+': /* Designate G3 Character set (ISO 2022) */
term_state = TSTATE_SETG3;
usedcharsets = true;
break;
case '~': /* Locking Shift 1, right */
gr = 1;
usedcharsets = true;
break;
case 'n': /* Locking Shift 2 */
gl = 2;
usedcharsets = true;
break;
case '}': /* Locking Shift 2, right */
gr = 2;
usedcharsets = true;
break;
case 'o': /* Locking Shift 3 */
gl = 3;
usedcharsets = true;
break;
case '|': /* Locking Shift 3, right */
gr = 3;
usedcharsets = true;
break;
case 'Y': /* vt52 cursor address mode , next chars are x,y */
term_state = TSTATE_VT52Y;
break;
default:
System.out.println("ESC unknown letter: " + c + " (" + ((int) c) + ")");
break;
}
break;
case TSTATE_VT52X:
C = c - 37;
term_state = TSTATE_VT52Y;
break;
case TSTATE_VT52Y:
R = c - 37;
term_state = TSTATE_DATA;
break;
case TSTATE_SETG0:
if (c != '0' && c != 'A' && c != 'B' && c != '<')
System.out.println("ESC ( " + c + ": G0 char set? (" + ((int) c) + ")");
else {
if (debug > 2) System.out.println("ESC ( : G0 char set (" + c + " " + ((int) c) + ")");
gx[0] = c;
}
term_state = TSTATE_DATA;
break;
case TSTATE_SETG1:
if (c != '0' && c != 'A' && c != 'B' && c != '<') {
System.out.println("ESC ) " + c + " (" + ((int) c) + ") :G1 char set?");
} else {
if (debug > 2) System.out.println("ESC ) :G1 char set (" + c + " " + ((int) c) + ")");
gx[1] = c;
}
term_state = TSTATE_DATA;
break;
case TSTATE_SETG2:
if (c != '0' && c != 'A' && c != 'B' && c != '<')
System.out.println("ESC*:G2 char set? (" + ((int) c) + ")");
else {
if (debug > 2) System.out.println("ESC*:G2 char set (" + c + " " + ((int) c) + ")");
gx[2] = c;
}
term_state = TSTATE_DATA;
break;
case TSTATE_SETG3:
if (c != '0' && c != 'A' && c != 'B' && c != '<')
System.out.println("ESC+:G3 char set? (" + ((int) c) + ")");
else {
if (debug > 2) System.out.println("ESC+:G3 char set (" + c + " " + ((int) c) + ")");
gx[3] = c;
}
term_state = TSTATE_DATA;
break;
case TSTATE_ESCSQUARE:
switch (c) {
case '8':
for (int i = 0; i < columns; i++)
for (int j = 0; j < rows; j++)
putChar(i, j, 'E', 0);
break;
default:
System.out.println("ESC # " + c + " not supported.");
break;
}
term_state = TSTATE_DATA;
break;
case TSTATE_DCS:
if (c == '\\' && dcs.charAt(dcs.length() - 1) == ESC) {
handle_dcs(dcs);
term_state = TSTATE_DATA;
break;
}
dcs = dcs + c;
break;
case TSTATE_DCEQ:
term_state = TSTATE_DATA;
switch (c) {
case '0':
case '1':
case '2':
case '3':
case '4':
case '5':
case '6':
case '7':
case '8':
case '9':
DCEvars[DCEvar] = DCEvars[DCEvar] * 10 + ((int) c) - 48;
term_state = TSTATE_DCEQ;
break;
case ';':
DCEvar++;
DCEvars[DCEvar] = 0;
term_state = TSTATE_DCEQ;
break;
case 's': // XTERM_SAVE missing!
if (true || debug > 1)
System.out.println("ESC [ ? " + DCEvars[0] + " s unimplemented!");
break;
case 'r': // XTERM_RESTORE
if (true || debug > 1)
System.out.println("ESC [ ? " + DCEvars[0] + " r");
/* DEC Mode reset */
for (int i = 0; i <= DCEvar; i++) {
switch (DCEvars[i]) {
case 3: /* 80 columns*/
setScreenSize(80, getRows(), true);
break;
case 4: /* scrolling mode, smooth */
break;
case 5: /* light background */
break;
case 6: /* DECOM (Origin Mode) move inside margins. */
moveoutsidemargins = true;
break;
case 7: /* DECAWM: Autowrap Mode */
wraparound = false;
break;
case 12:/* local echo off */
break;
case 9: /* X10 mouse */
case 1000: /* xterm style mouse report on */
case 1001:
case 1002:
case 1003:
mouserpt = DCEvars[i];
break;
default:
System.out.println("ESC [ ? " + DCEvars[0] + " r, unimplemented!");
}
}
break;
case 'h': // DECSET
if (debug > 0)
System.out.println("ESC [ ? " + DCEvars[0] + " h");
/* DEC Mode set */
for (int i = 0; i <= DCEvar; i++) {
switch (DCEvars[i]) {
case 1: /* Application cursor keys */
KeyUp[0] = "\u001bOA";
KeyDown[0] = "\u001bOB";
KeyRight[0] = "\u001bOC";
KeyLeft[0] = "\u001bOD";
break;
case 2: /* DECANM */
vt52mode = false;
break;
case 3: /* 132 columns*/
setScreenSize(132, getRows(), true);
break;
case 6: /* DECOM: move inside margins. */
moveoutsidemargins = false;
break;
case 7: /* DECAWM: Autowrap Mode */
wraparound = true;
break;
case 25: /* turn cursor on */
showCursor(true);
break;
case 9: /* X10 mouse */
case 1000: /* xterm style mouse report on */
case 1001:
case 1002:
case 1003:
mouserpt = DCEvars[i];
break;
/* unimplemented stuff, fall through */
/* 4 - scrolling mode, smooth */
/* 5 - light background */
/* 12 - local echo off */
/* 18 - DECPFF - Printer Form Feed Mode -> On */
/* 19 - DECPEX - Printer Extent Mode -> Screen */
default:
System.out.println("ESC [ ? " + DCEvars[0] + " h, unsupported.");
break;
}
}
break;
case 'i': // DEC Printer Control, autoprint, echo screenchars to printer
// This is different to CSI i!
// Also: "Autoprint prints a final display line only when the
// cursor is moved off the line by an autowrap or LF, FF, or
// VT (otherwise do not print the line)."
switch (DCEvars[0]) {
case 1:
if (debug > 1)
System.out.println("CSI ? 1 i : Print line containing cursor");
break;
case 4:
if (debug > 1)
System.out.println("CSI ? 4 i : Start passthrough printing");
break;
case 5:
if (debug > 1)
System.out.println("CSI ? 4 i : Stop passthrough printing");
break;
}
break;
case 'l': //DECRST
/* DEC Mode reset */
if (debug > 0)
System.out.println("ESC [ ? " + DCEvars[0] + " l");
for (int i = 0; i <= DCEvar; i++) {
switch (DCEvars[i]) {
case 1: /* Application cursor keys */
KeyUp[0] = "\u001b[A";
KeyDown[0] = "\u001b[B";
KeyRight[0] = "\u001b[C";
KeyLeft[0] = "\u001b[D";
break;
case 2: /* DECANM */
vt52mode = true;
break;
case 3: /* 80 columns*/
setScreenSize(80, getRows(), true);
break;
case 6: /* DECOM: move outside margins. */
moveoutsidemargins = true;
break;
case 7: /* DECAWM: Autowrap Mode OFF */
wraparound = false;
break;
case 25: /* turn cursor off */
showCursor(false);
break;
/* Unimplemented stuff: */
/* 4 - scrolling mode, jump */
/* 5 - dark background */
/* 7 - DECAWM - no wrap around mode */
/* 12 - local echo on */
/* 18 - DECPFF - Printer Form Feed Mode -> Off*/
/* 19 - DECPEX - Printer Extent Mode -> Scrolling Region */
case 9: /* X10 mouse */
case 1000: /* xterm style mouse report OFF */
case 1001:
case 1002:
case 1003:
mouserpt = 0;
break;
default:
System.out.println("ESC [ ? " + DCEvars[0] + " l, unsupported.");
break;
}
}
break;
case 'n':
if (debug > 0)
System.out.println("ESC [ ? " + DCEvars[0] + " n");
switch (DCEvars[0]) {
case 15:
/* printer? no printer. */
write(((char) ESC) + "[?13n", false);
System.out.println("ESC[5n");
break;
default:
System.out.println("ESC [ ? " + DCEvars[0] + " n, unsupported.");
break;
}
break;
default:
System.out.println("ESC [ ? " + DCEvars[0] + " " + c + ", unsupported.");
break;
}
break;
case TSTATE_CSI_EX:
term_state = TSTATE_DATA;
switch (c) {
case ESC:
term_state = TSTATE_ESC;
break;
default:
System.out.println("Unknown character ESC[! character is " + (int) c);
break;
}
break;
case TSTATE_CSI_TICKS:
term_state = TSTATE_DATA;
switch (c) {
case 'p':
System.out.println("Conformance level: " + DCEvars[0] + " (unsupported)," + DCEvars[1]);
if (DCEvars[0] == 61) {
output8bit = false;
break;
}
if (DCEvars[1] == 1) {
output8bit = false;
} else {
output8bit = true; /* 0 or 2 */
}
break;
default:
System.out.println("Unknown ESC [... \"" + c);
break;
}
break;
case TSTATE_CSI_EQUAL:
term_state = TSTATE_DATA;
switch (c) {
case '0':
case '1':
case '2':
case '3':
case '4':
case '5':
case '6':
case '7':
case '8':
case '9':
DCEvars[DCEvar] = DCEvars[DCEvar] * 10 + ((int) c) - 48;
term_state = TSTATE_CSI_EQUAL;
break;
case ';':
DCEvar++;
DCEvars[DCEvar] = 0;
term_state = TSTATE_CSI_EQUAL;
break;
case 'F': /* SCO ANSI foreground */
{
int newcolor;
System.out.println("ESC [ = "+DCEvars[0]+" F");
attributes &= ~COLOR_FG;
newcolor = ((DCEvars[0] & 1) << 2) |
(DCEvars[0] & 2) |
((DCEvars[0] & 4) >> 2) ;
attributes |= (newcolor+1) << COLOR_FG_SHIFT;
break;
}
case 'G': /* SCO ANSI background */
{
int newcolor;
System.out.println("ESC [ = "+DCEvars[0]+" G");
attributes &= ~COLOR_BG;
newcolor = ((DCEvars[0] & 1) << 2) |
(DCEvars[0] & 2) |
((DCEvars[0] & 4) >> 2) ;
attributes |= (newcolor+1) << COLOR_BG_SHIFT;
break;
}
default:
System.out.print("Unknown ESC [ = ");
for (int i=0;i<=DCEvar;i++)
System.out.print(DCEvars[i]+",");
System.out.println("" + c);
break;
}
break;
case TSTATE_CSI_DOLLAR:
term_state = TSTATE_DATA;
switch (c) {
case '}':
System.out.println("Active Status Display now " + DCEvars[0]);
statusmode = DCEvars[0];
break;
/* bad documentation?
case '-':
System.out.println("Set Status Display now "+DCEvars[0]);
break;
*/
case '~':
System.out.println("Status Line mode now " + DCEvars[0]);
break;
default:
System.out.println("UNKNOWN Status Display code " + c + ", with Pn=" + DCEvars[0]);
break;
}
break;
case TSTATE_CSI:
term_state = TSTATE_DATA;
switch (c) {
case '"':
term_state = TSTATE_CSI_TICKS;
break;
case '$':
term_state = TSTATE_CSI_DOLLAR;
break;
case '=':
term_state = TSTATE_CSI_EQUAL;
break;
case '!':
term_state = TSTATE_CSI_EX;
break;
case '?':
DCEvar = 0;
DCEvars[0] = 0;
term_state = TSTATE_DCEQ;
break;
case '0':
case '1':
case '2':
case '3':
case '4':
case '5':
case '6':
case '7':
case '8':
case '9':
DCEvars[DCEvar] = DCEvars[DCEvar] * 10 + ((int) c) - 48;
term_state = TSTATE_CSI;
break;
case ';':
DCEvar++;
DCEvars[DCEvar] = 0;
term_state = TSTATE_CSI;
break;
case 'c':/* send primary device attributes */
/* send (ESC[?61c) */
String subcode = "";
if (terminalID.equals("vt320")) subcode = "63;";
if (terminalID.equals("vt220")) subcode = "62;";
if (terminalID.equals("vt100")) subcode = "61;";
write(((char) ESC) + "[?" + subcode + "1;2c", false);
if (debug > 1)
System.out.println("ESC [ " + DCEvars[0] + " c");
break;
case 'q':
if (debug > 1)
System.out.println("ESC [ " + DCEvars[0] + " q");
break;
case 'g':
/* used for tabsets */
switch (DCEvars[0]) {
case 3:/* clear them */
Tabs = new byte[getColumns()];
break;
case 0:
Tabs[C] = 0;
break;
}
if (debug > 1)
System.out.println("ESC [ " + DCEvars[0] + " g");
break;
case 'h':
switch (DCEvars[0]) {
case 4:
insertmode = 1;
break;
case 20:
System.out.println("Setting CRLF to TRUE");
sendcrlf = true;
break;
default:
System.out.println("unsupported: ESC [ " + DCEvars[0] + " h");
break;
}
if (debug > 1)
System.out.println("ESC [ " + DCEvars[0] + " h");
break;
case 'i': // Printer Controller mode.
// "Transparent printing sends all output, except the CSI 4 i
// termination string, to the printer and not the screen,
// uses an 8-bit channel if no parity so NUL and DEL will be
// seen by the printer and by the termination recognizer code,
// and all translation and character set selections are
// bypassed."
switch (DCEvars[0]) {
case 0:
if (debug > 1)
System.out.println("CSI 0 i: Print Screen, not implemented.");
break;
case 4:
if (debug > 1)
System.out.println("CSI 4 i: Enable Transparent Printing, not implemented.");
break;
case 5:
if (debug > 1)
System.out.println("CSI 4/5 i: Disable Transparent Printing, not implemented.");
break;
default:
System.out.println("ESC [ " + DCEvars[0] + " i, unimplemented!");
}
break;
case 'l':
switch (DCEvars[0]) {
case 4:
insertmode = 0;
break;
case 20:
System.out.println("Setting CRLF to FALSE");
sendcrlf = false;
break;
default:
System.out.println("ESC [ " + DCEvars[0] + " l, unimplemented!");
break;
}
break;
case 'A': // CUU
{
int limit;
/* FIXME: xterm only cares about 0 and topmargin */
if (R > bm)
limit = bm + 1;
else if (R >= tm) {
limit = tm;
} else
limit = 0;
if (DCEvars[0] == 0)
R--;
else
R -= DCEvars[0];
if (R < limit)
R = limit;
if (debug > 1)
System.out.println("ESC [ " + DCEvars[0] + " A");
break;
}
case 'B': // CUD
/* cursor down n (1) times */
{
int limit;
if (R < tm)
limit = tm - 1;
else if (R <= bm) {
limit = bm;
} else
limit = rows - 1;
if (DCEvars[0] == 0)
R++;
else
R += DCEvars[0];
if (R > limit)
R = limit;
else {
if (debug > 2) System.out.println("Not limited.");
}
if (debug > 2) System.out.println("to: " + R);
if (debug > 1)
System.out.println("ESC [ " + DCEvars[0] + " B (at C=" + C + ")");
break;
}
case 'C':
if (DCEvars[0] == 0)
C++;
else
C += DCEvars[0];
if (C > columns - 1)
C = columns - 1;
if (debug > 1)
System.out.println("ESC [ " + DCEvars[0] + " C");
break;
case 'd': // CVA
R = DCEvars[0];
if (debug > 1)
System.out.println("ESC [ " + DCEvars[0] + " d");
break;
case 'D':
if (DCEvars[0] == 0)
C--;
else
C -= DCEvars[0];
if (C < 0) C = 0;
if (debug > 1)
System.out.println("ESC [ " + DCEvars[0] + " D");
break;
case 'r': // DECSTBM
if (DCEvar > 0) // Ray: Any argument is optional
{
R = DCEvars[1] - 1;
if (R < 0)
R = rows - 1;
else if (R >= rows) {
R = rows - 1;
}
} else
R = rows - 1;
setBottomMargin(R);
if (R >= DCEvars[0]) {
R = DCEvars[0] - 1;
if (R < 0)
R = 0;
}
setTopMargin(R);
_SetCursor(0, 0);
if (debug > 1)
System.out.println("ESC [" + DCEvars[0] + " ; " + DCEvars[1] + " r");
break;
case 'G': /* CUP / cursor absolute column */
C = DCEvars[0];
if (debug > 1) System.out.println("ESC [ " + DCEvars[0] + " G");
break;
case 'H': /* CUP / cursor position */
/* gets 2 arguments */
_SetCursor(DCEvars[0] - 1, DCEvars[1] - 1);
if (debug > 2) {
System.out.println("ESC [ " + DCEvars[0] + ";" + DCEvars[1] + " H, moveoutsidemargins " + moveoutsidemargins);
System.out.println(" -> R now " + R + ", C now " + C);
}
break;
case 'f': /* move cursor 2 */
/* gets 2 arguments */
R = DCEvars[0] - 1;
C = DCEvars[1] - 1;
if (C < 0) C = 0;
if (R < 0) R = 0;
if (debug > 2)
System.out.println("ESC [ " + DCEvars[0] + ";" + DCEvars[1] + " f");
break;
case 'S': /* ind aka 'scroll forward' */
if (DCEvars[0] == 0)
insertLine(rows - 1, SCROLL_UP);
else
insertLine(rows - 1, DCEvars[0], SCROLL_UP);
break;
case 'L':
/* insert n lines */
if (DCEvars[0] == 0)
insertLine(R, SCROLL_DOWN);
else
insertLine(R, DCEvars[0], SCROLL_DOWN);
if (debug > 1)
System.out.println("ESC [ " + DCEvars[0] + "" + (c) + " (at R " + R + ")");
break;
case 'T': /* 'ri' aka scroll backward */
if (DCEvars[0] == 0)
insertLine(0, SCROLL_DOWN);
else
insertLine(0, DCEvars[0], SCROLL_DOWN);
break;
case 'M':
if (debug > 1)
System.out.println("ESC [ " + DCEvars[0] + "" + (c) + " at R=" + R);
if (DCEvars[0] == 0)
deleteLine(R);
else
for (int i = 0; i < DCEvars[0]; i++)
deleteLine(R);
break;
case 'K':
if (debug > 1)
System.out.println("ESC [ " + DCEvars[0] + " K");
/* clear in line */
switch (DCEvars[0]) {
case 6: /* 97801 uses ESC[6K for delete to end of line */
case 0:/*clear to right*/
if (C < columns - 1)
deleteArea(C, R, columns - C, 1, attributes);
break;
case 1:/*clear to the left, including this */
if (C > 0)
deleteArea(0, R, C + 1, 1, attributes);
break;
case 2:/*clear whole line */
deleteArea(0, R, columns, 1, attributes);
break;
}
break;
case 'J':
/* clear below current line */
switch (DCEvars[0]) {
case 0:
if (R < rows - 1)
deleteArea(0, R + 1, columns, rows - R - 1, attributes);
if (C < columns - 1)
deleteArea(C, R, columns - C, 1, attributes);
break;
case 1:
if (R > 0)
deleteArea(0, 0, columns, R, attributes);
if (C > 0)
deleteArea(0, R, C + 1, 1, attributes);// include up to and including current
break;
case 2:
deleteArea(0, 0, columns, rows, attributes);
break;
}
if (debug > 1)
System.out.println("ESC [ " + DCEvars[0] + " J");
break;
case '@':
if (debug > 1)
System.out.println("ESC [ " + DCEvars[0] + " @");
for (int i = 0; i < DCEvars[0]; i++)
insertChar(C, R, ' ', attributes);
break;
case 'X':
{
int toerase = DCEvars[0];
if (debug > 1)
System.out.println("ESC [ " + DCEvars[0] + " X, C=" + C + ",R=" + R);
if (toerase == 0)
toerase = 1;
if (toerase + C > columns)
toerase = columns - C;
deleteArea(C, R, toerase, 1, attributes);
// does not change cursor position
break;
}
case 'P':
if (debug > 1)
System.out.println("ESC [ " + DCEvars[0] + " P, C=" + C + ",R=" + R);
if (DCEvars[0] == 0) DCEvars[0] = 1;
for (int i = 0; i < DCEvars[0]; i++)
deleteChar(C, R);
break;
case 'n':
switch (DCEvars[0]) {
case 5: /* malfunction? No malfunction. */
writeSpecial(((char) ESC) + "[0n");
if (debug > 1)
System.out.println("ESC[5n");
break;
case 6:
// DO NOT offset R and C by 1! (checked against /usr/X11R6/bin/resize
// FIXME check again.
// FIXME: but vttest thinks different???
writeSpecial(((char) ESC) + "[" + R + ";" + C + "R");
if (debug > 1)
System.out.println("ESC[6n");
break;
default:
if (debug > 0)
System.out.println("ESC [ " + DCEvars[0] + " n??");
break;
}
break;
case 's': /* DECSC - save cursor */
Sc = C;
Sr = R;
Sa = attributes;
if (debug > 3)
System.out.println("ESC[s");
break;
case 'u': /* DECRC - restore cursor */
C = Sc;
R = Sr;
attributes = Sa;
if (debug > 3)
System.out.println("ESC[u");
break;
case 'm': /* attributes as color, bold , blink,*/
if (debug > 3)
System.out.print("ESC [ ");
if (DCEvar == 0 && DCEvars[0] == 0)
attributes = 0;
for (int i = 0; i <= DCEvar; i++) {
switch (DCEvars[i]) {
case 0:
if (DCEvar > 0) {
if (terminalID.equals("scoansi")) {
attributes &= COLOR; /* Keeps color. Strange but true. */
} else {
attributes = 0;
}
}
break;
case 1:
attributes |= BOLD;
attributes &= ~LOW;
break;
case 2:
/* SCO color hack mode */
if (terminalID.equals("scoansi") && ((DCEvar - i) >= 2)) {
int ncolor;
attributes &= ~(COLOR | BOLD);
ncolor = DCEvars[i + 1];
if ((ncolor & 8) == 8)
attributes |= BOLD;
ncolor = ((ncolor & 1) << 2) | (ncolor & 2) | ((ncolor & 4) >> 2);
attributes |= ((ncolor) + 1) << COLOR_FG_SHIFT;
ncolor = DCEvars[i + 2];
ncolor = ((ncolor & 1) << 2) | (ncolor & 2) | ((ncolor & 4) >> 2);
attributes |= ((ncolor) + 1) << COLOR_BG_SHIFT;
i += 2;
} else {
attributes |= LOW;
}
break;
case 4:
attributes |= UNDERLINE;
break;
case 7:
attributes |= INVERT;
break;
case 8:
attributes |= INVISIBLE;
break;
case 5: /* blink on */
break;
/* 10 - ANSI X3.64-1979, select primary font, don't display control
* chars, don't set bit 8 on output */
case 10:
gl = 0;
usedcharsets = true;
break;
/* 11 - ANSI X3.64-1979, select second alt. font, display control
* chars, set bit 8 on output */
case 11: /* SMACS , as */
case 12:
gl = 1;
usedcharsets = true;
break;
case 21: /* normal intensity */
attributes &= ~(LOW | BOLD);
break;
case 25: /* blinking off */
break;
case 27:
attributes &= ~INVERT;
break;
case 28:
attributes &= ~INVISIBLE;
break;
case 24:
attributes &= ~UNDERLINE;
break;
case 22:
attributes &= ~BOLD;
break;
case 30:
case 31:
case 32:
case 33:
case 34:
case 35:
case 36:
case 37:
attributes &= ~COLOR_FG;
attributes |= ((DCEvars[i] - 30) + 1) << COLOR_FG_SHIFT;
break;
case 39:
attributes &= ~COLOR_FG;
break;
case 40:
case 41:
case 42:
case 43:
case 44:
case 45:
case 46:
case 47:
attributes &= ~COLOR_BG;
attributes |= ((DCEvars[i] - 40) + 1) << COLOR_BG_SHIFT;
break;
case 49:
attributes &= ~COLOR_BG;
break;
default:
System.out.println("ESC [ " + DCEvars[i] + " m unknown...");
break;
}
if (debug > 3)
System.out.print("" + DCEvars[i] + ";");
}
if (debug > 3)
System.out.print(" (attributes = " + attributes + ")m \n");
break;
default:
System.out.println("ESC [ unknown letter:" + c + " (" + ((int) c) + ")");
break;
}
break;
default:
term_state = TSTATE_DATA;
break;
}
if (C > columns) C = columns;
if (R > rows) R = rows;
if (C < 0) C = 0;
if (R < 0) R = 0;
if (doshowcursor)
setCursorPosition(C, R);
markLine(R, 1);
}
/* hard reset the terminal */
public void reset() {
gx[0] = 'B';
gx[1] = '0';
gx[2] = 'B';
gx[3] = 'B';
gl = 0; // default GL to G0
gr = 1; // default GR to G1
/* reset tabs */
int nw = getColumns();
if (nw < 132) nw = 132;
Tabs = new byte[nw];
for (int i = 0; i < nw; i += 8) {
Tabs[i] = 1;
}
/*FIXME:*/
term_state = TSTATE_DATA;
}
}
jta_2.6+dfsg.orig/de/mud/terminal/VDUDisplay.java 0000644 0001750 0001750 00000002251 10610772601 020402 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.terminal;
/**
* Generic display
*/
public interface VDUDisplay {
public void redraw();
public void updateScrollBar();
public void setVDUBuffer(VDUBuffer buffer);
public VDUBuffer getVDUBuffer();
}
jta_2.6+dfsg.orig/de/mud/terminal/keyCodes.conf 0000644 0001750 0001750 00000000225 10610772601 020167 0 ustar paul paul # this file has been intentionally left empty
#
# F1=F1-pressed
# ESCAPE=Escape
# SESCAPE=Shift-Escape
# CESCAPE=Control-Escape
# AESCAPE=Alt-Escape
jta_2.6+dfsg.orig/Makefile 0000644 0001750 0001750 00000013210 10610772601 014220 0 ustar paul paul # This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
#
# (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
#
# Please visit http://javatelnet.org/ for updates and contact.
#
# --LICENSE NOTICE--
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
# --LICENSE NOTICE--
#
JAVA = java
JAR = jar
JAVAC = javac
JAVADOC = javadoc
JAVAH = javah
#JAVA = /q/opt/jdk1.2.2/bin/java
#JAR = /q/opt/jdk1.2.2/bin/jar
#JAVAC = /q/opt/jdk1.2.2/bin/javac
#JAVADOC = /q/opt/jdk1.2.2/bin/javadoc
#DEBUG = -g -deprecation
DEBUG = -g
JFLAGS = -classpath $(CLASSPATH):jar/org.apache.crimson.jar:jar/jdom.jar:jar/gnu-regexp-1.0.8.jar:.
SRCDIR = de
PKGNAME = jta20
VERSION = `java -version 2>&1 | head -1 | \
sed 's/^java version //' | sed 's/"//g'`
DATE = `date +%Y%m%d-%H%M`
.SUFFIXES: .java .class
# compile java files to class
.java.class:
$(JAVAC) $(DEBUG) $(JFLAGS) $<
#
# major rules to create files
#
all: app cont doc jar tools/mrelayd tools/relayd
run: app
$(JAVA) $(JFLAGS) de.mud.jta.Main
doc: app
@echo Creating source documentation ...
@if [ ! -d doc ]; then mkdir doc; fi
@-rm -r doc/source/*.html doc/source/de
@$(JAVADOC) -d doc/source -version -author \
-sourcepath $(CLASSPATH):.:contrib \
`(find de -name \*.java -printf '%h\n'; \
(cd contrib; find * -name \*.java -printf '%h\n')) | \
sort | uniq | \
grep -v CVS | sed 's/\//./g'`; > /dev/null
@echo Source documentation done.
tex: app
@echo Creating latex source documentation ...
@$(JAVADOC) -docletpath ../tex -doclet TexDoclet \
-output $(PKGNAME).tex \
-docdir de/mud/jta `find de/mud -type d -print | \
grep -v CVS | grep -v '^de/mud$$' | sed 's/\//./g'`; > /dev/null
@echo Source documentation done.
jar: app build
@echo Creating binary archive ...
@if [ ! -d jar ]; then mkdir jar; fi
@touch "Created-$(DATE)"
@$(JAR) cvfm jar/$(PKGNAME).jar jta.manifest \
"Created-$(DATE)" README \
license/COPYING \
`find $(SRCDIR) -name \*.class` \
`find $(SRCDIR) -name \*.conf` > /dev/null
@rm -f Created-*
@echo Created jar/$(PKGNAME).jar
opt:
@[ -f ../Jopt.jar ] && $(JAVA) -jar ../Jopt.jar jar/$(PKGNAME).jar
@echo Created jar/$(PKGNAME)_o.jar
cont:
@echo Compiling contributed software ...
@(cd contrib; make)
dist: all opt revision changes
@echo Creating distribution package ...
@if [ "$(CVSROOT)" = "" ]; then echo "Missing CVSROOT!"; exit -1; fi
@(cvs -Q -d $(CVSROOT) export -D now -d $(PKGNAME) jta && \
export CLASSPATH=$(CLASSPATH):`pwd`/jar/cryptix.jar && \
cp REVISION CHANGES $(PKGNAME)/ && \
cp -r doc/source $(PKGNAME)/doc/ && \
touch "$(PKGNAME)/Created-$(DATE)" && \
sed "s//$(DATE)/g" < $(PKGNAME)/index.html \
> $(PKGNAME)/index.new && \
mv $(PKGNAME)/index.new $(PKGNAME)/index.html && \
echo "s//$(DATE)/g" > /tmp/jta.sed && \
(cd $(PKGNAME); make cont; \
rm -r contrib/de/mud/bsx contrib/de/mud/jta/plugin/BSX*; \
$(JAR) cvMf ../jar/contrib.jar contrib) &&\
(cd jar; for i in *.jar; do \
echo 's//'`\ls -l $$i | \
awk '{printf("%dk", $$5/1024);}' `'/g'; \
done) >> /tmp/jta.sed && \
sed -f /tmp/jta.sed < $(PKGNAME)/html/download.html \
> $(PKGNAME)/html/download.new && \
rm -f /tmp/jta.sed && \
mv $(PKGNAME)/html/download.new $(PKGNAME)/html/download.html && \
bin/users.pl > $(PKGNAME)/html/users.html.new && \
mv $(PKGNAME)/html/users.html.new $(PKGNAME)/html/users.html && \
rm -r $(PKGNAME)/tools/* \
$(PKGNAME)/html/users.db \
$(PKGNAME)/bin/users.pl && \
(cd $(PKGNAME); $(MAKE) clean) && \
$(JAR) cvMf jar/$(PKGNAME)-src.jar $(PKGNAME) \
) > /dev/null
@rm -rf $(PKGNAME)
@echo Created jar/$(PKGNAME)-src.jar
@$(JAR) cvMf jar/relay.jar \
tools/relayd tools/mrelayd tools/*.c tools/*.exe
build:
@echo "package de.mud.jta; public class Build implements Version { public String getDate() { return \"$(DATE)\"; } }" > de/mud/jta/Build.java
changes:
@rcs2log > CHANGES
@echo Created CHANGES.
revision:
@find de -name \*.java | xargs cat | grep @version | \
awk 'BEGIN{ \
printf("%-26.26s %2.2s.%-2.2s (%10s) %s\n", \
"File","R","M", "Date", "Last Accessed by:"); \
} \
{ \
split($$5,rev,"."); \
printf("%-26.26s %2.2s.%-2.2s (%10s) %s\n", \
$$4,rev[1],rev[2],$$6,$$8); \
}' \
> REVISION
@echo Created REVISION.
small: app
jar cvf jar/jta20-small.jar \
license/README \
de/mud/jta/SmallApplet*class \
de/mud/telnet/TelnetProtocolHandler.class \
de/mud/terminal/VDU*class \
de/mud/terminal/vt320*class \
de/mud/terminal/SoftFont.class
#
# application dependencies
#
app:
@find $(SRCDIR) -name \*.java | sed 's/java$$/class/' | xargs make
@echo Done.
clean:
-find . -name \*.class -print | xargs rm > /dev/null 2>&1
-find . -name \*~ -print | xargs rm > /dev/null 2>&1
-rm -f tools/relayd tools/mrelayd
cd jni && $(MAKE) clean
realclean: clean
-rm -f jar/$(PKGNAME).jar jar/$(PKGNAME)-src.jar
cd jni && $(MAKE) realclean
jta_2.6+dfsg.orig/index.html 0000644 0001750 0001750 00000020131 10610772601 014555 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0
Final Version 2.0
The software has been rewritten and comes with a
complete new base system. Apart from changes to the event handling in our
terminal
emulation the base parts have only been portet to Java 2 to retain
the efficiency and speed of our well known terminal emulation. Both the
terminal emulation and the telnet protocol handler have been taken
out of the software to be available as standalone packages to be used by
other programmers. The new bus/event system that connects the plugins ensures
ease of use and allows the addition of self-written plugins. Features include:
-
full Java 2 compatibility (works with Java
1.1.x! for now)
-
currently 11 plugins
-
application menu bar for plugin menus
-
configuration file
-
configurable foreground and background color
-
telnet and ssh support
-
PersonalJavatm edition quickly ported by Michael Andreasen for his Nokia 9210
This version should run with all runtime environments
that are at least Java 1.1.x compatible. If you are working with an older
Java runtime environment (e.g. 1.0) please go to the old
Java 1 version that will work with most currently available browsers.
Comments About this Release
Most of the requests we got have been included but some of it is more difficult
than imagined and sometimes difficult to achieve, like printing in applets.
It turned out that the pass-through printing will not really work in
applets and so we have left it out for now. The stubs are in the code,
but it will come in a later release eventually.
We have also as for now decided not to move on to a Swing based framework.
Most browsers around have a Java 1.1 compliant runtime and we don't want
to forces users to install the Java 2 plugin. It is planned for the next
release to move on and provide full Swing support.
Last but not least we would like to say "Thank you!" to everyone
who sent us comments, questions and bug reports and thus helped to make
the software better.
|
Did
you download the latest version? Have
a look at the timestamp:
What is ...
JTA - Telnet/SSH for the JAVA(tm) platform |
... is a fully featured telnet implementation coupled
with a very sophisticated terminal emulation for VT and ANSI
terminals.
Telnet was one of the first protocols to be developed during the early
stages of the ARPANET that later became the Internet. telnet allows you
to login to another Internet location to gain access to databases, library
catalogs, and interactive environments.
Despite its name, his software works either as applet or as
application.
The former is quite useful for service providers such as libraries or stock
tickers who would like to allow access to terminal driven applications
via the World Wide Web.
End users may find the application mode interesting as it provides a
fast and reliable telnet implementation to login to other workstations
or text-based online games, such as MUDs. |
|
Member Of The
Open Source Java Web-Ring
[Skip
Prev] [Prev]
[Next]
[Skip
Next] [Random]
[Next
5] [List
Sites]
jta_2.6+dfsg.orig/doc/ 0000755 0001750 0001750 00000000000 10610772601 013330 5 ustar paul paul jta_2.6+dfsg.orig/doc/tools/ 0000755 0001750 0001750 00000000000 10610772601 014470 5 ustar paul paul jta_2.6+dfsg.orig/doc/tools/relayd.html 0000644 0001750 0001750 00000013266 10610772601 016646 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: relayd/mrelayd
relayd/mrelayd
All Java Applets have several security restrictions that prevent a random
applet from doing damage on your computer or on the network.
Due to this reason it is not possible to open a telnet/ssh connection
to any other machine then the one the applet was downloaded from (the webserver).
Sometimes your application is not running on the webserver, in these
cases you need some kind of forwarder.
Any program, tool or firewall configuration that forwards connections
going to a specified port on the webserver to your real targethost and
port will do.
We have supplied to simple tools that establish that portforwarding.
They run on the webserver (you will need permission from its system
administrator).
Single Relay Demon
The first one is the single relaydemon. It can have just one targethost
and -port (but it can be used by multiple users at the same time).
It is started on the webserver host by running:
./relayd <localport> <targethost> <targetport>
In the applet you only set the parameter Socket.port to <localport>.
<targethost> and <targetport> are the host where the application
is.
<localport> can be choosen freely and should be above 1024.
Multiple Relay Demon
This one allows multiple users going to multiple targets (only needed if
you have more than one access point). If you have just one targethost and
targetport, the single relay demon above works as well!
It is started on the webserver host by running:
./mrelayd
It listens on port 31415 by default.
In the applet you have to change the parameters:
Socket.host to the target host you want to connect to.
Socket.port to the target port you want to connect
to.
Socket.relay to the webserver address.
Socket.relayPort to 31415.
(Note: Both relay demons impose a security risk. Always clear their
use with your administrator.)
|
Additional
Programmer Documentation is available:
You can download the relay
package from our download page!
|
jta_2.6+dfsg.orig/doc/index.html 0000644 0001750 0001750 00000015655 10610772601 015341 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: Documentation
Software Documentation
There are two classes of software documentation available.
One is for end users who would like to use the application/applet
on their web server or standalone and the other is for programmers
who would like to write additional plugins or use parts of the software
for their own development.
Additionally we will compile a small Frequently
Asked Questions list to answer the most common questions about the
software. So if you are new and have problems with the software have a
look there first, before you proceed and Email
to the authors.
The configuration documentation is split into
several parts. Each of the plugins has it's own set
of properties that may be used in applet.conf. Please refer to
the appropriate plugin documentation!
Documentation |
Remarks |
Frequently
Asked Questions |
Look here first if you are experiencing problems while using the software.
Most people have the same questions and those will be answered here. |
End
User Documentation |
Java Telnet
Application |
The standalone program to be used as a replacement for native
Telnet implementations. |
Java Telnet
Applet |
An applet implementation to be used by web service providers
or just as private remote log in to your home account. |
Plugins |
Documentation for available plug-ins. These include the standard plug-ins
like Socket, Telnet
and Terminal and some addional
ones like Status and SSH. |
Programmers
Documentation |
Top
of the Source
[no frames] |
This points to the top of the documentation source tree. It contains
a list of all packages and all Classes and Interfaces. |
|
You
may want to look at other sources for information about Java, Telnet, Terminal
Emulation and Secure Shell.
JavaSoft
Homepage |
Contains general information about Java, Documentation and downloadable
packages for the SDK (Software Development Kit) and JRE (Java Runtime Environment)
for Java. |
SSH Homepage |
Homepage of the company who invented SSH. If you are looking for information
on SSH (protocols, encryption) look there. |
|
jta_2.6+dfsg.orig/doc/Applet.html 0000644 0001750 0001750 00000037441 10610772601 015454 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: Applet
The Applet
The applet is for those people that provide terminal
based services and would like to add web capabilities to it.
The applet is the perfect way to make the transition from a terminal based
system to a more sophisticated web based framework easier. To bring the
terminal based application on the web one need to allow telnet or ssh access
to it (which usually already exists) and then set up the Applet on a page
on their web server. A second interesting usage is to set the applet up
on your private home page and use it to be able to log in from remote
locations without the need for any communication programs except a
Java capable web browser.
Quickstart
To quickly have the applet up and running following
the steps below:
-
Copy one of the examples in the html
directory (AppletTest.html
or AppletEnhanced.html)
to the directory on your web server where you would like to install the
applet.
-
Copy the jta20.jar
file to the same directory on your web server.
-
Edit the file you copied in step number one!
Look for the applet tag, set the CODEBASE
to
"." and remove the jar/ from the archive file
name.
Make sure it looks like the following piece
of HTML text:
<applet CODEBASE="."
ARCHIVE="jta20.jar"
CODE="de.mud.jta.Applet"
WIDTH=590 HEIGHT=360>
... some more configurations but not
essential now ...
</applet> |
-
Important: There is a problem with Netscape
that forces you to put the default.conf file
in the same directory as the jar and the html file. Simply download default.conf
and put it there.
-
Verify that all files (html and jar) are readable
for all users, so that the web server can handle them.
-
Go to the page AppletTest.html on
your web server. It should load the applet and prompt you with your telnet
login. If you have a problem check the files
again and have a look at the Java console of your web browser to find out
what the problem is. In case you still do not understand what is going
wrong have a look at our FAQ and next write
to us, but include a copy of your java console contents.
Applet Parameters
The new version of the software tries to reduce the amount of parameters
that you have to change to make the applet work. Instead of using these
applet parameters it uses a configuration file now. Which file to use is
determined by a parameter however.
Before we go into more detail on the applet parameters lets take a look
at the <applet> tag in general. The example files (see documentation)
usually contain a piece of html text like the following:
-
<applet CODEBASE="../"
-
ARCHIVE="jar/jta20.jar"
-
CODE="de.mud.jta.Applet"
-
WIDTH=590
HEIGHT=360>
-
<PARAM NAME="config" VALUE="applet.conf">
-
<!--
-
Make sure
the config file is in the same directory.
-
The file
applet.conf
looks just like default.conf.
-
applet.conf
overrides settings in default.conf!
-
-->
-
</applet>
<applet CODEBASE="../"
The first line contains the CODEBASE attribute
which points to the directory where the jar archives are located. This
is necessary as the example html files are in a different location. So
if you put the jar files in the same directory as your applet html file
you may set this to "." or simply remove the whole attribute.
ARCHIVE="jar/jta20.jar"
The next line contains the actual archive that is
used to get the classes from. Using a jar archive drastically reduces the
download time for the applet. In our example the jar archive rests in a
directory jar/ and you need to remove that directory part if you
placed the jar file in the same directory as the html file.
CODE="de.mud.jta.Applet"
The third line tells the browser which class to load
as the applet. You do not need to change anything here.
WIDTH=590 HEIGHT=360>
The last line of the opening <applet>
tag tells the browser how big to make the applet. In our example it has
a width of 590 pixels and a height of 360 pixels. Adapt this according
to your needs. In general the applet adapts its font size to match the
size of the applet.
Everything else will be explained below and finally you need to close
the applet definition using the </applet> tag.
The parameter format is <PARAM NAME="name" VALUE="value">
and has to appear within the <applet> and </applet>
tags.
Parameter |
Documentation |
NAME="config"
VALUE="configuration file" |
The parameter points to the configuration file for the applet. It may
be either a path relative to the CODEBASE or a fully qualified
URL. You can also set the configurations as PARAMS: see
below |
NAME="Applet.detach"
VALUE="boolean" |
Detach the actual terminal display and its components from the browser
window and run in a separate window. Use with care.
The boolean value may either be true or false.
See below! |
NAME="Applet.detach.fullscreen"
VALUE="boolean" |
When detaching make the resulting
window fill the whole screen. This might be useful for systems where people
have to remote login and should get the biggest font that is possible on
their screen. |
NAME="Applet.detach.title"
VALUE="string" |
Sets the window title of the detached
applet. |
NAME="Applet.disconnect"
VALUE="boolean" |
If set to true, the applet will disconnect from the remote
host if you leave the web page. If false, the applet will stay
connected and allows the user to continue the session. |
NAME="Applet.disconnect.closeWindow"
VALUE="boolean" |
Closes the detached window if the connection is lost. If you want to
disable this feature set it to false. |
NAME="Applet.detach.immediately"
VALUE="boolean" |
This parameter is usually set to false and determines if the applet
should detach immediately and run if set to true or simply display
the button and wait until it is pressed if false. |
NAME="Applet.detach.startText"
VALUE="string" |
Set this parameter if you want to use a start button to detach the
applet. The default value is "Connect". |
NAME="Applet.detach.stopText"
VALUE="string" |
The value set here will appear as the label of the button if the applet
is in detached mode and running. The default value is "Disconnect". |
NAME="Applet.detach.menuBar"
VALUE="boolean" |
Use this parameter if you want to disable the menubar in a detached
applet. Usually that menubar is visible in a detached window but can be
removed setting this parameter to false. |
Important: Any
configuration options you can specify in the configuration file (applet.conf
or default.conf) can also appear
as an applet's tag:
<PARAM NAME="parameter"
VALUE="value">
The only drawback is, before it is recognized a default
value of that parameter must have appeared in one of the configuration
files! |
To
use the applet keep in mind, a few of the following hints:
Java
Security |
Java Applet are only allowed to connect back to the server, where the
classes where loaded from. So you need a web server on the computer where
you want to log in. However, using our relayd
program on your web server you can log into other hosts as well.
Additionally you can use the Applet.Netscape.privilege property
in applet.conf. It can be set to one of the security
targets defined by Netscape. Most useful is the UniversalClipboardAccess
or UniversalConnect.
Read about the CODEBASE principals
in the Overview
of the Capabilities API. |
Without a
Web Server |
People sometimes try to load the html pages without a web server
from their local hard disk. This may work or it may not, as some security
manager implementations do not accept local hard disks as a secure source
for classes. |
|
jta_2.6+dfsg.orig/doc/Main.html 0000644 0001750 0001750 00000032770 10610772601 015113 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: Test Page
The Application (Main)
There are two ways to operate the program.
One is to simply start it and to configure everything within the application
or to give arguments, like host and port, on the command line. The first
way may be the least complicated as the menu entries are self descriptive.
You need to have installed a java runtime environment or java development
kit to run the application. On Microsoft Windows systems an installed Internet
Explorer with Java support should suffice though.
Quickstart
Make sure either the program java (JRE,
JDK) or jview (Windows IE) is in your path. Optionally you may
set the environment variable CLASSPATH to point to the file
jta20.jar
(see the box to the right for more information). Then try the following
command:
JRE or JDK on UNIX or Windows (for Windows and
IE installed, use jview instead)
java de.mud.jta.Main
alternative:
java -jar jta20.jar
Now you should see the following output:
** JTA - Telnet/SSH for the JAVA(tm) platformn
** Version 2.0 for Java 1.1.x and Java 2
** Copyright (c) 1996-2000 Matthias L. Jugel,
Marcus Meissner
** Build: 20000627-1208
jta: loading plugin 'Status' ...
jta: loading plugin 'Socket' ...
jta: loading plugin 'Telnet' ...
jta: loading plugin 'Terminal' ...
Some other messages might appear, but unless
you see an Exception a window should appear on your screen and
prompt you for login into your local host. If you are running on windows
you will probably see an error message and should append the target host
you want to connect to to the command line above.
Command Line Options
The application understand several command line arguments
to configure the way it looks and where to initially connect to. The following
command line arguments are possible:
de.mud.jta.Main [-plugins pluginlist]
[-addplugin plugin]
[-config file]
[host [port]]
(Options enclosed in brackets are
optional and may be left out.)
Option |
Documentation |
-plugins pluginlist |
Use this option to define a different list of plugins to be
loaded on startup of the application. Plugins are always added from back
to front and are separated by comma:
Socket,Telnet,Terminal
The above pluginlist is the default. |
-addplugin plugin |
Add a plugin to the list of standard plugins. |
-config file |
You can specify a configuration file here. See default.conf
for an example how it looks like. |
host |
The host where you would like to open the connection to. This must
be the second last entry on the command line, unless you leave out the
port.
You can either give the symbolic name of the host or the IP address. |
port |
If you want to connect to a different port that the default telnet
port (23) you need to enter the port number as the last entry on the command
line. |
Working with the Menu
After you startet the application as explained above you can change setting,
connect, disconnect or exit the application using the menus provided. The
default menus will be explained here, but some plugins
may provide their own menu and you will have to look at their own documentation
for further help.
File |
Connect |
(DOES NOT WORK CURRENTLY) Opens a dialog to select a new host and port to connect to.
By simply pressing Enter or clicking on the connect button will connect
to the default host and port that is shown in the editable text fields
on that dialog. |
Disconnect |
Disconnect from the host you are currently connected to. This option
is not available of you are not connected. |
Close |
Closes the current application window. If that window is the
last one the application exits as would happen if you selected the next
menu entry Exit below. An open connection in that window will be
closed by this operation. |
Exit |
Close all connections, all windows and exit the application. |
|
Edit |
Copy |
Copy the currently selected text on the terminal to the clipboard. |
Paste |
Paste text in the clipboard to the terminal. |
Select
All |
Select the complete terminal window and all text that is in the scrollback
buffer. |
|
Help |
Plugins |
This will give you a short introduction on plugins and will
explain how to use them or add/remove plugins from the software. Other
help entries may appear if the plugins provide their own help menus. |
About |
Selecting the help about the Javatm Telnet Application
gives you a dialog showing the names of the authors, some explanation on
licensing
and a link to the home page of the
software. |
|
|
There
are some differences in how to invoke the java interpreter for either Java
1.1.x or Java 2:
Java
1.1.x |
It is generally advicable to set the environment
variable CLASSPATH to point to the jta20.jar file. Examples
are shown below:
UNIX:
CLASSPATH=/java/jta20.jar
Windows:
CLASSPATH=C:\java\jta20.jar
|
Java 2 |
In Java 2 it is much easier to run the application as
you can simply use the command line parameter -cp to add the jar
file to the class path:
UNIX:
java -cp /java/jta20.jar
Windows:
java -cp C:\java\jta20.jar |
|
jta_2.6+dfsg.orig/doc/FAQ.html 0000644 0001750 0001750 00000017571 10610772601 014640 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: Test Page
Frequently Asked Questions
General
Questions |
What is telnet?
The telnet protocol was developed durin the early stages of
the Internet. Actually it was developed by people who set up the ARPA net.
It is a protocol to allow a user to remotely log into another computer
and perform tasks there as if he would be sitting on a terminal connected
to that computer.
What is SSH?
SSH or Secure SHell is just like the telnet protocol, but it
provided a secure way to log into that remote host. All communication is
encrypted, which makes it much harder for third parties to tamper with
the information you send over the network or to sniff out your password.
Will the software be ported to use Swing?
Good question. The software is ready to be ported to use Swing
components instead of the AWT components. But in favor of size and portability
we have decided not to use Swing. To support Swing on browsers that are
using Java 1.1 only you would have to provide the swing.jar as a separate
download and that would increase the download time dramatically. As soon
as Swing is supported by all browsers we will make use of those components.
|
Network
related questions |
I am behind a firewall, can I use the applet?
If you try to use an applet that is located outside your firewall
you will not be able to use it. This is due to the fact that the applet
tries to open a normal connection from your client to the remote host and
the firewall is simply in the way. The applet is not firewall enabled!
Can I tunnel a telnet connection through the http
(80) port?
Even though there are proxy applications that allow such tunneling
we do not actively support this. First it breaks the security a firewall
establishes and second the http port is not usually thought for tunneling
other connections. In contrast to http, telnet is connection oriented,
means it holds the connection open for the time of you doing work. http
does not!
|
Problem
related questions |
The applet will not load.
First, have a look at the Java console of your browser and
try to interpret the error message that appears there. Most commen cause
for problems with the loading of the applet are:
-
insufficient rights of the files (web browser can't read them)
-
missing file (make sure all files you need are there)
-
wrong path names (the CODEBASE and other tag attributes)
I can't get a connection!
It may happen that you do not see the login prompt. This may
have several reasons. First of all the target host may have telnet disabled.
Secondly if you are behind a firewall you will not be able to connect
to the remote host as the firewall usually prevents that. The applet is
a normal telnet implementation and can't cross firewalls!
|
|
The
FAQ does only answer questions directly related to the JTA. However, you
might also have a look at the following related FAQ's and RFC's:
|
jta_2.6+dfsg.orig/doc/plugins/ 0000755 0001750 0001750 00000000000 10610772601 015011 5 ustar paul paul jta_2.6+dfsg.orig/doc/plugins/Script.html 0000644 0001750 0001750 00000013675 10610772601 017157 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: Script Plugin
Script Plugin
To automate certain processes like login into guest accounts or BBS' the
script plugin enables you to write simple scripts of pattern and answer
pairs to be sent to the remote host if the pattern was found in the data
that came from the remote host.
To use the script simply put it into the plugin list as described in
the configuration of the Application or Applet.
The script language itself is very basic:
pattern|text|pattern_1|text_1
Any number of pattern and text pairs can be given and they will be processed
in the order they appear in the script. That means if pattern
is not matched pattern_1 will not be processed! For example the
following script would login into some computer:
login:|leo|password:|mypass
It first waits for the pattern "login:" and sends the text "leo\n"
(\n is a newline). Then it waits for the pattern "password:" and
if that appears it sends "mypass\n". Next you could add some pattern
that looks like your command prompt and issue a shell command.
If the first pattern is emtpy, its answer string will be sent on connect.
For instance:
|connect foo|login:|leo|password:|mypass
will send 'connect foo' upon connect.
You can configure the plugin using the following properties:
Property |
Documentation |
Script.script |
This property contains the script that is used by the plugin. |
NOTE:
The Script plugin MUST be BETWEEN the Telnet or SSH Plugin and
the Terminal plugin.
The order of plugins in the plugins line is important!
Example:
plugins=Status,Socket,Telnet,Script,Terminal |
Additional
Programmer Documentation is available:
de.mud.jta.plugin.Script |
This is the programmer documentation for the plugin. Use it as an example
if you want to write your own back end plugins. |
de.mud.jta.event |
This plugins uses some of the events and listeners described here. |
|
jta_2.6+dfsg.orig/doc/plugins/Socket.html 0000644 0001750 0001750 00000013020 10610772601 017123 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: Socket Plugin
Socket Plugin
The Socket plugin is a very low level plugin that is needed as back end
for the system to create network connections and provide the data streams
to and from the remote host.
You can configure the plugin using the following properties:
Property |
Documentation |
Socket.host |
This property should be set to the host you want to connect
to initially. The default for this property is the host of the code base
URL. |
Socket.port |
This is the port you want to connect to on the remote host. The default
value is 23 (telnet) but you may use any integer value. The port for ssh
is 22. |
Socket.relay |
Use this property if you plan to use the mrelayd (see download
page). It will allow applets to connect to any host!
Do not use this property if you
installed relayd on your web server! For more information
see the relayd documentation. |
Socket.relayPort |
In connection with Socket.relay this can be used to specify
the port on which the mrelay daemon is listening on the web server. It
defaults to 31415. |
|
Additional
Programmer Documentation is available:
de.mud.jta.plugin.Socket |
This is the programmer documentation for the plugin. Use it as an example
if you want to write your own back end plugins. |
de.mud.jta.event |
This plugins uses some of the events and listeners described here. |
|
jta_2.6+dfsg.orig/doc/plugins/Terminal.html 0000644 0001750 0001750 00000053147 10610772601 017464 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: Script Plugin
Terminal (ANSI/vt320) Plugin
The terminal plugin is a visual software component that acts as the front
end. It displays the data that is transmitted by the remote host and translates
keystrokes to be sent to the remote host. It implements an ANSI,
vt320/vt220/vt100 and SCOANSI compliant terminal.
Most of the features of the terminal emulation can be configured
using the properties explained below. Additionally it provides a plugin menu
that can be operated if a menu bar is available.
You can configure the plugin using the following properties:
Property |
Documentation |
General Properties
|
Terminal.foreground |
Set the foreground color of the terminal. You can use 24 but hexadecimal
values:
#ffffff is white and #000000
is black. This is just like the encoding you use in HTML. |
Terminal.background |
Set the background color of the terminal. You can use 24 but hexadecimal
values:
#ffffff is white and #000000
is black. This is just like the encoding you use in HTML. |
Terminal.cursor.foreground |
Set the cursor foreground color.
If unset this is the inverted current foreground. |
Terminal.cursor.background |
Set the cursor background color. If unset this is the inverted current
background. |
Terminal.localecho |
While both SSH and Telnet client part detect localechostate automatically,
it can be overridden using this option. This is only recommended if you really
need it.
Set to true for always localecho and false for never. |
Terminal.print.color |
Set to true to print the terminal in full color. The
default setting false will force the Terminal to print black
& white only. |
Terminal.colorSet |
Use this property to define a complete color set for the terminal. A
color set contains eight colors as defined by the ANSI standard.
The colorset should be in a file that is referenced by this
property as either a file name relative to the jar file or a complete URL.
The default value is /de/mud/terminal/colorSet.conf
.
The file contains a line for each color:
color0 = color
color1 = color
...
color7 = color
bold = color
invert = color
color can be either a name or a number similar to
the foreground and background above. The keywords bold and invert will set
a color instead of the actual attribute for display. Bold text will be displayed
using the color and inverted text will show up with a background color that
is set.
|
Terminal.border |
Declare the size of the border that will sourround the terminal. |
Terminal.borderRaised |
This property has no effect if Terminal.border is not set or
zero. It may be set to "true" or "false". |
Terminal.scrollBar |
Adds a scroll bar to the terminal using the direction set in the property.
Possible directions are "East" and "West".
Using a "none" removes the scrollbar completely. |
Terminal.beep |
If this property points to a fully
qualified URL of a sound file this will be played in case of a terminal
bell signal. This works for applets only.
Note: Some browsers (Netscape 4, IE 5.5 or earlier) sometimes can only play
.au files here. In IE the sound needs to be on the same server as the applet
or you get a security exception. |
Terminal Emulation Properties
|
Terminal.id |
Used to identify the type of the terminal. This is the string that is
sent to the remote host. Default is "vt320" but you may use any string,
like "vt100", "vt220" or "xterm" if it suits you.
If you change it to scoansi, it will change the linedrawing
characters to match the scoansi ones.
|
Terminal.answerback |
The string the terminal sents back when it gets an 'ENQ' code. You can
set it to anything you want or what your local environment requires. (The
default is just a pointer to this config option.) |
Terminal.buffer |
This sets the size of the scroll back buffer the terminal uses. The
buffer is allocated dynamically until it reaches this size. You cannot set
the scrollback buffer to a value smaller than the amount of lines on the
screen. |
Terminal.size |
Set the size of the terminal in terms of rows and lines. The value has
to be given in the following format:
[width,height
]
Whitespaces are allowed within the brackets and just before and after the
comma. The standard is "[80,24]" |
Terminal.resize |
This property defines the method that is applied when the terminal window
is resized. It may be either "font" - to resize the font
to match the window size or "screen" - to change the amount
of lines and columns displayed or "none" - to do nothing. |
Terminal.font |
Tells the terminal which font to use for the display of characters.
This is usually "Monospaced" as any other font name might
not be available on the client host. |
Terminal.fontStyle |
The font style to be used when looking up the font. The font style may
be "plain", "bold" or "italic
". The default is "plain". |
Terminal.fontSize |
The size of the font to be used. If you use automatic font resize this
will be used as the initial font size. |
Terminal.keyCodes |
This should be set to the URL of a property file that contains the key
codes you would like to use. The file is first tried using the resource
loading mechanism, which looks in the CLASSPATH and then as a URL. Have a
look at the file format for the key codes definition
. |
Terminal.VMS |
Set this property to "true" if you are connecting to
a VMS system. |
Terminal.IBM |
Set this to "true" if you would like to use PC ANSI
graphics characters as used by some BBS's. |
Terminal.encoding |
Use this property if you have real UNICODE fonts installed on your system
or at least fonts that include the characters you would like to display.
The default setting it ISO8859_1 but it may be used to make the terminal
aware of special characters like in the japanese (i.e. SJIS) or chinese
region. |
Definition of Key
Codes
The definition of key codes should only be done if
your application uses a very different keyboard layout than the standard vt320.
The definition of almost all special keys is possible and follows rules described
below:
# here is the rule
[SCA]
KEY=STRING
The characters enclosed in [ and ]
are optional and only one of the characters 'S' (Shift),
'C' (Control) or 'A' (Alt) may appear before
the KEY, which is a textual representation (F1, PGUP etc) of the key
you would like to redefine.
The new STRING you define to be
sent when pressing the key should come after the equal sign (=
). Hash marks (#) in the file declare a line as comment and will
be ignored. Some examples explain the syntax:
Send the string "test" when pressing
the F1 key:
F1 = test
On pressing Control + PGUP send the
string "pgup pressed":
CPGUP = pgup pressed
Redefine the key Alt + F12 to send
an escape character:
AF12 = \\e
As you can see the string
you can define may contain special characters which may be escaped using
the backslash (\). Allowed special characters follow in the table below:
(Important
: for some of the escape codes you need two backslashes as these are our
own definitions and not known by the Java Property mechanism)
Special Character |
Explanation |
\\b |
Backspace, this character is usually sent by the <-
key (not the cursor left key!). |
\\e |
Escape, this character is usually sent by the Esc key. |
\n
(only
one backslash) |
Newline, this character will move the cursor to a new line. On
UNIX systems it is equivalent to carriage return + newline. Usually the
Enter key send this character. |
\r
(only
one backslash) |
Carriage Return, this key moves the cursor to the
beginning of the line. In conjunction with Newline it moves the cursor
to the beginning of a new line. |
\t
(only
one backslash) |
Tabulator, the tab character is sent by the ->|
key and moves the cursor to the next tab stop defined by the terminal. |
\\v |
Vertical Tabulator, sends a vertical tabulator character. |
\\a |
Bell, sends a terminal bell character which should make the terminal
sound its bell, but the implementation is a silent one ;-) |
\\number |
Inserts the character that is defined by this number in the ISO
Latin1 character set. The number should be a decimal value. |
The following table explains
which key may be redefined. As explained above each of the keys may be prefixed
by a character defining the redefinition that occures if it is pressed in
conjunction with the shift, control or alt keys.
Key Representation |
Remarks |
F1 - F20
|
The function key, F1, F2 ... up to F20. |
PGUP
|
The Page Up key. |
PGDOWN
|
The Page Down key. |
END
|
The End key. |
HOME
|
The Home (Pos 1) key. |
INSERT
|
The Insert key. |
REMOVE
|
The Remove key. |
UP
|
The Cursor Up key. |
DOWN
|
The Cursor Down key. |
LEFT
|
The Cursor Left key. |
RIGHT
|
The Cursor right key. |
NUMPAD0 - NUMPAD9
|
The numbered Numpad keys. |
ESCAPE
|
The ESCAPE key. |
BACKSPACE
|
The backspace key. |
TAB
|
The tabulator key. |
|
Additional Programmer Documentation is available:
de.mud.jta.plugin.Terminal |
This is the programmer documentation for the plugin. Use it as an example
if you want to write your own back end plugins. |
de.mud.jta.event |
This plugins uses some of the events and listeners described here. |
de.mud.terminal |
Have a look here for the underlying terminal emulation package. |
If you produced
keyCode definition files you'd like to share with others
send them to us and we will publish them here.
AT 386 Terminal |
A key code definition file for an AT-386 Terminal. It should
work with ANSI and most version of UNIX. More info is in the file. |
|
jta_2.6+dfsg.orig/doc/plugins/SSH.html 0000644 0001750 0001750 00000013736 10610772601 016346 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: SSH Plugin
Secure Shell Plugin
Today it is advicable to use secure communications as public networks,
like the Internet are not secure. The secure shell (SSH) plugin provides
an easy to use, but secure way to log into a remote host. To use this plugin
make sure your remote host has a secure shell server running. It may be
used as a replacement for the Telnet plugin,
which does no encryption!
This implementation of SSH provides IDEA, Blowfish and RSA/PKCS#1 encryption
and was originally written in 1998 by
Cedric
Gourio. He used a part of the old Java Telnet Applet to write his Java
SSH client and so the code was similar to our old applet.
There are other implementations of ssh for Java available, but those
packages implement the whole ssh protocol and all features which makes
the packages very big. We tried to keep our implementation to a minimum
for easier download.
You can configure the plugin using the following properties:
(there will be configurable parts, but these
are not yet implemented!)
Security Note:
The applet is suspectible to the man-in-the-middle attacks published
by Security
Portal. We cannot avoid this. We can't even use the RSA based
host authorization, since the applet itself is downloaded from the remote
host, may not keep local state and might be modified by the man-in-the-middle.
The only way to guard against applet modification would be having it
signed with a trust certificate. This is too expensive both money- and
timewise for us.
So there is encryption, but it only guards against normal packetsniffing
attacks.
|
Additional
Programmer Documentation is available:
de.mud.jta.plugin.SSH |
This is the programmer documentation for the plugin. Use it as an example
if you want to write your own back end plugins. |
de.mud.jta.event |
This plugins uses some of the events and listeners described here. |
|
jta_2.6+dfsg.orig/doc/plugins/Status.html 0000644 0001750 0001750 00000013427 10610772601 017171 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: Status Plugin
Status Plugin
The status plugin displays status information about the connection. It
tells the user whether the program is online or offline and the name of
the host it is connected to. It uses symbolic names instead of port numbers
to inform the user which port it uses.
Additionally it can display info text in the status line that is read
from a URL.
This plugin must be put before the lowest level Socket
plugin!
You can configure the plugin using the following properties:
Property |
Documentation |
Status.info |
A URL pointing to a text file that is used to display additional
information in the status line. If the text file contains more than one
line each line is displayed 1/10 of the re-read interval. Additionally,
if a line starts with "#XXXXXX" where "XXXXXX" is a hexadecimal
color code. The line is displayed with that foreground color, overriding
the default. |
Status.font |
Set the font name of for the status line. |
Status.fontSize |
The size of the font to be used in the status line. |
Status.fontStyle |
The font style may be plain, bold, italic or "bold+italic". |
Status.foreground |
The foreground color of the status text. |
Status.background |
The background color of the status text |
Status.interval |
The interval to re-read the URL. This value is in seconds. |
|
Additional
Programmer Documentation is available:
de.mud.jta.plugin.Status |
This is the programmer documentation for the plugin. Use it as an example
if you want to write your own back end plugins. |
de.mud.jta.event |
This plugins uses some of the events and listeners described here. |
|
jta_2.6+dfsg.orig/doc/plugins/index.html 0000644 0001750 0001750 00000022056 10610772601 017013 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: Plugins
Plugins
The JTA uses a pugin scheme to allow easy addition
of software modules to the whole framework. These plugins may either be
used to work on the data streams, display additional information to the
user or be bywork. A few standard plugins are provided with the package.
These plugins are desribed here. Jump down to the
list.
In contrast to the old version we have introduced a new scheme for loading
plugins. It is now possible to have two or more plugins of the same
name with several different configurations used in one application.
The order of the plugins is important!
To accomplish that we have introduced identifier for the plugins. A
normal plugin list would look like:
plugins = Socket,Telnet,ButtonBar,Terminal
If you wanted to set up another button bar you are in trouble because
it would read the same options twice. So when setting up two plugins of
the same name you do as follows:
plugins = Socket,Telnet,ButtonBar(one),ButtonBar(two),Terminal
You give both plugins a unique name (one and two)
and use this name in any following configuration properties:
layout.ButtonBar(one) = North
layout.ButtonBar(two) = South
ButtonBar(one).setup = http://server/one.conf
ButtonBar(two).setup = http://server/two.conf
And that is it! If you define properties without the unique name they
will be used as fallback values in case a needed property is not set for
a specific plugin.
Have a look at the example page
and the applet.conf used there.
Note:If you are using the 'Script' plugin, note that it must be between the Telnet/SSH and Terminal plugin to get at the datastream.
Plugin |
Remarks |
Basic Plugins
|
Socket |
A most basic plugin used for low level communication with remote
hosts. It almost always needed. |
Telnet |
This is the actual handler for telnet type communications. It filters
the data streams and handles all telnet options. |
SSH |
For more secure communication you would rather use SSH instead of the
Telnet plugin as it provides a way for secure communication over insecure
networks. |
Shell
|
A shell plugin for use with local command shells. Not really useful
right now. |
Terminal |
This is a very important plugin as it is the actual terminal so you
can see what you do. It implements an ANSI/VT320 compatible terminal emulation. |
Add-On
|
Status |
An example how to write a listener plugin and display information. |
Timeout
|
A useful plugin for Applet users. It will allow you to define an idle
timeout to close the connection. |
ButtonBar
|
The new implemenation of our well known button bar module. With new
configuration options and better look than ever. |
Script
|
The script plugin may be used to automate login procedures for guest
accounts. |
Sink
|
The Sink plugin is a replacement of the Terminal plugin, which just
reads and discard data. Useful if you do not want output. |
URLFilter
|
Filters URLs out of the incoming data and displays a list to open them
in a web browser (Applet) |
MudConnector
|
A special plugin for www.mudconnector.com
to display a list of muds to connect to. |
BSX plugin
|
A third party plugin for use with BSX enabled MUDs. It is contained
in the contrib.jar package. |
|
If
you would like to write your own plugins you should refer to the following
documentation:
de.mud.jta |
This package is the main package and contains information about
the plugin system, applet and application. |
de.mud.jta.plugin |
All the standard plugins are documented here. |
de.mud.jta.event |
The plugins use some sort of event system to communicate. Look what
evens are implemented already. |
|
jta_2.6+dfsg.orig/doc/plugins/URLFilter.html 0000644 0001750 0001750 00000010755 10610772601 017517 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: Timeout Plugin
URLFilter Plugin
With the URLFilter plugin you can grab URLs from
the data stream you receive from the remote host. The URLs are captured
and shown in a list where you can select and display them in your web browser.
The plugin does not work when the JTA is run as an application.
To use the plugin put it in your plugin list,
preferrably between the Terminal and the Telnet
or SSH plugin.
Property |
Documentation |
URLFilter.protocols |
Defines the list of protocols the filter plugin recognises. The default
is http,ftp,gopher,file. |
|
Additional
Programmer Documentation is available:
|
jta_2.6+dfsg.orig/doc/plugins/Shell.html 0000644 0001750 0001750 00000011003 10610772601 016741 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: Shell Plugin
Shell Plugin
If you want to use the JTA do just provide a shell terminal, you use the
Shell plugin as a datasource (instead of Socket) at the left side of the
plugin bus.
This requires a JNI component for the lowlevel terminal stuff, which
needs to be compiled in the jni/ subdirectory of the applet sourcecode.
Configuration options are:
Configurationvalue |
Description |
Shell.command |
The command to be executed, default is /bin/sh. |
|
Additional
Programmer Documentation is available:
de.mud.jta.plugin.Shell |
This is the programmer documentation for the plugin. Use it as an example
if you want to write your own back end plugins. |
de.mud.jta.event |
This plugins uses some of the events and listeners described here. |
|
|
|
jta_2.6+dfsg.orig/doc/plugins/Timeout.html 0000644 0001750 0001750 00000013313 10610772601 017326 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: Timeout Plugin
Timeout Plugin
The timeout plugin can be used to make sure a connection
is only open as long as there is data beeing sent or received. You can
define the time the connection may be open until it will be closed by the
software. As some hosts may have difficulties with connections that simply
close the connection this plugin allows you to define a graceful logout
command.
The timeout will be reset every time something
happens and after a disconnection and reconnect it will start again automatically.
To use the plugin put it in your plugin list,
preferrably between the Terminal and the Telnet
or SSH plugin.
Property |
Documentation |
Timeout.seconds |
The seconds the connection may be open without data transmitted between
client and server. |
Timeout.command |
The graceful logout command to be used to close the connection from
server side. You may want to use "logout" or "exit" for
most UNIX systems. Make sure you put a newline (\n) at the end.
Example: logout\n |
Timeout.warning |
A warning message to be displayed on screen to tell the user that his
connection will be closed. Not implemented yet. |
|
Additional
Programmer Documentation is available:
|
jta_2.6+dfsg.orig/doc/plugins/ButtonBar.html 0000644 0001750 0001750 00000022334 10610772601 017603 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: ButtonBar Plugin
ButtonBar Plugin
The button bar plugin is very useful to provide short
cuts to common keystrokes and to define the unique look and feel of your
installation.
To use this plugin simply set the property as
defined below in the configuration file (applet.conf) and write a button
definition file. How the buttons are defined is described in the lower
part of this page.
Property |
Documentation |
ButtonBar.setup |
The URL of the configuration file for the button bar. The file contains
the definitions for look and function of the buttons and input fields. |
ButtonBar.clearFields |
If set to true the input fields will be cleared after return
or pressing a button that reads the field. |
ButtonBar Setup
The setup file contains definitions for buttons,
input fields and keywords for the layout of the components. Possible keywords
are:
the buttons are defined is described in the lower
part of this page.
Keyword |
Description |
button text command |
Create a new button with the displayed text that sends the command
upon pressing that button. The command can be a simple piece of text or
a function call as described below this table.
If the command contains whitespace characters enclose it in
quotation characters ("). |
label text |
Create a new textlabel with the displayed text. The text needs
to be enclosed with quotation characters (") if it contains whitespace. |
input name length command text |
Create a new input field with the specified name and length.
Optionally you can provide a command and an initial text
that is used to initialize the input field. If the text contains
whitespace characters enclose it in quotation characters ("). You can leave
the command out. Then the input field will not allow pressing return to
send its text! |
break |
If that keyword appears just after a button or input field that field
will stretch the rest of the line and the next button or input field will
be placed in the next line. |
stretch |
If that keyword appears just after a button or input field it will
cause that button or input field to take as much space in that line as
it can get. |
choice label1 value1 label2 value2 ... |
This keyword starts the definition of a choicebox selector. It is followed
by label/value pairs where the label is put into the options list of the
choicebox and the value will be sent as text (or executed as command) if
the item is selected.
It is best if the first label / value pair is left, since you cannot
easily select it. |
Buttons can contains function calls as command to issue commands like,
connect, disconnect or to exit the application. A function call looks like:
To connect to the remote host on pressing a button you would define
the following button
button Connect "\\$connect(\\@host@,\\@port@)"
input host 20 "myhost.mydomain.com"
input port 4 "23"
This will create a button labeled "Connect" which will call the
function connect with the arguments taken from the input fields
"host" and "port". If you do not encluse the command in quotation
characters you do not have to type two backspaces (\\).
Function |
Documentation |
\\$connect(\\@host@,\\@port@) |
Connect the applet to host and port. |
\\$disconnect() |
Disconnect the applet. |
\\$exit() |
Exit the application. Applets cannot exit the
application (due to security reasons). |
\\$break() |
Send a TELNET IAC BREAK command. This is usually needed by telnet
controllable embedded devices, like CISCO routers and similar. |
If you want to have a look at an example
look at the b1.conf or b2.conf
from our examples. |
Additional
Programmer Documentation is available:
|
jta_2.6+dfsg.orig/doc/plugins/Telnet.html 0000644 0001750 0001750 00000012255 10610772601 017137 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: Telnet Plugin
Telnet Plugin
This is a more complicated plugin. It handles all the telnet negotiations
between the client (this program) and the remote host. In cooperation with
other plugins, like the Terminal it negotiates
setting like terminal type and terminal size. However, as a user you do
not actually have to know about that.
There is nothing you could configure in the telnet layer. Make sure
you put this plugin in between a Socket-like
plugin and other plugins that operate above the
telnet protocol layer, like the Script plugin.
Property |
Documentation |
Telnet.crlf |
The Request for Comments defining the Telnet protocol suite (RFC 854
mostly), define the carriage return linefeed value to be the bytevalues
13,10. (\r\n).
This is the default as sent by the applet, which you can redefine it
using this property. |
Telnet.cr |
The RFC defines this to be 13,0 (\r\0). You can redefine it it with
this property |
|
Additional
Programmer Documentation is available:
de.mud.jta.plugin.Telnet |
This is the programmer documentation for the plugin. Use it as an example
if you want to write your own back end plugins. |
de.mud.jta.event |
This plugins uses some of the events and listeners described here. |
|
jta_2.6+dfsg.orig/doc/plugins/keyCodes.at386 0000644 0001750 0001750 00000002147 10610772601 017352 0 ustar paul paul #
# keyCodes.at386 contributed by Selwyn Rosenstein (SelwynR@scas.com)
#
# AT-386 ANSI Terminal keyCodes definition file for Java Terminal Applet with
# Terminal.id = at386
# Terminal.IBM = true
# Terminal.colorSet = /de/mud/terminal/colorSet.conf (default)
#
# This configuration file should be compatible with most ANSI monitors
# monitors running under most versions of UNIX.
#
# F1 thru F10
#
F1=\\eOP
F2=\\eOQ
F3=\\eOR
F4=\\eOS
F5=\\eOT
F6=\\eOU
F7=\\eOV
F8=\\eOW
F9=\\eOX
F10=\\eOY
F11=\\eOZ
F12=\\eOA
#
# Shift F1 thru F10
#
SF1=\\eOp
SF2=\\eOq
SF3=\\eOr
SF4=\\eOs
SF5=\\eOt
SF6=\\eOu
SF7=\\eOv
SF8=\\eOw
SF9=\\eOx
SF10=\\eOy
SF11=\\eOz
SF12=\\eOa
#
# Other cursor movement keys
#
UP=\\e[A
DOWN=\\e[B
RIGHT=\\e[C
LEFT=\\e[D
#
INSERT=\\e[@
# REMOVE=\\177 #( hex 7F / Decimal 127 / Octal 177 / DEL Key)
#
HOME=\\e[H
PGDOWN=\\e[U
PGUP=\\e[V
END=\\e[Y
#
#
# The following may be usefull to someone wishing to know the correct escape
# sequences to send to the terminal to change display modes
#
# LOW-INTENSITY=\\e[0m
# HIGH-INTENSITY=\\e[1m
# REVERSE=\\e[7m
# RESET=\\e[0m
#
# COLOR-SEQ=\\e[3%d;4%dm
# COLOR-8=1
jta_2.6+dfsg.orig/doc/plugins/Sink.html 0000644 0001750 0001750 00000010407 10610772601 016605 0 ustar paul paul
JTA - Telnet/SSH for the JAVA(tm) platform v2.0: Sink Plugin
Data Sink Plugin
If you have a script and do not want to display anything, this is the plugin
you need to plug in at the right end of the bus.
It just reads from the whole filter plugin chain and discards the rest
of the data that is left over from script and such plugins.
You cannot configure this plugin.
|
Additional
Programmer Documentation is available:
de.mud.jta.plugin.Sink |
This is the programmer documentation for the plugin. Use it as an example
if you want to write your own back end plugins. |
de.mud.jta.event |
This plugins uses some of the events and listeners described here. |
|
|
|
jta_2.6+dfsg.orig/JTA.iml 0000644 0001750 0001750 00000002645 10610772601 013713 0 ustar paul paul
jta_2.6+dfsg.orig/CHANGES 0000644 0001750 0001750 00000000000 10610772601 013544 0 ustar paul paul jta_2.6+dfsg.orig/README 0000644 0001750 0001750 00000004653 10610772601 013453 0 ustar paul paul JTA - Telnet/SSH for the JAVA(tm) platform
==========================================
(c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
Please make sure you read and understood the documentation that comes
with this software. The documentation explains about the most common
problems encountered and contains information about the license this
software is covered by. By using this software you agree to the terms
and conditions laid down in the license. For a quick start the license
is provided in the "license" directory in text format.
As it seems there are situations where people cannot agree to the license.
Please contact us to discuss the terms and conditions for a commercial
license. Use the address mentioned at the bottom of the file.
The most current version of the software can always be found at:
http://javassh.org/
The directories and files contained in the distribution contain the
following information:
README
You are currently reading this file.
REVISION
Contains a list of source files and their respective revision
number. This may be useful to find our which files have
changed since you last updated the software.
CHANGES
This file contains all the comments for the changes made to
the source files.
bin/
Contains scripts and additional helper programs.
de/
This is the root package name for the software. It contains
all Java related source files.
doc/
The documentation for the source is contained herein.
jar/
Using the make file to compile the source and building jar
files will result in the packages to be stored in that
directory.
jni/
Implementation of native methods for different platforms.
license/
Contains the license this software is covered by in text format.
We provide this software with confidence that is useful. If you feel that
you would like to repay the authors you may do so by either sending a
postcard or whatever you think is appropriate to either Matthias or Marcus.
The mail address can be achieved by sending an email to either leo@mud.de
or marcus@mud.de or both.
Quite a lot of people have helped us to debug the software and make it
better by giving us new ideas to implement. If you feel that an important
feature is missing do not hesitate to contact us. We thank all those
who have already done so.
Thank you for using the software.
Matthias L. Jugel, Marcus Meißner
Contact:
Matthias L. Jugel | Marcus Meißner
leo@mud.de | marcus@mud.de
jta_2.6+dfsg.orig/build.xml 0000644 0001750 0001750 00000007456 10610772601 014420 0 ustar paul paul
jta_2.6+dfsg.orig/contrib/ 0000755 0001750 0001750 00000000000 10610772601 014223 5 ustar paul paul jta_2.6+dfsg.orig/contrib/de/ 0000755 0001750 0001750 00000000000 10610772601 014613 5 ustar paul paul jta_2.6+dfsg.orig/contrib/de/mud/ 0000755 0001750 0001750 00000000000 10610772601 015400 5 ustar paul paul jta_2.6+dfsg.orig/contrib/de/mud/jta/ 0000755 0001750 0001750 00000000000 10610772601 016156 5 ustar paul paul jta_2.6+dfsg.orig/contrib/de/mud/jta/plugin/ 0000755 0001750 0001750 00000000000 10610772601 017454 5 ustar paul paul jta_2.6+dfsg.orig/contrib/de/mud/jta/plugin/EInput01.java 0000644 0001750 0001750 00000007444 10610772601 021675 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
import de.mud.jta.FilterPlugin;
import de.mud.jta.Plugin;
import de.mud.jta.PluginBus;
import de.mud.jta.VisualPlugin;
import javax.swing.JButton;
import javax.swing.JComponent;
import javax.swing.JMenu;
import javax.swing.JPanel;
import javax.swing.JTextArea;
import java.awt.BorderLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.IOException;
/**
* An example plugin that creates a text area and sends the text entered
* there to the remote host. The example explains how to create a filter
* plugin (for sending only) and a visual plugin.
*
* Maintainer: Matthias L. Jugel
*
* @version $Id: EInput01.java 499 2005-09-29 08:24:54Z leo $
* @author Matthias L. Jugel, Marcus Mei�ner
*/
public class EInput01 extends Plugin
implements FilterPlugin, VisualPlugin {
protected JTextArea input;
protected JButton send;
protected JPanel panel;
public EInput01(PluginBus bus, final String id) {
super(bus, id);
// create text field and send button
input = new JTextArea(10, 30);
send = new JButton("Send Text");
// add action listener to send the text
send.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
try {
// calls the write from FilterPlugin interface
write(input.getText().getBytes());
} catch (Exception e) {
System.err.println("EInput01: error sending text: " + e);
e.printStackTrace();
}
}
});
// create a panel and put text field and button into it.
panel = new JPanel(new BorderLayout());
panel.add("Center", input);
panel.add("South", send);
}
/** the source where we get data from */
protected FilterPlugin source = null;
public void setFilterSource(FilterPlugin plugin) {
source = plugin;
}
public FilterPlugin getFilterSource() {
return source;
}
/**
* Read data from the filter plugin source and return the amount read.
* We do not really do anything here
* @param b the array where to read the bytes in
* @return the amount of bytes actually read
*/
public int read(byte[] b) throws IOException {
return source.read(b);
}
/**
* Write data to the filter plugin source. This method is used by the
* visual components of the plugin to send data.
*/
public void write(byte[] b) throws IOException {
source.write(b);
}
/**
* This method returns the visual part of the component to be displayed
* by the applet or application at the specified location in the config
* file.
* @return a visual Component
*/
public JComponent getPluginVisual() {
return panel;
}
/**
* If you want to have a menu configure it and return it here.
* @return the plugin menu
*/
public JMenu getPluginMenu() {
return null;
}
}
jta_2.6+dfsg.orig/contrib/de/mud/jta/plugin/BSX.java 0000644 0001750 0001750 00000033352 10610772601 020761 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
import de.mud.bsx.BSXDisplay;
import de.mud.jta.FilterPlugin;
import de.mud.jta.Plugin;
import de.mud.jta.PluginBus;
import de.mud.jta.VisualPlugin;
import javax.swing.JComponent;
import javax.swing.JMenu;
import javax.swing.JPanel;
import java.io.IOException;
import java.awt.FlowLayout;
/**
* ultrahighspeed-BSX-command-parser as Plugin for JTA 2.0.
* Features:
- BSX-Commands: @RFS, @DFS, @DFO, @RQV, @SCE, @VIO, @RMO, @TMS
- faulttolerant handling of buggy BSX data -> ignoring until @RFS
- own support package: de.mud.bsx
@version Java 1.0
@author Thomas Kriegelstein (tk4@rb.mud.de)
*/
public class BSX extends Plugin
implements FilterPlugin, VisualPlugin {
/** the canvas that contains the Gfx */
protected BSXDisplay visual = new BSXDisplay();
/** the container for this plugin */
protected JPanel panel = new JPanel(new FlowLayout(FlowLayout.CENTER));
/* the BSX Commands to be understood */
private static final byte[] RFS = "@RFS".getBytes();
private static final byte[] SCE = "@SCE".getBytes();
private static final byte[] VIO = "@VIO".getBytes();
private static final byte[] DFS = "@DFS".getBytes();
private static final byte[] DFO = "@DFO".getBytes();
private static final byte[] RMO = "@RMO".getBytes();
private static final byte[] TMS = "@TMS".getBytes();
private static final byte[] RQV = "@RQV".getBytes();
/** the BSX style version of this Parser */
protected static String VERSION = "Java 1.0";
/** ignoreErrors in BSX data */
protected boolean ignoreErrors = true;
/**
* initialize the parser
*/
public BSX(PluginBus bus, final String id) {
super(bus, id);
panel.add(visual);
reset();
}
public JComponent getPluginVisual() {
return panel;
}
public JMenu getPluginMenu() {
return null;
}
FilterPlugin source;
public void setFilterSource(FilterPlugin source) {
this.source = source;
}
public FilterPlugin getFilterSource() {
return source;
}
public int read(byte[] b) throws IOException {
int len;
len = source.read(b);
len = parse(b, len);
return len;
}
public void write(byte[] b) throws IOException {
source.write(b);
}
private void write(String s) throws IOException {
write(s.getBytes());
}
/* ********************************************************************* */
/* "Ultrahighspeed" Statemachine for BSX Sequences */
/* ********************************************************************* */
/* Buffers & States */
/* ********************************************************************* */
private byte[] cmd = new byte[4]; // command */
private int cmdlen = 0; // length of command */
private byte[] id = new byte[64]; // identifier */
private int idlen = 0; // length of identifier */
private String obj = null; // string representation of id */
private int[][] data = null; // data */
private byte[] hex = new byte[2]; // 00-FF integer */
private int hexlen = 0; // length of integer */
private byte[] res = new byte[4096]; // storage for parse-result */
/* ********************************************************************* */
private int polys = 0; // 0..31 number of polygons in data */
private int edges = 0; // 0..31 number of edges in data */
private int poly = 0; // 0..31 current polygon in data */
private int pos = 0; // 0..edges*2+1 current position in polygon */
private int xpos = 0; // 0..15 xpos of object */
private int ypos = 0; // 0..7 ypos of object */
private int state = 0; // 0..8 what to do next */
/* ********************************************************************* */
/* 0 read until next '@' */
/* 1 read command */
/* 2 read identifier */
/* 3 read polygoncount */
/* 4 read edgecount */
/* 5 read polygondata */
/* 6 read xpos */
/* 7 read ypos */
/* 8 error in data -> discard until @RFS */
/* ********************************************************************* */
/**
* reset the parser
*/
protected void reset() {
cmdlen = idlen = hexlen = 0;
data = null;
obj = null;
polys = edges = poly = pos = xpos = ypos = state = 0;
}
private void DBG(String arg) {
System.err.println("BSX:\t" + arg);
}
/**
* parse the input buffer
@param b input buffer byte array
@param length count of valid bytes in buffer
@return new length of valid bytes in buffer
*/
protected int parse(byte[] b, int length) throws IOException {
int index,resindex;
for (index = resindex = 0; index < length; index++) {
switch (state) {
case 0: // read until next @
if ((char) b[index] == '@') {
cmd[cmdlen++] = b[index];
state = 1;
} else {
res[resindex++] = b[index];
}
break;
case 1: // read command
if ((char) b[index] == '@') {
for (int i = 0; i < cmdlen; i++)
res[resindex++] = cmd[i];
cmdlen = 0;
cmd[cmdlen++] = b[index];
} else {
cmd[cmdlen++] = b[index];
if (cmdlen == 4) {
if (equals(cmd, RFS)) {
visual.refreshScene();
reset();
} else if (equals(cmd, RQV)) {
write("#VER " + VERSION + "\n");
reset();
} else if (equals(cmd, SCE)) {
state = 2;
} else if (equals(cmd, VIO)) {
state = 2;
} else if (equals(cmd, DFO)) {
state = 2;
} else if (equals(cmd, RMO)) {
state = 2;
} else if (equals(cmd, DFS)) {
state = 2;
} else if (equals(cmd, TMS)) {
byte[] temp = "\n\n\tTerminate Session!\n\n".getBytes();
for (int i = 0; i < temp.length; i++)
res[resindex++] = temp[i];
reset();
} else {
for (int i = 0; i < cmdlen; i++)
res[resindex++] = cmd[i];
reset();
}
}
}
break;
case 2: // read identifier
if ((char) b[index] == '@') {
for (int i = 0; i < cmdlen; i++)
res[resindex++] = cmd[i];
for (int i = 0; i < idlen; i++)
res[resindex++] = id[i];
cmdlen = 0;
cmd[cmdlen++] = b[index];
idlen = 0;
state = 1;
} else if ((char) b[index] != '.') {
id[idlen++] = b[index];
} else {
obj = new String(id, 0, idlen);
if (equals(cmd, SCE)) {
String query = visual.showScene(obj);
if (query != null)
write(query);
reset();
} else if (equals(cmd, VIO)) {
state = 6;
} else if (equals(cmd, RMO)) {
visual.removeObject(obj);
reset();
} else if (equals(cmd, DFS)) {
state = 3;
} else if (equals(cmd, DFO)) {
state = 3;
}
}
break;
case 3: // read polygoncount
hex[hexlen++] = b[index];
if (hexlen == 2) {
polys = hexToInt(hex);
if (polys > 32 || polys < 0) {
DBG("polys " + polys + "\t" + obj);
if (ignoreErrors) {
DBG("ignoring till @RFS");
cmdlen = 0;
state = 8;
} else {
reset();
}
} else {
data = new int[polys][];
if (polys > 0) {
state = 4;
} else { // Empty BSX is "00"
if (equals(cmd, DFS)) {
visual.defineScene(obj,
data);
} else if (equals(cmd, DFO)) {
visual.defineObject(obj,
data);
}
reset();
}
hexlen = 0;
}
}
break;
case 4: // read edgecount
hex[hexlen++] = b[index];
if (hexlen == 2) {
edges = hexToInt(hex);
if (edges > 32 || edges < 0) {
DBG("edges " + edges + "\t" + obj);
if (ignoreErrors) {
DBG("\tignoring till @RFS");
cmdlen = 0;
state = 8;
} else {
reset();
}
} else {
data[poly] = new int[1 + edges * 2];
state = 5;
hexlen = 0;
}
}
break;
case 5: // read polygondata
hex[hexlen++] = b[index];
if (hexlen == 2) {
int c = hexToInt(hex);
if (c < 0) {
DBG("edge " + c + "\t" + obj);
if (ignoreErrors) {
DBG("\tignoring till @RFS");
cmdlen = 0;
state = 8;
} else {
reset();
}
} else {
data[poly][pos] = c;
hexlen = 0;
pos++;
if (pos == edges * 2 + 1) {
poly++;
state = 4;
pos = 0;
if (poly == polys) {
if (equals(cmd, DFS)) {
visual.defineScene(obj,
data);
} else if (equals(cmd, DFO)) {
visual.defineObject(obj,
data);
}
reset();
}
}
}
}
break;
case 6: // read xpos
hex[hexlen++] = b[index];
if (hexlen == 2) {
xpos = hexToInt(hex);
if (xpos > 15 || xpos < 0) {
DBG("xpos " + xpos + "\t" + obj);
reset();
} else {
state = 7;
hexlen = 0;
}
}
break;
case 7: // read ypos
hex[hexlen++] = b[index];
if (hexlen == 2) {
ypos = hexToInt(hex);
if (ypos > 7 || ypos < 0) {
DBG("ypos " + ypos + "\t" + obj);
reset();
} else {
String query = visual.showObject(obj, xpos, ypos);
if (query != null)
write(query);
reset();
}
}
break;
case 8: // error in data -> read until @RFS
if ((char) b[index] == '@') // start of new command sequence
{
cmdlen = 0;
cmd[cmdlen++] = b[index];
} else if (cmdlen > 0) // read command sequence
{
cmd[cmdlen++] = b[index];
if (cmdlen == 4) // command sequence complete
{
if (equals(cmd, RFS)) {
visual.refreshScene();
reset();
} else // wrong command
{
cmdlen = 0;
}
}
} else // discard this byte
{
}
break;
}
}
System.arraycopy(res, 0, b, 0, resindex);
return resindex;
}
/**
* compares two byte[]
@return true if they contain the same values
*/
protected boolean equals(byte[] a, byte[] b) {
for (int i = 0; i < a.length && i < b.length; i++)
if (a[i] != b[i]) return false;
return a.length == b.length;
}
/**
* computes an integer from an byte[2] containing a
* hexadecimal representation in capitol letters (0-9,A-F)
@return -1 on parseerror
*/
protected int hexToInt(byte[] b) {
int f = 0,g = 0;
char h = 0,i = 0;
h = (char) b[0];
i = (char) b[1];
if (h >= 'A' && h <= 'F')
f = h - 'A' + 10;
else if (h >= '0' && h <= '9')
f = h - '0';
else
return -1;
if (i >= 'A' && i <= 'F')
g = i - 'A' + 10;
else if (i >= '0' && i <= '9')
g = i - '0';
else
return -1;
return f * 16 + g;
}
}
jta_2.6+dfsg.orig/contrib/de/mud/jta/plugin/MUDColorizer.java 0000644 0001750 0001750 00000022706 10610772601 022644 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.jta.plugin;
import de.mud.jta.FilterPlugin;
import de.mud.jta.Plugin;
import de.mud.jta.PluginBus;
import de.mud.jta.PluginConfig;
import de.mud.jta.event.ConfigurationListener;
import de.mud.jta.event.EndOfRecordListener;
import gnu.regexp.RE;
import java.io.IOException;
import java.net.URL;
import java.util.Enumeration;
import java.util.Hashtable;
import java.util.Properties;
/**
* Some little hack for colors and prompts.
* We are using GNU, so we should release this under the GPL :)
*
* - needs gnu.regexp package (approx. 22 kB)
*
- handles prompt with EOR (maybe buggy, but testet with mglib 3.2.6)
*
- colorizes single lines using regular expressions
*
* @author Thomas Kriegelstein
*/
public class MUDColorizer extends Plugin
implements FilterPlugin, EndOfRecordListener, ConfigurationListener {
public static String BLACK = "[30m";
public static String RED = "[31m";
public static String BRED = "[1;31m";
public static String GREEN = "[32m";
public static String BGREEN = "[1;32m";
public static String YELLOW = "[33m";
public static String BYELLOW = "[1;33m";
public static String BLUE = "[34m";
public static String BBLUE = "[1;34m";
public static String PINK = "[35m";
public static String BPINK = "[1;35m";
public static String CYAN = "[36m";
public static String BCYAN = "[1;36m";
public static String WHITE = "[37m";
public static String BWHITE = "[1;37m";
public static String NORMAL = "[0m";
public static String BOLD = "[1m";
/* Prompthandling:
* if we do have a prompt, in every read of a new line, write a
* Clearline (ie. \r\e[K), then write the text and then
* rewrite the prompt after the last \n
*/
private Object[] exps = null;
public MUDColorizer(PluginBus bus, final String id) {
super(bus, id);
bus.registerPluginListener(this);
}
public void setConfiguration(PluginConfig cfg) {
String tmp;
if ((tmp = cfg.getProperty("MUDColorizer", id, "regexpSet")) != null) {
Properties regexpSet = new Properties();
try {
regexpSet.load(getClass().getResourceAsStream(tmp));
} catch (Exception e) {
try {
regexpSet.load(new URL(tmp).openStream());
} catch (Exception ue) {
error("cannot find regexpSet: " + tmp);
error("resource access failed: " + e);
error("URL access failed: " + ue);
regexpSet = null;
}
}
if (regexpSet != null && !regexpSet.isEmpty()) {
exps = new Object[regexpSet.size() * 2];
Hashtable colors = new Hashtable();
colors.put("BLACK", BLACK);
colors.put("RED", RED);
colors.put("BRED", BRED);
colors.put("GREEN", GREEN);
colors.put("BGREEN", BGREEN);
colors.put("YELLOW", YELLOW);
colors.put("BYELLOW", BYELLOW);
colors.put("BLUE", BLUE);
colors.put("BBLUE", BBLUE);
colors.put("PINK", PINK);
colors.put("BPINK", BPINK);
colors.put("CYAN", CYAN);
colors.put("BCYAN", BCYAN);
colors.put("WHITE", WHITE);
colors.put("BWHITE", BWHITE);
colors.put("NORMAL", NORMAL);
colors.put("BOLD", BOLD);
Enumeration names = regexpSet.propertyNames();
int ex = 0;
while (names.hasMoreElements()) {
String exp = (String) names.nextElement();
RE re = null;
try {
re = new RE(exp);
} catch (Exception e) {
System.err.println("Something wrong with regexp: " +
ex + "\t" + exp);
System.err.println(e);
}
exps[ex++] = re;
exps[ex++] = colors.get(regexpSet.get(exp));
System.out.println("MUDColorizer: loaded: " + exp + " with " + regexpSet.get(exp));
}
}
}
}
FilterPlugin source;
public void setFilterSource(FilterPlugin source) {
this.source = source;
}
public FilterPlugin getFilterSource() {
return source;
}
public void EndOfRecord() {
readprompt = true;
}
private byte[] transpose(byte[] buf) {
byte[] nbuf;
int nbufptr = 0;
nbuf = new byte[8192];
/* Prompthandling I */
if (promptwritten && prompt != null && prompt.length > 0) {
// "unwrite"
nbuf[nbufptr++] = (byte) '\r';
nbuf[nbufptr++] = 27;
nbuf[nbufptr++] = (byte) '[';
nbuf[nbufptr++] = (byte) 'K';
promptwritten = false;
}
if (readprompt) {
int index;
for (index = buf.length - 1; index >= 0; index--)
if (buf[index] == '\n') break;
index++;
prompt = new byte[buf.length - index];
System.arraycopy(buf, index, prompt, 0, buf.length - index);
readprompt = false;
writeprompt = true;
promptwritten = false;
promptread = true;
// System.out.println("Neues Prompt: $"+new String(prompt)+"$");
}
/* /Prompthandling I */
/* Colorhandling should be done herein
* Problem: Strings aren�t allways transposed completely
* sometimes a \n is in the next transpose buffer
* Solution: Buffer lines outside like read does
*/
if (promptwritten) {
lp = 0;
line[0] = 0;
}
for (int i = 0; i < buf.length; i++, lp++) {
// nbuf[nbufptr++] = buf[i];
line[lp] = buf[i];
if (line[lp] == '\n') {
String l = new String(line, 0, lp + 1);
boolean colored = false;
boolean useexp = (exps != null);
for (int ex = 0; !colored && useexp && ex < exps.length; ex += 2) {
RE exp = (RE) exps[ex];
if (null != exp.getMatch(l)) {
byte[] color = (byte[]) ((String) exps[ex + 1]).getBytes();
System.arraycopy(color, 0, nbuf, nbufptr, color.length);
nbufptr += color.length;
System.arraycopy(line, 0, nbuf, nbufptr, lp + 1);
nbufptr += lp + 1;
byte[] normal = NORMAL.getBytes();
System.arraycopy(normal, 0, nbuf, nbufptr, normal.length);
nbufptr += normal.length;
colored = true;
}
}
if (!colored) {
System.arraycopy(line, 0, nbuf, nbufptr, lp + 1);
nbufptr += lp + 1;
}
colored = false;
lp = -1;
line[0] = 0; // gets overwritten soon;
}
}
if (promptread) {
lp = 0;
line[0] = 0;
promptread = false;
}
/* /Colorhandling */
/* Prompthandling II */
if (buf[buf.length - 1] == '\n') writeprompt = true;
if (buf[buf.length - 1] == '\r') writeprompt = true;
if (writeprompt && prompt != null && prompt.length > 0) {
// "rewrite"
nbuf[nbufptr++] = (byte) '\r';
nbuf[nbufptr++] = 27;
nbuf[nbufptr++] = (byte) '[';
nbuf[nbufptr++] = (byte) 'K';
System.arraycopy(prompt, 0, nbuf, nbufptr, prompt.length);
nbufptr += prompt.length;
promptwritten = true;
writeprompt = false;
}
/* /Promphandling II */
byte[] xbuf = new byte[nbufptr];
System.arraycopy(nbuf, 0, xbuf, 0, nbufptr);
return xbuf;
}
// einzufaerbende zeile
private int lp = 0;
private byte[] line = new byte[8192];
// prompt handeln
private boolean readprompt = false;
private boolean promptread = false;
private boolean writeprompt = false;
private boolean promptwritten = false;
private byte[] prompt = null;
// bufferoverflows handeln
private byte[] buffer = null;
private int pos = 0;
public int read(byte[] b) throws IOException {
// empty the buffer before reading more data
if (buffer != null) {
int amount = (buffer.length - pos) <= b.length ?
buffer.length - pos : b.length;
System.arraycopy(buffer, pos, b, 0, amount);
if (pos + amount < buffer.length) {
pos += amount;
} else {
buffer = null;
pos = 0;
}
return amount;
}
// now we are sure the buffer is empty and read on
int n = source.read(b);
if (n > 0) {
byte[] tmp = new byte[n];
System.arraycopy(b, 0, tmp, 0, n);
buffer = transpose(tmp);
if (buffer != null && buffer.length > 0) {
int amount = buffer.length <= b.length ? buffer.length : b.length;
System.arraycopy(buffer, 0, b, 0, amount);
pos = n = amount;
if (amount == buffer.length) {
buffer = null;
pos = 0;
}
} else
return 0;
}
return n;
}
public void write(byte[] b) throws IOException {
if (b[b.length - 1] == '\n') {
writeprompt = true;
promptwritten = false;
}
source.write(b);
}
}
jta_2.6+dfsg.orig/contrib/de/mud/bsx/ 0000755 0001750 0001750 00000000000 10610772601 016174 5 ustar paul paul jta_2.6+dfsg.orig/contrib/de/mud/bsx/BSXScene.java 0000644 0001750 0001750 00000011472 10610772601 020456 0 ustar paul paul /*
* This file is part of "JTA - Telnet/SSH for the JAVA(tm) platform".
*
* (c) Matthias L. Jugel, Marcus Meißner 1996-2005. All Rights Reserved.
*
* Please visit http://javatelnet.org/ for updates and contact.
*
* --LICENSE NOTICE--
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* --LICENSE NOTICE--
*
*/
package de.mud.bsx;
import java.awt.Point;
import java.awt.Graphics;
import java.awt.Color;
import java.util.Vector;
import java.util.Enumeration;
/**
* Scene object for BSX Scenes.
- keeps track on objects with their positions
- renders its data on a given Graphics object
@author Thomas Kriegelstein (tk4@rb.mud.de)
@version 1.1
*/
public class BSXScene extends BSXObject
{
/** the eight BSX depth layers */
protected final Vector[] layers = new Vector[8];
/** positions of the contained objects */
protected final Vector[] positions = new Vector[8];
/**
* checks if specified object is within this scene
@param id object to be checked
@return true if object is here, otherwise false
*/
public boolean containsObject( String id )
{
return (-1==layerOfObject(id)?false:true);
}
/**
* adds an object to this scene
@param id object to be added
@param x x-position of object in scene
@param y y-position of object in scene
*/
public void addObject( String id, int x, int y)
{
int layer;
if (-1!=(layer = layerOfObject(id))) {
removeObject(id,layer);
}
layers[y].addElement(id);
positions[y].addElement(new Point(x,y));
}
/**
* query the layer of the specified object
@param id object in this scene
@return -1 object not in this scene, 0..7 layer of the object
*/
public int layerOfObject( String id )
{
for (int layer = 0;layer