How to kill open server sockets under windows7? - java

I wrote a simple server client socket program and when I recompile the server I get:
java.net.BindException: Address already in use: JVM_Bind
at java.net.DualStackPlainSocketImpl.bind0(Native Method)
at java.net.DualStackPlainSocketImpl.socketBind(Unknown Source)
at java.net.AbstractPlainSocketImpl.bind(Unknown Source)
at java.net.PlainSocketImpl.bind(Unknown Source)
at java.net.ServerSocket.bind(Unknown Source)
at java.net.ServerSocket.<init>(Unknown Source)
at java.net.ServerSocket.<init>(Unknown Source)
Therefore my question is how to kill the socket under windows 7? Is there a possible solution to kill it in eclipse?
I appreciate your answer!!

Kill the jvm this fixed the issue when I ran into it. Are you closing the socket in your code before you stop your simple server?

Like RGdev I assume that you still have a javaw process running in the background which keeps the connection open. But it could also be a different server program on your machine which hogs the port you want to use.
You can find out which processes are listening to which port with the netstat command in the cmd shell. The following parameters list (a) all connections including servers, (b) shows the executable which opened the connection and (n) suppresses the substitution of port numbers with service names for well-known ports.
netstat -abn

Here is my code for server side:
import java.io.*;
import java.net.*;
public class ServerSide {
public static void main(String[] args) {
try
{
ServerSocket myServerSocket = new ServerSocket(9999);
System.out.println("Server is waiting on host" + InetAddress.getLocalHost().getCanonicalHostName() + "port= "+ myServerSocket.getLocalPort());
Socket skt = myServerSocket.accept();
BufferedReader myInput = new BufferedReader(new InputStreamReader(skt.getInputStream()));
PrintStream myOutput = new PrintStream(skt.getOutputStream());
String buf = myInput.readLine();
System.out.println("Server readLine");
if(buf!=null)
{
System.out.println("Buf = " + buf);
myOutput.print("Got it?");
}
else
{
System.out.println("Nothing returned in server sidex`x ");
}
skt.close();
System.out.println("Server shutdown");
}
catch(IOException e)
{
e.printStackTrace();
System.out.println("Whooops");
}
}
}
As you can see for clean-up I've written:
skt.close();
But maybe this is not your problem, Maybe your problem is which I had 1 hour ago ;) I used to run a program but the result is not what I expected so I modify it and run it again but the port was busy or already in use! What I do on eclipse? Under the Console where you get the error, on the right side of the window there is red colour rectangle button! It say "Terminate". If you click on that your port will be free. By the way don't forget to check the console for both(Server/Client) sides.

You can also get this error message, when the process already terminated. TCP has a time wait state. This state is used to ensure that no TCP packets from an old connection can be delivered to a new process listening at the same port. Normally you should use the ServerSocket.setRuseAddress(true) to avoid this issue.

Related

Java - Program crashing after multiple uses of writeBytes

I've got a very simple multithreaded server that just prints back the client's input. The problem I'm having is that the client is crashing out after more than one use of outToServer.writeBytes().
My source code for the client is here:
public class Client {
public void run() throws Exception{
String sentence;
Socket clientSocket = new Socket("localhost", 25565);
BufferedReader inFromUser = new BufferedReader(new InputStreamReader(System.in));
DataOutputStream outToServer = new DataOutputStream(clientSocket.getOutputStream());
while (true){
sentence = inFromUser.readLine();
if(!sentence.equalsIgnoreCase("exit")){
outToServer.writeBytes(sentence + '\n');
} else {
break;
}
}
clientSocket.close();
}
}
I've done some research on the error and it might be my college network killing the connection, but it doesn't make much sense given that it allows the first connection.
Also, here's the error:
java.net.SocketException: Software caused connection abort: socket write error
at java.net.SocketOutputStream.socketWrite0(Native Method)
at java.net.SocketOutputStream.socketWrite(Unknown Source)
at java.net.SocketOutputStream.write(Unknown Source)
at java.io.DataOutputStream.writeBytes(Unknown Source)
at com.cs.Client.run(Client.java:21)
at com.cs.Main.main(Main.java:14)
At line 21 in Client.java is the line with writeBytes in it
Opening a connection is not like opening a door. A connection is a virtual concept and not a guaranteed path.
So when you open a connection, basically you have reconfigured some operating system managed area of memory to know that when you write data into a particular memory location, it needs to copy that data on the wire.
This means that opening a connection is not always a shared event (as in the remote machine might not fully guarantee a path to the program, or even might not be aware that a path to the remote program was requested).
So, in network programming, despite APIs that are worded to imply otherwise, you don't have a functional connection until you get the first response from the remote machine.
I'd see if you can fire up wireshark and see if you can capture the data prior to send, and I'd check any connection parameters, and attempt to verify connection reachability independently of the program.
The above procedure will help you quickly identify which network componet is at fault from the client's point of view; however, 90% of the time, it is something really trivial, like a software firewall blocking the desired port.
Also, you can use telnet to provide similar functionality, but connecting to a non-standard port.
telnet hostname 25565
Good luck, and your code seems pretty reasonable, I'd spend a little time making sure that you aren't focusing on the code when the environment might be at fault.

