How work with socket and hostnames in Java? - sockets

Recently I had to change my router, it was an Belking for one D-Link, my program worked it with my Belkin router but not now with the D-Link router.
Here is my program:
The client:
package brainset.socket;
import java.io.IOException;
import java.io.PrintStream;
import java.net.Socket;
/**
*
* #author Valter
*/
public class Client {
public static void main(String[] args) {
Socket s = null;
PrintStream ps = null;
try{
s = new Socket("valterhenrique.dyndns.info", 40000);
ps = new PrintStream(s.getOutputStream());
ps.println("lamp");
}catch(IOException e){
System.out.println("Some problem happens.");
e.printStackTrace();
}finally{
try{
s.close();
}catch(IOException e){}
}
}
}
And here's my server:
package brainset.socket;
// imports
public class Server {
private Supervisory supervisory;
public Server(Supervisory supervisory) {
this.supervisory = supervisory;
}
public void start() {
ThreadServer ts = new ThreadServer();
Thread t = new Thread(ts);
t.start();
}
class ThreadServer extends Thread {
public void run() {
ServerSocket ss = null;
Socket socket = null;
BufferedReader br = null;
try {
ss = new ServerSocket(40000);
socket = ss.accept();
br = new BufferedReader(new InputStreamReader(socket.getInputStream()));
String message;
while ((message = br.readLine()) != null) {
System.out.println("message:" + message);
try {
if (message.equals("lamp")) {
supervisory.active();
supervisory.switchLamp();
} else if (message.contains("airConditioning")) {
String airConditioning[] = message.split(":");
// temperature[0] = 'temperature'
// temperature[1] = temperature value
supervisory.active();
supervisory.changeTemperature(Float.parseFloat(airConditioning[1]));
}
} catch (Exception ex) {
Logger.getLogger(Server.class.getName()).log(Level.SEVERE, null, ex);
}
socket = ss.accept();
br = new BufferedReader(new InputStreamReader(socket.getInputStream()));
}
} catch (IOException ioe) {
ioe.printStackTrace();
} finally {
try {
socket.close();
ss.close();
} catch (IOException ioe) {
ioe.printStackTrace();
}
}
}
}
public static void main (String args[]){
Server s = new Server(new Supervisory("192.168.1.149", "192.168.1.255", 101));
s.start();
}
}
I already opened a port in my new router and update the hostname in DynDns.org but still keeping launching an exception:
java.net.ConnectException: Connection refused: connect
at java.net.PlainSocketImpl.socketConnect(Native Method)
at java.net.PlainSocketImpl.doConnect(PlainSocketImpl.java:351)
at java.net.PlainSocketImpl.connectToAddress(PlainSocketImpl.java:213)
at java.net.PlainSocketImpl.connect(PlainSocketImpl.java:200)
at java.net.SocksSocketImpl.connect(SocksSocketImpl.java:366)
at java.net.Socket.connect(Socket.java:529)
at java.net.Socket.connect(Socket.java:478)
at java.net.Socket.<init>(Socket.java:375)
at java.net.Socket.<init>(Socket.java:189)
at brainset.socket.Client.main(Client.java:28)
If I change the hostname 'valterhenrique.dyndns.info' it works, but this is not what I want, I want to works with the hostname because I'm in a dynamic ip network.
Any idea ?

