I no sabe lo que quiere lograr en el final, pero trabajando con UDP no es tan fácil ... la razón principal está en la descripción del objeto DatagramPacket:
paquetes de datagramas se utilizan para implementar un servicio de entrega de paquetes sin conexión servicio. Cada mensaje se enruta desde una máquina a otra basándose únicamente en en la información contenida en ese paquete . Los paquetes múltiples enviados desde una máquina a otra pueden enrutarse de manera diferente, y pueden llegar en cualquier orden . La entrega del paquete no está garantizada .
Un buen tutorial cuando se trabaja con UDP es http://download.oracle.com/javase/tutorial/networking/datagrams/clientServer.html
Acerca de su bloqueo:
recibe un paquete de datagramas desde este conector . Cuando este método retorna, el buffer del DatagramPacket se rellena con los datos recibidos. El paquete de datagramas también contiene la dirección IP del remitente, y el número de puerto en la máquina del remitente.
Este método bloquea hasta que se reciba un datagrama . El campo de longitud del objeto de paquete de datagrama contiene la longitud del mensaje recibido. Si el mensaje es más largo que la longitud del paquete , el mensaje se trunca.
casi no lo pruebo, pero estoy bastante seguro de que - basándose en la descripción - que la función datagramsocket.reseive bloqueará hasta que se llena el paquete (en su caso hasta que se reciban 100000 bytes).
Le sugiero que comience con un datagrampacket con una longitud fija conocida, donde transmite el tamaño de la carga real.Algo así como:
public static void main(String[] args) {
ClientModel c1 = new ClientModel();
c1.data = 123;
c1.name = "test";
try {
ByteArrayOutputStream baos = new ByteArrayOutputStream();
ObjectOutputStream oos = new ObjectOutputStream(baos);
oos.writeObject(c1);
oos.flush();
// get the byte array of the object
byte[] Buf= baos.toByteArray();
int number = Buf.length;;
byte[] data = new byte[4];
// int -> byte[]
for (int i = 0; i < 4; ++i) {
int shift = i << 3; // i * 8
data[3-i] = (byte)((number & (0xff << shift)) >>> shift);
}
DatagramSocket socket = new DatagramSocket(1233);
InetAddress client = InetAddress.getByName("localhost");
DatagramPacket packet = new DatagramPacket(data, 4, client, 1234);
socket.send(packet);
// now send the payload
packet = new DatagramPacket(Buf, Buf.length, client, 1234);
socket.send(packet);
System.out.println("DONE SENDING");
} catch(Exception e) {
e.printStackTrace();
}
}
Por otro lado Ahora ya sabe sus tamaños:
public static void main(String[] args) {
try {
DatagramSocket socket = new DatagramSocket(1234);
byte[] data = new byte[4];
DatagramPacket packet = new DatagramPacket(data, data.length);
socket.receive(packet);
int len = 0;
// byte[] -> int
for (int i = 0; i < 4; ++i) {
len |= (data[3-i] & 0xff) << (i << 3);
}
// now we know the length of the payload
byte[] buffer = new byte[len];
packet = new DatagramPacket(buffer, buffer.length);
socket.receive(packet);
ByteArrayInputStream baos = new ByteArrayInputStream(buffer);
ObjectInputStream oos = new ObjectInputStream(baos);
ClientModel c1 = (ClientModel)oos.readObject();
c1.print();
} catch(Exception e) {
e.printStackTrace();
}
}
El clas CientModel sI utilizado:
public class ClientModel implements Serializable{
private static final long serialVersionUID = -4507489610617393544L;
String name = "";
int data = 1;
void print() {
System.out.println(data +": " + name);
}
}
He probado el código y funciona muy bien. Espero que ayude (obtuve el byte-to-int y alrededor de http://www.tutorials.de/java/228129-konvertierung-von-integer-byte-array.html)
Editar: Como se dice en los comentarios, a menudo es una muy mala idea usar UDP, principalmente, porque no sabes si tus paquetes se reciben en el orden correcto, o incluso en absoluto. UDP NO garantiza eso. No hice demasiada programación udp, pero la única parte en la que puede confiar (si lo entendí correctamente) es que si obtiene un paquete y encaja dentro del datagrama (65.527 bytes - vea https://en.wikipedia.org/wiki/User_Datagram_Protocol) contendrá la totalidad cosa. Entonces, si no le importa el orden en que aparece el mensaje y su objeto encaja en el datagrama, debería estar bien.
Edit2: En cuanto al código: no lo use como está. es solo un ejemplo, ind UDP solo debería tener un tipo de paquete, y esto con un tamaño conocido. de esa manera no necesitas enviar el "tamaño". Si usa el código como se muestra arriba, y se descarta un paquete, el siguiente paquete tendrá el tamaño incorrecto (es decir, si se descarta el primer paquete, de repente está verificando los primeros bytes de la carga útil para obtener el tamaño).
quizás necesite vaciar el búfer ... – ultrajohn