BindException: Address already in use even with unique port

I've asked this question yesterday and no one was able to figure out the problem I was having. So I was hoping of providing a more up to date code with the suggestions from yesterday added on. Basically, I've been trying to form a connection between a server and a client but whenever I executed the server then the client, I'd get this exception: Address already in use. The obvious answer would be to give it a new port, but even then I still get this error. I'm assuming it has something to do with my code somewhere going wrong. Can anyone spot it please? I have attached the server class and the client class.
This is the error I get:
Exception in thread "main" java.net.BindException: Address already in use
at java.net.PlainSocketImpl.socketBind(Native Method)
at java.net.AbstractPlainSocketImpl.bind(AbstractPlainSocketImpl.java:376)
at java.net.ServerSocket.bind(ServerSocket.java:376)
at java.net.ServerSocket.<init>(ServerSocket.java:237)
at java.net.ServerSocket.<init>(ServerSocket.java:128)
at MessageServer.main(MessageServer.java:16)
Server code:
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.Writer;
import java.net.ServerSocket;
import java.net.Socket;
public class MessageServer {
public static void main(String[] args) throws IOException {
try {
int port = 53705;
ServerSocket server = new ServerSocket(port);
while (true) {
System.out.println("Waiting for client...");
//server.setReuseAddress(true);
Socket client = server.accept();
System.out.println("Client from " + server.getInetAddress() + " connected.");
BufferedReader in = new BufferedReader(new InputStreamReader(client.getInputStream()));
String inputLine = in.readLine();
System.out.println("Client said: '"+inputLine+"'");
Writer count = new BufferedWriter(new OutputStreamWriter(client.getOutputStream()));
byte c [] = count.toString().getBytes();
count.flush();
count.close();
in.close();
}
} catch (IOException e) {
System.err.println(e);
}
}
}
Client code:
import java.net.*;
import java.io.*;
public class MessageSendClient {
public static void man(String args[]) throws IOException {
String servername = "localhost";
int port = 53705;
Socket server;
//server.setReuseAddress(true);
try {
server = new Socket (servername,port);
System.out.println("Connected to " + server.getInetAddress());
DataInputStream in = new DataInputStream(new BufferedInputStream(server.getInputStream()));
server.close();
byte c[] = new byte[100];
int num = in.read(c);
String count = new String(c);
System.out.println("Server said: " + count);
} catch (Exception e) { }
}
}
You're getting the error when the server program attempts to open up a socket on port 53705 for listening. The Address already in use message means just that, another process on your machine is already using port 53705. It could be that some daemon process has opened this same port by coincidence, or your web browser has opened this port and is still using it.
Most likely, though, is that you have another instance of your server program running somewhere in the background. Check all your terminal windows, or check your IDE for tabs containing the status of running programs.
By the way, "unique port" is a bit misleading, as port 53705 isn't "unique" in any way, it just happens to be a port number you (or somebody) picked that you hope isn't already in use. To get a truly unique port, use new ServerSocket(0) which will ask the system to allocate an unused port. To find out which port was assigned, use serverSocket.getLocalPort(). You might print it out, and then pass it to the client program as a command-line option.
I think you are running into a plattform and java liberary specific issue.
Please provide additional infos about your os plattform (x86/x64) and which version of jdk from which vendor are you using?
According to this Link
http://www.oracle.com/technetwork/java/javase/7u51-relnotes-2085002.html
Above Oracle JDK 7u51: The default socket permissions assigned to all code including untrusted code have been changed. You can only bind sockets to the ephemeral port range on each system.
Port 53705 should be a save ephemeral port.
But still use
netstat -an | grep 53705
to double check if the port is used in linux and use netstat or tcpview for windows.
You can use
less /proc/sys/net/ipv4/ip_local_port_range
for linux to check your ephemeral port range for linux and find
HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters
in windows to get determine your ephemeral port range. More about ephemeral range in windows can be found in how to change/view ephemeral port range in windows machines
I can confirm your server code and client without the "man" -> "main" typo is running under Opensuse 12.3 with
Java version "1.7.0_51"
OpenJDK Runtime Environment (IcedTea 2.4.4) (suse-8.32.5-i386)
OpenJDK Client VM (build 24.45-b08, mixed mode)
jvm is running by an non admin user with groups: www,dialout,video,shadow,users
I tested your code and it works correctly (meaning: I can connect to the server, didn't test the rest). Just pay attention to the main method in MessageSendClient, there's a typo ("man" instead of "main") and the correct signature is:
public static void main(String[] args)
not
public static void main(String args[]) // Still compatible but not recommended (C-like syntax)
Make sure the listening port is free by executing (replace YOUR_PORT with the number)
netstat -tulpn | grep :YOUR_PORT
because that's the reason why you get that exception. If you're on Windows you might just run
netstat -an
and search for the port.

Differences on Java Sockets between Windows and Linux - How to handle them?

I am having a lot of trouble in understanding the differences about how Java handles Sockets on Windows and Linux - Particularly when one of the sides (Client or Server) closes the connection abruptly.
I have written the following very simple Server and Client classes to keep my point as simple, objective and as easy for you to understand as possible:
SimpleClient.java:
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.net.Socket;
public class SimpleClient {
public static void main(String args[]) {
try {
Socket client_socket = new Socket("127.0.0.1", 9009);
// Used to read from a terminal input:
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
// Used for client/server communication:
BufferedReader in = new BufferedReader(new InputStreamReader(client_socket.getInputStream()));
BufferedWriter out = new BufferedWriter(new OutputStreamWriter(client_socket.getOutputStream()));
while(true) {
System.out.print("Command: ");
String msg = br.readLine();
// Send:
out.write(msg);
out.newLine();
out.flush();
// Receive:
int ifirst_char;
char first_char;
if((ifirst_char = in.read()) == -1) { // Server Closed
System.out.println("Server was closed on the other side.");
break;
}
first_char = (char) ifirst_char;
msg = String.valueOf(first_char);
msg += in.readLine();
// Shows the message received from the server on the screen:
System.out.println(msg);
}
}
catch(Exception e) {
e.printStackTrace();
}
}
}
SimpleServer.java:
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.net.ServerSocket;
import java.net.Socket;
public class SimpleServer {
public static void main(String args[]) {
try {
ServerSocket server_socket = new ServerSocket(9009);
Socket client_socket = server_socket.accept();
while(true) {
BufferedReader in = new BufferedReader(new InputStreamReader(client_socket.getInputStream()));
BufferedWriter out = new BufferedWriter(new OutputStreamWriter(client_socket.getOutputStream()));
// Receive:
int ifirst_char;
char first_char;
if((ifirst_char = in.read()) == -1) { // Client Closed
System.out.println("Client was closed on the other side.");
break;
}
first_char = (char) ifirst_char;
String msg = msg = String.valueOf(first_char);
msg += in.readLine();
msg = "Server Received: " + msg;
// Send:
out.write(msg);
out.newLine();
out.flush();
}
}
catch(Exception e) {
e.printStackTrace();
}
}
}
Of course I could implement a code for properly shutting down the client or the server, but the objective, as I said, is to simulate an abrupt shutdown on either side, where no "disconnection code" could be sent or received. That's why I created these 2 very simple classes.
On Linux, it runs pretty well:
$ java SimpleClient
Command: echo
Server Received: echo
Command: test
Server Received: test
Command: (server now was closed on the other side)
Server was closed on the other side.
$
On Windows, however:
C:\simplesocket>java SimpleClient
Command: echo
Server Received: echo
Command: test
Server Received: test
Command: (server now was closed on the other side)
java.net.SocketException: Connection reset by peer: socket write error
at java.net.SocketOutputStream.socketWrite0(Native Method)
at java.net.SocketOutputStream.socketWrite(Unknown Source)
at java.net.SocketOutputStream.write(Unknown Source)
at sun.nio.cs.StreamEncoder.writeBytes(Unknown Source)
at sun.nio.cs.StreamEncoder.implFlushBuffer(Unknown Source)
at sun.nio.cs.StreamEncoder.implFlush(Unknown Source)
at sun.nio.cs.StreamEncoder.flush(Unknown Source)
at java.io.OutputStreamWriter.flush(Unknown Source)
at java.io.BufferedWriter.flush(Unknown Source)
at SimpleClient.main(SimpleClient.java:32)
Let's say I try to ignore this Exception by modifying the following lines on my SimpleClient.java:
// Send:
try {
out.write(msg);
out.newLine();
out.flush();
}
catch(Exception e) {}
Another Exception is thrown:
C:\simplesocket>java SimpleClient
Command: echo
Server Received: echo
Command: test
Server Received: test
Command: (server now was closed on the other side)
java.net.SocketException: Connection reset
at java.net.SocketInputStream.read(Unknown Source)
at java.net.SocketInputStream.read(Unknown Source)
at sun.nio.cs.StreamDecoder.readBytes(Unknown Source)
at sun.nio.cs.StreamDecoder.implRead(Unknown Source)
at sun.nio.cs.StreamDecoder.read(Unknown Source)
at java.io.InputStreamReader.read(Unknown Source)
at java.io.BufferedReader.fill(Unknown Source)
at java.io.BufferedReader.read(Unknown Source)
at SimpleClient.main(SimpleClient.java:42)
I don't know if the corresponding lines on the code will be the ones pointed out on these Exceptions, but the first one is thrown on out.flush() and the second one on in.read().
So basically, as you can see on Linux, even after abruptly closing the server:
1. It doesn't throw an Exception when I try to send the data.
2. And more importantly, when I try to receive it, the first char is "-1" and received correctly.
On Windows, it throws Exceptions both when sending and more importantly on receiving - when calling the read() method - I cannot get the "end of the stream" (-1) code.
Which leads to some questions:
1. Why is there such a big difference on Windows x Linux? Why on Linux these Exceptions are not thrown while on Windows they are?
2. Shouldn't Java, with all its cross-platform qualities, try to minimize the differences on running in both the Systems? (by the way I'm using JDK 7 on both)
3. Is there a way to change the code for an abrupt shutdown and get it to work more "Linux-like" on Windows, without throwing all these Exceptions and getting the -1 on my in.read()??
4. If not, any external API recommended?
I've tried to search the web for hours on this specific topic but without success.
I have also tried many solutions like calling methods like isConnected(), isBound(), isClosed(), etc. in the client_socket on the client side without success. They always say that there is an active connection and no problem with it, even after shutting down the server.Hopefully someone would take the time to answer at least one of these questions.
You have my most sincere thanks in advance for any answers.
Your code doesn't do any close, so I'll assume you actually mean that one endpoint process is stopped aka killed.
Unix socket sd's are "just" fd's, and when a Unix process ends without closing an fd, including the case where a JVM stops
and you hadn't called close (or shutdown-WR), the fd is closed by the OS, which for TCP socket does (at least tries)
the normal aka graceful close: FIN/ACK exchange with FIN-WAITs and TIME-WAIT. The only way I know to make Unix socket
do graceless close at the TCP level (RST) is to set linger to 0 before closing (either explicitly or by exiting).
It is also possible and not uncommon for a middlebox to forcibly break your connection with RST; for example I've seen firewalls
that RST you after 15min inactivity. I've also more rarely seen middleboxes that fake FIN, or that try to but do it wrong.
Windows sockets (WinSock) are a different API than files. If a Windows process ends without calling closesocket (similar to
but separate from close) or at least shutdown-WR, Winsock does RST. To get graceful close (FIN) on Windows you (via JVM)
must call one of those. JVM presumably could track java.net.Sockets (but not any in JNI) and do this for you on JVM exit, but
it doesn't; you could request an enhancement. Even that might not work if you externally kill it with TaskMgr or similar, and
might not work right if you hit a JVM fault: the JVM tries to catch faults and give a minidump, which would be a place to try
to cleanup sockets, but if there was a JVM bug it might fail again -- and IME most JVM faults are due to JVM bugs.
If it's enough to handle code bugs (leaks) and signals but not JVM bugs and failures, you could just subclass Socket
so that if forces (graceful) close on .finalize and on exit using Runtime.addShutdownHook, and use that instead.
In either Unix or Windows sockets, received FIN is treated as end-of-file, like any other file for example a disk file.
Received RST is returned as an error [WSA]ECONNRESET to JVM, which raises an exception. It wouldn't be good to hide this
difference, because for apps other than yours it can be significant -- enough so that some protocols have had to be changed
to prevent fake-FIN being a security vulnerability notably SSLv2 and HTTP/0.9.
If you also consider cases where the peer system fails (not just the JVM), or certain parts of the network fail,
or your network interface fails, the Exceptions you can get are quite a bit more varied. IMHO don't try to handle those,
just report what you see and let the sysadmins and netadmins sort it out. I've seen cases where a programmer got Exception X
due to problem P in laboratory conditions and coded for that, but in the real world exception X happened for very different
reasons and the "helpful" handling actually made it harder to solve the problem.
Asides: the server should create the BufferedReader before not inside the while(true)do-a-line loop;
if you ever get/want a client that sends more than one line at a time, the code shown will lose data.
You don't need that hair for if first_char==-1 else convert to String; just use in.readLine, it returns null in exactly
the same case where initial in.read returns -1, which for (TCP) Socket is when FIN is received.
Conversely the client readLine from System.in should be checked; if someone types ^Z or ^D or whatever you'll get NPE.

