import java.io.InputStream;
import java.io.OutputStream;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.lang.Integer;
class Agent implements Runnable
{
private InputStream in = null;
private OutputStream out = null;
private AgentMonitor am = null;
private byte buffer[] = null;
private static int BUFFER_SIZE = 4096;
private String name = null;
private boolean echo = false;
// Format the current time in a nice iso 8601 format.
private static SimpleDateFormat formatter =
new SimpleDateFormat ("yyyy-MM-dd hh:mm:ss.S");
public Agent(
InputStream in,
OutputStream out,
AgentMonitor am,
String name,
boolean echo
)
{
this.in = in;
this.out = out;
this.am = am;
this.name = new String(name);
this.echo = echo;
buffer = new byte[BUFFER_SIZE];
Thread t = new Thread(this);
t.start();
}
public void run()
{
try
{
int bytesRead = 0;
while(true)
{
if((bytesRead = in.read(buffer, 0, BUFFER_SIZE)) == -1)
break;
if(echo)
doEcho(buffer, bytesRead);
out.write(buffer, 0, bytesRead);
}
}
catch(IOException e) {}
am.agentHasDied(this);
}
private void doEcho(byte buffer[], int nBytes)
{
synchronized(System.out)
{
Date currentTime = new Date();
System.out.println("[" + name + ", (" + nBytes + " bytes) " + formatter.format(currentTime) +"]");
StringBuffer sb = new StringBuffer(nBytes); // formatted string
StringBuffer pb = new StringBuffer(4 * nBytes); // formatted binary string
String hb = new String(); // hex buffer string
String tb = new String(); // text buffer string
int j = 0; // line position counter
int c = 0; // byte counter
float k = 0; // binary character counter
for(int i = 0; i < nBytes; i ++)
{
int value = (buffer[i] & 0xFF); // 32 bit Unicode to 16 bit ASCII
if(value == '\r' || value == '\n' || value == '\t' ||
(value >= ' ' && value <= '~')) {
sb.append((char)value); // text character
}
else {
sb.append("[" + hexPad(Integer.toHexString(value), 2) + "]"); // binary character
k++;
}
if (value >= ' ' && value <= '~') {
tb = tb + (char)value; // "printable" character
} else {
tb = tb + "."; // non-printable
}
hb = hb + hexPad(Integer.toHexString(value), 2);
if (j == 3 || j == 7 || j == 11) { // for readability, space every 4 chars
hb = hb + " ";
tb = tb + " ";
}
if (j == 15) { // 16 characters per line
pb.append(hexPad(Integer.toHexString(c), 4) +": " + hb + " " + tb + "\n");
j = 0;
c += 16;
hb = "";
tb = "";
} else {
j++;
}
}
for (int i = hb.length(); i < 35; i++) {
hb = hb + " "; // pad to length of other lines
}
pb.append(hexPad(Integer.toHexString(c), 4) +": " + hb + " " + tb + "\n");
if ((k/nBytes) < .05) { // less than 5% binary?
System.out.println(sb.toString()); // print as text
} else {
System.out.println(pb.toString()); // print as hex dump
}
}
}
/* prepend 0's to a hex string
*/
private String hexPad(String a, int length)
{
for (int j = a.length(); j < length; j++) {
a = "0" + a;
}
return a;
}
}