Is there a way to check see if a packet is null or not?
Me and my friend have this game.. and we send the people objects back and forth and it works fine and dandy.... except for sometimes after awhile a random nullpointer exception will just come out of no where when it shouldn't. We've been through are code thousands of times and can't find anything wrong with why it'd cause a nullPointer error.. so we thought that maybe it was dropping a packet and so when we'd try to set the object to something the packet isn't there so it'd cause the nullPointer error.... any ideas?and also is there a way to check and see if the packet is null or not in the client code or what not? I'm using multicast sockets so its p2p basically..... so is there a way to see if an incoming packet is null or not? because if it is null then I can make it not set the object and all should be fine and dandy right?
Java gives you stack traces which name the actual line where the null pointer was encountered. Finding where it happens should be no problem at all.There is no such thing as a null packet.
but we have looked at the line where it says the error.. made changes.. edited it... and each time we fix it. and points to a different place and what not. So there has to be One problem that will stop the error. And the error has no reason to happen as for it works for awhile then all a sudden it happens.. and the stack trace points to the first time we use the object that was set by the client... so I can only assume that when it gets the object and sets the object it somehow randomly ends up null.. ?So if it drops a packet and it tries to receive it, it doesn't come up as null? then if that isn't the case, explain what may be the error?
All that means is that you haven't found the problem yet, just a few places where it shows up as a symptom. I suggest a few more null pointer checks in your application. Also have a think about concurrency.
Your question about receiving null packets doesn't make any sense. If the packet is dropped it is dropped. It ceases to exist. The receive statement only returns datagrams that have been received. How can it know about packets that have been dropped? so how can it know to return null?
ok, so I'm going to go make a lot more tests to figure out the problem, hopefully it'll work out alright.. Idk..
but in my mind.. I was thinking that (idk why I was, I've never thought this before) it was expecting that packet to come and since it didn't come it would freak out... which now that I think about it makes some sense.. but yet none at all...
so now it remains, why does it take awhile for the error to happen? why not off the bat? the only thing we ever do is let are little men move around the screen and thats it... and after awhile the error pops up... so it confuses me. cause the only variables changing are the x, y of the peoples, the bullets that they fire, and the decrease in health as they get hit... er idk..
ok, so I've narrowed the error down to this.. so wth is going on?
.Exception: java.io.EOFException
java.io.EOFException
at java.io.ObjectInputStream$PeekInputStream.readFully(ObjectInputStream
.java:2232)
at java.io.ObjectInputStream$BlockDataInputStream.readInt(ObjectInputStr
eam.java:2722)
at java.io.ObjectInputStream.readHandle(ObjectInputStream.java:1398)
at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1279)
at java.io.ObjectInputStream.defaultReadFields(ObjectInputStream.java:19
12)
at java.io.ObjectInputStream.readSerialData(ObjectInputStream.java:1836)
at java.io.ObjectInputStream.readOrdinaryObject(ObjectInputStream.java:1
713)
at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1299)
at java.io.ObjectInputStream.readArray(ObjectInputStream.java:1628)
at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1293)
at java.io.ObjectInputStream.readObject(ObjectInputStream.java:339)
at PacketClient.recvObjFrom(PacketClient.java:54)
at PacketClient.main(PacketClient.java:28)
Short datagram.
As UDP can't do that, probably the data being serialized overflowed the packet at the sender and wasn't detected.
Your sending code should look something like this:
ByteArrayOutputStream baos = new ByteArrayOutputStream();
ObjectOutputStream oos = new ObjectOutputStream(baos);
oos.writeObject(object);
oos.close();
DatagramPacket packet = new DatagramPacket(baos.toByteArray(), baos.size());
socket.send(packet);
this is my sending code, which is the way its been since its been giving me this error
ByteArrayOutputStream byteStream = new
ByteArrayOutputStream(4096);
ObjectOutputStream os = new ObjectOutputStream(new
BufferedOutputStream(byteStream));
os.flush();
os.writeObject(o);
os.flush();
//retrieves byte array
byte[] sendBuf = byteStream.toByteArray();
DatagramPacket packet = new DatagramPacket(
sendBuf, sendBuf.length, address, desPort);
socket.send(packet);
os.close();
any ideas? I read somewhere, that you may receive the packet, but it may not always be the correct length.. maybe that is causing the error?
If you receive the datagram at all it will arrive complete and intact. This is a primary property of UDP and it is guaranteed by the RFC. However if your DatagramPacket is too short for the incoming datagram the excess is silently truncated. This can happen during receive if you reuse the same DatagramPacket: it keeps shrinking to the size of the smallest packet received so far, and this would account for your EOFException. The cure is to either use a new DGP or at least reset its size before every receive.
would it be possible to get the correct length and check and see if a packet is that length, and if its not then just do away with it?
or you can explain about using a new DGP (I don't even know what that stands for lol) and if I reset the size of the packet, would there be information thats lost since its smaller than what it should be? so when i set it would it come up null or no?
DGP = DatagramPacket.
You need to decide what the maximum packet size is and use a buffer one bigger. Then if you get anything that size it has been truncated. If you're reusing the same packet for every receive you need to reset its length, because the receive alters the length to the actual length received so it will slowly shrink. Something like this:
static final int MAX_PACKET_SIZE = xxx; // you decide
// ...
byte[] buffer = new byte[MAX_PACKET_SIZE+1];
DatagramPacket packet = new DatagramPacket(buffer, buffer.length);
// ...
// now for every receive ...
packet.setLength(buffer.length); // restore the length
datagramSocket.receive(packet);
if (packet.length() == buffer.length)
{
// you have just received a truncated packet, discard it
}
else
{
// process the packet
ByteArrayInputStream bais = new ByteArrayInputStream(packet.getData(), packet.getOffset(), packet.getLength());
ObjectInputStream ois = new ObjectInputStream(bais);
Object object = ois.readObject();
// etc
}
ok, well the error is gone now... but now after awhile it like... just stops working? but it is still sending stuff back and forth I think.... cause its not causing any errors.. it just plain stops working.. lol that also might be that since I'm testing the entire thing on my comp it might be overloaded with info since both clients are running on my computer... so tomorrow in the school lab I'll try it.. but for now, could it be that its just sending to much information to fast? if that might be the case, is there a way to slow it down just a wee bit so you can't tell the difference?
Increase the DatagramSocket.setReceiveBufferSize() to about 63k, and put a little sleep in between all the sends.
well it works now, except I don't check the length of the packet and it works.. it was jsut I needed to up the size. Thanks!
hey, one more question, and I don't feel like making a new thread.. so the question is, whats the easiest way to send a string using mulitcast sockets?
new DataOutputStream(byteArrayOutputStream).writeUTF(string);string = new DataInputStream(byteArrayInputStream).readUTF()
thanks a lot... You've been a big help.. and I'm sure I'll have more questions in the near future.. oh speaking of questions in the near future.... this might be out of forum section, but how would I make an input box like.... like the JOptionPane but with only that space you type in, any ideas on how to create one of those? would be a big help thanks!