Troubleshoot connecting client to server in java

I have been having this problem for some time now and although my efforts and my friends help I can't seem to get past this problem .
My problem is I am trying to establish a connection between client and a server using sockets its very common actually, but for some reason client can't seem to connect to the server don't know why , here is my attempts to solve the problem
1- I used http://portforward.com/ to open the used port on my router which is of type "zhone"
2- I changed the port multiple times and every time I used PFPortChecker to see if my port is open
my code is fairly simple it opens server and when client connects to it , the server sends the date and time
my server code looks like this
public class DateServer {
/** Runs the server. */
public static void main(String[] args) throws IOException {
ServerSocket listener = new ServerSocket(6780);
try {
while (true) {
Socket socket = listener.accept();
try {
PrintWriter out = new PrintWriter(socket.getOutputStream(), true);
out.println(new Date().toString());
} finally {
socket.close();
}
}
} finally {
listener.close();
}
}
}
my client code looks like this
public class DateClient {
/** Runs the client as an application. First it displays a dialog box asking for the IP address or hostname of a host running the date server, then connects to it and displays the date that it serves. */
public static void main(String[] args) throws IOException {
//I used my serverAddress is my external ip address
Socket s = new Socket(serverAddress, 6780);
BufferedReader input = new BufferedReader(new InputStreamReader(s.getInputStream()));
String answer = input.readLine();
JOptionPane.showMessageDialog(null, answer);
System.exit(0);
}
}
even though I continued my attempts
3- I closed my firewall just in case
4- I added connection time out in my server socket
with all my attempts I always get this error
Exception in thread "main" java.net.ConnectException: Connection timed out: connect
at java.net.DualStackPlainSocketImpl.connect0(Native Method)
at java.net.DualStackPlainSocketImpl.socketConnect(Unknown Source)
at java.net.AbstractPlainSocketImpl.doConnect(Unknown Source)
at java.net.AbstractPlainSocketImpl.connectToAddress(Unknown Source)
at java.net.AbstractPlainSocketImpl.connect(Unknown Source)
at java.net.PlainSocketImpl.connect(Unknown Source)
at java.net.SocksSocketImpl.connect(Unknown Source)
at java.net.Socket.connect(Unknown Source)
at java.net.Socket.connect(Unknown Source)
at java.net.Socket.<init>(Unknown Source)
at java.net.Socket.<init>(Unknown Source)
at DateClient.main(DateClient.java:13)
note that DateClient.java:13 is this line Socket s = new Socket(serverAddress, 6780);
please help me with this problem , thanks in advance
I tried running your code. First, localhost (127.0.0.1) could solve your problem. On the other side, I changed the ports and IP to my own, and it just works fine (even my external IP). So probably there is something wrong with your port/IP.
In case it works using localhost, your IP was not the right one, or something on your computer is blocking external connections.
Your client code should look like this, for some reason new Socket(String host, int port) wont work.
public class DateClient {
/** Runs the client as an application. First it displays a dialog box asking for the IP address or hostname of a host running the date server, then connects to it and displays the date that it serves. */
public static void main(String[] args) throws IOException {
//I used my serverAddress is my external ip address
InetAddress serverAddress = InetAddress.getByName(String host);
Socket s = new Socket(serverAddress, 6780);
BufferedReader input = new BufferedReader(new InputStreamReader(s.getInputStream()));
String answer = input.readLine();
JOptionPane.showMessageDialog(null, answer);
System.exit(0);
}
}
If it doesn't work using localhost, your port is not forwarded correctly. Try to log in to your router and forward the port from there.
And indeed, like #Audrius Meškauskas said, you might want to close your PrintWriter on your server, right before closing your ServerSockect listener.
Close the PrintWriter on the server side
Be sure you use localhost (try 127.0.0.1) as the server address. Depending on how are you connecting the Internet, the external Internet address (as shown by various "get my ip" tools on the web) may be different from the actual address to that your network interface is configured and not work from the same machine. More here.