I think you need permit external access to your network. In the Port Forwarding page (in the router's configuration page) add a entry that forwards the external requests to a specific address in your LAN.

Related

eofexception on the server side of sslsocket while there is data for sure

I have this dummy program:
package com.company;
import javax.net.ssl.*;
import java.io.*;
import java.net.InetSocketAddress;
import java.net.ServerSocket;
import java.net.Socket;
import java.net.SocketTimeoutException;
import java.security.*;
import java.security.cert.CertificateException;
class MyClass implements Serializable
{
private int i,j;
public MyClass(int i, int j)
{
this.i = i;
this.j = j;
}
public int getJ()
{
return j;
}
public void setJ(int j)
{
this.j = j;
}
public int getI()
{
return i;
}
public void setI(int i)
{
this.i = i;
}
}
class SSLContextHelper
{
static SSLContext createSSLContext(String path) throws KeyStoreException, UnrecoverableKeyException, NoSuchAlgorithmException, IOException, KeyManagementException, CertificateException
{
KeyStore keyStore = KeyStore.getInstance("PKCS12");
keyStore.load(new FileInputStream(path),"DSL2137976".toCharArray());
// Create key manager
KeyManagerFactory keyManagerFactory = KeyManagerFactory.getInstance("SunX509");
keyManagerFactory.init(keyStore, "DSL2137976".toCharArray());
KeyManager[] km = keyManagerFactory.getKeyManagers();
// Create trust manager
TrustManagerFactory trustManagerFactory = TrustManagerFactory.getInstance("SunX509");
trustManagerFactory.init(keyStore);
TrustManager[] tm = trustManagerFactory.getTrustManagers();
// Initialize SSLContext
SSLContext sslContext = SSLContext.getInstance("TLSv1.2");
sslContext.init(km, tm, new SecureRandom());
return sslContext;
}
}
class ServerThread extends Thread
{
ServerSocket server;
Socket client;
ObjectOutputStream out;
ObjectInputStream in;
boolean issecure;
SSLContext sslContext;
public ServerThread(int port, boolean issecure) throws IOException, UnrecoverableKeyException, CertificateException, NoSuchAlgorithmException, KeyStoreException, KeyManagementException
{
this.issecure=issecure;
client=null;
if(issecure)
{
sslContext = SSLContextHelper.createSSLContext("/usr/lib/jvm/java-8-openjdk/jre/lib/security/ssltest");
SSLServerSocketFactory sslServerSocketFactory = sslContext.getServerSocketFactory();
server = sslServerSocketFactory.createServerSocket(port);
server.setSoTimeout(200);
}
else
server=new ServerSocket(port);
}
#Override
public void run()
{
while (true)
{
try
{
if(client==null)
{
if (issecure)
{
SSLSocket clientssl = (SSLSocket) server.accept();
clientssl.setEnabledCipherSuites(clientssl.getSupportedCipherSuites());
clientssl.startHandshake();
client = clientssl;
}
else
client = server.accept();
in = new ObjectInputStream(client.getInputStream());
out = new ObjectOutputStream(client.getOutputStream());
client.setSoTimeout(200);
}
String[] req = in.readUTF().split("\n");
out.writeUTF("hello I'm the server");
out.flush();
req = in.readUTF().split("\n");
out.writeUTF("I mean I'll serve you");
out.flush();
}
catch (IOException e)
{
e.printStackTrace();
}
}
}
}
public class Main
{
public static void main(String... args) throws IOException, ClassNotFoundException, UnrecoverableKeyException, CertificateException, NoSuchAlgorithmException, KeyStoreException, KeyManagementException
{
ServerThread serverThread=new ServerThread(14200, true);
serverThread.setDaemon(true);
serverThread.start();
ServerThread mail=new ServerThread(14201, false);
mail.setDaemon(true);
mail.start();
try
{
Thread.sleep(5000);
}
catch (InterruptedException e)
{
e.printStackTrace();
}
SSLSocket client=(SSLSocket)SSLContextHelper.createSSLContext("/usr/lib/jvm/java-8-openjdk/jre/lib/security/ssltest").getSocketFactory().createSocket();
client.connect(new InetSocketAddress("localhost",14200),5000);
Socket mailclient = new Socket();
mailclient.connect(new InetSocketAddress("localhost", 14201), 5000);
client.startHandshake();
client.setSoTimeout(5000);
ObjectOutputStream out = new ObjectOutputStream(client.getOutputStream());
ObjectInputStream in = new ObjectInputStream(client.getInputStream());
out.writeUTF("hello\nhow are you");
out.flush();
System.out.println(in.readUTF());
out.writeUTF("what\nI didn't understand");
out.flush();
System.out.println(in.readUTF());
int i=0;
while (i<=1)
{
try
{
try
{
Thread.sleep(10000);
}
catch (InterruptedException e)
{
e.printStackTrace();
}
out.writeUTF("hello\nhow are you");
out.flush();
System.out.println(in.readUTF());
out.writeUTF("what\nI didn't understand");
out.flush();
System.out.println(in.readUTF());
i++;
}
catch (SocketTimeoutException ignored)
{
}
}
}
}
It's just a simulation of a real program I have, the Thread.sleep on the client side is a simulation of a user doing some interaction with the system before clicking a button(the first sleep is the simulation of the user putting the sign in information, the second sleep is the user opening tab,clicking link,answers dialogs,etc).
Unfortunately I'm getting EOFException in the server side right after the server.accept succeed(that is when the client connects).
I know that this exception occurs when there is no data to get but this happens even after these two lines(the first ones before the while loop) on the client side:
out.writeUTF("hello\nhow are you");
out.flush();
after these two lines the client waits 5 seconds(the timeout I put) , during this 5 seconds the server keeps on its EOFException, when the timeout finishes the client gets SocketTimeoutException and the program exits.
The original program is getting the same EOFException on the server side, it began when I moved to SSLSockets.
So what's the issue here ?
Edit
I have found that when I remove the timeout(the Read timeout not the Accept timeout) it works perfectly.
Playing with the timeout, setting it to different value gives me strange NullPointerExceptions(that in is null !!!!!!!!!!).
I need the timeout because in my real program the server won't wait the client forever, it has other clients to serve as well .
Why timeout causes this ?

socket connection works well in wireless toolkit but no in my nokia phone

wireless toolkit code
//j2me code for client mobile
public class TCPConnectSend extends MIDlet implements CommandListener {
Display display;
public TCPConnectSend0 () {
frm = new Form ("TCPConnectSend0");
sendCmd = new Command("Send",Command.SCREEN, 1);
frm.addCommand(sendCmd);
frm.setCommandListener(this);
text = new TextField("text:","",40,TextField.ANY);
frm.append(text);
}
public void startApp() {
if(display==null) {
display = Display.getDisplay (this);
}
display.setCurrent(frm);
try {
conn=(SocketConnection)Connector.open("socket://|ip-address|:80");//socket connection to the server
outs=conn.openOutputStream();
} catch(IOException e) { }
}
public void pauseApp() { }
public void destroyApp(boolean unconditional) { }
public void commandAction(Command c, Displayable s) {
if(c==sendCmd) {
try {
outs.write((text.getString()+"\n").getBytes());
} catch(IOException e) {}
} else { }
}
}
server code
//this receives the socket request from client
class TCPServer
{
public static void main(String argv[]) throws Exception
{
try {
ServerSocket server = new ServerSocket(80);
System.out.println("ip address : "+InetAddress.getLocalHost());
System.out.println("waiting for connection");
Socket s1 = server.accept();
System.out.println("connection established");
BufferedReader br = new BufferedReader(new
InputStreamReader(s1.getInputStream()));
while (true) {
String str1 = br.readLine();
System.out.println("client says :" +str1);
if (str1.equals("quit"))
break;
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
//after running this code i m getting a java security exception in my nokia phone any other port no is no responding in the nokia phone
the problem happened because Nokia was blocking the 80 port no for some of its system application so changing of port no along with public ip address did the trick
You should add the public IP of the server in your client code ex.
(SocketConnection)Connection.open( "socket://105.225.251.58" + ":" + "port" );
Note that to use privileged ports like 80, 443, 8080 and generally anything below 1000, you need a code signing certificate(e.g from Thawte) for a real phone.
Otherwise, still to higher un-privileged ports likes 8000 etc

How can I test, whether my deployed background server application on AWS beanstalk gets messages through a socketstream with an android mobile client?

The overall topic is actually like a Chat Application sending a simple string message to an aws server, which uses the message to make calculations server-side and sending a simple string message as a solution back to the client.
Server: I have written a Server Class and deployed it through eclipse to aws beanstalk. (see code Server)
Client: My android device creates a socket, establishes a successful connection to my aws beanstalk ip and 8080 port, while iterating through an endless while loop in a thread listening to incoming messages from the server. (see code Client and ClientThread)
Problem: My problem is that I don't know how to check whether the server receives the connection request and messages from the client. How do I make sure, that code on aws beanstalk actually runs in background continuously listening for incoming connections? I have deployed the code, does aws beanstalk automatically start the main method of the Server Class and runs it infinitely?
Here's the server code:
import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
public class Server {
public static void main(String args[]) {
ServerSocket server = null;
System.out.println("Trying to open serversocket!");
try {
server = new ServerSocket(8080);
} catch (IOException e) {
System.out.println("Error on port: 8080 " + ", " + e);
System.exit(1);
}
System.out
.println("Server setup and waiting for client connection ...");
Socket client = null;
try {
client = server.accept();
} catch (IOException e) {
System.out.println("Did not accept connection: " + e);
System.exit(1);
}
System.out
.println("Client connection accepted. Moving to local port ...");
try {
DataInputStream streamIn = new DataInputStream(
new BufferedInputStream(client.getInputStream()));
DataOutputStream streamOut = new DataOutputStream(
new BufferedOutputStream(client.getOutputStream()));
boolean done = false;
String line;
int i = 4;
while (!done) {
line = streamIn.readUTF();
if (line.equalsIgnoreCase(".bye"))
done = true;
else
System.out.println("Client says: " + line);
if (i == 4) {
streamOut
.writeUTF("Actually connected to Server with round "
+ i);
streamOut.flush();
i++;
}
}
streamIn.close();
streamOut.close();
client.close();
server.close();
} catch (IOException e) {
System.out.println("IO Error in streams " + e);
}
}
}
Here's the client code:
package com.amazon.aws.singlesensor;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.io.PrintWriter;
import java.net.Socket;
import java.net.UnknownHostException;
import android.util.Log;
class Client implements Runnable {
private Socket socket = null;
private InputStream streamIn = null;
private OutputStream streamOut = null;
public InputStream getStreamIn() {
return streamIn;
}
public Client(String serverName, int serverPort) {
System.out.println("Establishing connection. Please wait ...");
try {
socket = new Socket(serverName, serverPort);
Log.d("DEBUG", "Connected: " + socket);
start();
} catch (UnknownHostException uhe) {
Log.d("DEBUG", "Host unknown: " + uhe.getMessage());
} catch (IOException ioe) {
Log.d("DEBUG", "Unexpected exception: " + ioe.getMessage());
}
}
public void start() throws IOException {
streamIn = socket.getInputStream();
streamOut = socket.getOutputStream();
}
public void run() {
try {
streamOut.write(streamIn.read());
streamOut.flush();
} catch (IOException ioe) {
System.out.println("Sending error: " + ioe.getMessage());
stop();
}
}
public void handle(String msg) {
if (msg.equals(".bye")) {
System.out.println("Good bye. Press RETURN to exit ...");
stop();
} else
System.out.println(msg);
}
public void stop() {
try {
if (streamIn != null)
streamIn.close();
if (streamOut != null)
streamOut.close();
if (socket != null)
socket.close();
} catch (IOException ioe) {
System.out.println("Error closing ...");
}
}
public void send(String msg) {
PrintWriter printwriter = new PrintWriter(streamOut);
printwriter.write(msg);
printwriter.flush();
}
}
Here's the ClientThread Code
package com.amazon.aws.singlesensor;
import java.io.IOException;
import java.io.InputStream;
import android.os.Handler;
public class ClientThread extends Thread {
private Client client;
private InputStream input;
private String output;
private Handler handler;
private Runnable runner;
public ClientThread() {
}
public ClientThread(Client client, Handler handler, Runnable runner) {
this.setClient(client);
this.input = client.getStreamIn();
this.handler = handler;
this.runner = runner;
this.output = "";
}
public void run() {
int status = 0;
while (status != -1) {
try {
status = input.read();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
while (status != '~'){
try {
status = input.read();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
output = output + String.valueOf((char) status);
handler.post(runner);
}
output = output + "\n";
}
}
public String giveString(){
return output;
}
public void setClient(Client client) {
this.client = client;
}
public Client getClient() {
return client;
}
}
Thank you for your time!

How do i accept multiple clients on this program?

Through a lot of learning and research, i wrote a server side program. But the problem with this program is that it doesn't accept multiple clients, and i also wanted to know how to send the output back to client side instead of displaying it on the server side. Can someone please help me out with the code? This is what I've tried till now -
class Program
{
private static Regex _regex = new Regex("not|http|console|application", RegexOptions.Compiled | RegexOptions.IgnoreCase | RegexOptions.CultureInvariant);
static void Main(string[] args)
{
{
TcpListener serversocket = new TcpListener(8888);
TcpClient clientsocket = default(TcpClient);
serversocket.Start();
Console.WriteLine(">> Server Started");
clientsocket = serversocket.AcceptTcpClient();
Console.WriteLine("Accept Connection From Client");
try
{
using (var reader = new StreamReader(clientsocket.GetStream()))
{
string line;
int lineNumber = 0;
while (null != (line = reader.ReadLine()))
{
lineNumber += 1;
foreach (Match match in _regex.Matches(line))
{
Console.WriteLine("Line {0} matches {1}", lineNumber, match.Value);
}
}
}
}
catch (Exception ex)
{
Console.Error.WriteLine(ex.ToString());
}
clientsocket.Close();
serversocket.Stop();
Console.WriteLine(" >> exit");
Console.ReadLine();
}
}
}
You could change it to something like this.
static void Main(string[] args)
{
TcpListener serversocket = new TcpListener(8888);
TcpClient clientsocket = default(TcpClient);
serversocket.Start();
Console.WriteLine(">> Server Started");
while(true)
{
clientsocket = serversocket.AcceptTcpClient();
Console.WriteLine("Accept Connection From Client");
LineMatcher lm = new LineMatcher(clientsocket);
Thread thread = new Thread(new ThreadStart(lm.Run));
thread.Start();
Console.WriteLine("Client connected");
}
serversocket.Stop();
Console.WriteLine(" >> exit");
Console.ReadLine();
}
And then have this seperate class handling the linematching
public class LineMatcher{
private static Regex _regex = new Regex("not|http|console|application", RegexOptions.Compiled | RegexOptions.IgnoreCase | RegexOptions.CultureInvariant);
private TcpClient _client;
public LineMatcher(TcpClient client)
{
_client = client;
}
public void Run()
{
try
{
using (var reader = new StreamReader(_client.GetStream()))
{
string line;
int lineNumber = 0;
while (null != (line = reader.ReadLine()))
{
lineNumber += 1;
foreach (Match match in _regex.Matches(line))
{
Console.WriteLine("Line {0} matches {1}", lineNumber, match.Value);
}
}
}
}
catch (Exception ex)
{
Console.Error.WriteLine(ex.ToString());
}
Console.WriteLine("Closing client");
_client.Close();
}
}
This is purely a proof of concept and is no way stable code ;)
Please note that this doesn't manage the child-threads in any way.
There is also no correct way of shutting down the listener because of the while(true)

Server and Java Applet: Connecting Socket

I have a java applet recently stopped working after the server is updated, more specifically:
1. The server is updated from Sun, running Solaris 9, 32 bit. (installed in 2005) to CentOS 5, (linux) on 64 bit.
2. The applet has two major classes 1) collect.class: collects data from a canvas 2) server.class: listens to collect.class through a PORT and acts accordingly;
but the applet got stuck and I check the start_server.sh (which produces a report nohup.out) there is a line
Exception creating server socket: java.net.BindException: Address already in use
This is weird, because PORT = 9999 which collect.class uses with no problem. How comes the problem happens only in server.class (who listens to collet.class).
Please help!
ADDITIONAL INFORMATION:
I.IN COLLECT.JAVA:
There is a canvas with grid on it, the user draw some area on the grid and click "Submit".
-> The MineCanvas.submit() is triggered -> The value of the area is computed by MineCanvas.ComputeGridValue() -> then Collect.cleintSend (stuck here)
import java.applet.*;
import java.awt.*;
import java.net.*;
import java.io.*;
import java.util.*;
public class Collect extends Applet {
...
public static final int PORT = 8888;
...
public boolean action(Event e, Object arg) {
...
if (arg.equals("Submit")) {
if (action(null, "Update Grid")) {
minecanvas.Submit();
} else {
return true;
}
}
return true;
}
...
public void clientSend(){
s = new Socket(this.getCodeBase().getHost(), PORT);
in = new DataInputStream(s.getInputStream());}
out = new DataOutputStream(s.getOutputStream());
listener = new SolutionListener(in, minecanvas);}
minecanvas.mode = MineCanvas.SUBMITTING;
minecanvas.repaint();
int n = 1;
out.writeBytes(minecanvas.gridh + "\n" + minecanvas.gridw + "\n");
for (int h = 0; h < minecanvas.gridh; h++) {
for (int w = 0; w < minecanvas.gridw; w++) {
out.writeBytes(n + " " + minecanvas.AllCells[w][h].net + "\n");
n++;
}
}
out.writeBytes("done\n");
s = null;
in = null;
out = null;
}
}
class MineCanvas extends Canvas {
...
public int gridw = 0; // number of grid squares width-ly
public int gridh = 0; // number of grid squares height-ly
public GridCell[][] AllCells; // array of grid cells comprising the grid
...
// compute values for minecanvas
public void ComputeGridValue() {...}
public void Submit() {
ComputeGridValue();
parent.clientSend();
}
...
}
...
}
II. SERVER.JAVA
import java.io.*;
import java.net.*;
public class Server extends Thread {
private OPM_Server opm; // this is the corresponding server for collect
...
public Server() {
...
opm = new OPM_Server();
}
public static void main(String[] args) {
new Server();
}
}
...
// OPM: correspond to Collect
class OPM_Server extends Thread {
public final static int DEFAULT_PORT = 8888;
protected int port;
protected ServerSocket listen_socket;
public static void fail(Exception e, String msg) {
System.err.println(msg + ": " + e);
System.exit(1);
}
public OPM_Server() {
this.port = DEFAULT_PORT;
try { listen_socket = new ServerSocket(port); }
catch (IOException e){ fail(e, "Exception creating server socket");}
System.out.println("Server: listening on port " + port);
this.start();
}
public void run() {
try {
while(true) {
System.out.println("I got to before ServerSocket");
Socket client_socket = listen_socket.accept();
OPM_Connection c = new OPM_Connection(client_socket);
}
}
catch (IOException e) {fail(e, "Exception while listening for connections");}
}
}
...
class OPM_Connection extends Thread {
protected Socket client;
protected BufferedReader in;
protected DataOutputStream out;
File mine_data = new File("mine_data"); // output file data
FileOutputStream file_stream;
DataOutputStream file_out;
public OPM_Connection(Socket client_socket) {
client = client_socket;
try {
in = new BufferedReader(new InputStreamReader(client.getInputStream()));
out = new DataOutputStream(client.getOutputStream());
} catch (IOException e) {
try {
client.close();
} catch (IOException e2) {
}
;
System.err.println("Exception while getting socket stream: "
+ e.toString());
return;
}
this.start();
}
public void run() {
...
file_stream = new FileOutputStream(mine_data);
file_out = new DataOutputStream(file_stream);
...// write to mine data
file_out = null;
if (inputGood == true) {
System.out.println(pid + "> ---Got all info from client");
Runtime r = Runtime.getRuntime();
Process Aproc = null;
Process Bproc = null;
int returnVal = -1;
try {
Aproc = r.exec("runOPM");
} catch (IOException e) {
inputGood = false;
System.out.println(pid + "> runOPM didn't exec");
}
try {
returnVal = Aproc.waitFor();
} catch (InterruptedException e) {
inputGood = false;
System.out.println(pid + "> runOPM didn't return");
}
System.out.println(pid + "> ---All execing done");
File report = new File("mine_report");
FileInputStream report_stream = null;
...
// create a mine report
System.out.println(pid + "> ---Done sending data back to client");
}
try {
client.close();
} catch (IOException e2) {
}
;
System.out.println(pid + "> EXITING THREAD");
}
}
Exception creating server socket: java.net.BindException: Address
already in use
This exception means that the port number the socket is trying to bind to (the port number your socket is trying to use in the local-end of the connection) is already in use by some other program. To fix it, you either need to find out what other software is using the port and see if you can safely change it, or change the port your program is using.
Edit: It might be worth trying to look for rarely used port(s), to lessen the chance of using yet another port that is known to be used by some common software, here's Wikipedias list of typical TCP and UDP ports in use by common programs and services.