Android check if remote server is online

I am new to Android programming and I have been facing problems that didn't exist in native Java. When I run this code in my computer, it runs correctly. But, when I run it in my device.I get nothing, I even tried to post the message to UI and there's no logcat for this. I am not sure what is wrong.
try{
Socket socket = new Socket(serverAddr, SERVER_PORT);
Log.i("TAG","Socket connected");
}catch(IOException e){
Log.i("TAG","Socket not connected");
}
Update 1: I just changed the code..nothing much and realized that after 2 minutes or so it does what it was supposed to do?? Is is anything to do with keep alive flags? Or is there anyway that I can run the code just for a second or two and stop it. Please understand that the code below the socket creation line executes only after 2 minutes if the server is dead. Here below is my code:
try{
InetAddress serverAddr = InetAddress.getByName(serverIP);
//Line below executes with no delay
postToUI("Trying to connect to standalone server" + "\n\n");
socket = new Socket(serverAddr, SERVER_PORT);
//Line below executes after 2 minutes
postToUI("Successfully connected to standalone server" + "\n\n");
}catch(ConnectException e){
postToUI("Socket not connected");
}catch(IOException e){
postToUI("Socket not connected");
}
I have done very few Andrioid development so don't bite me smiley.
Possible reasons why the host might not communicate with the client
Host has firewall which might be closing the connection (unlikely)
Host might have unexpectly shutdown e.g power failure (unlikely)
Host might not properly port forwared (possibly)
Your andriod app doesn't have the proper manifest that allows the use of sockets.
Your andrioid device you are testing on might have its internet disabled which can enabled easily.
Host's address could have changed if it is dynamic.
For logcat, I think that logcat only displays log messages for the main thread. But I am unsure.

Categories