Situation: An Android phone has been connected to a PC via USB. Using the ADB command adb forward tcp:35000 tcp:30000
, I succeed in forwarding a port.
I want the PC to send its system time to the Android phone every 5 seconds for an hour. To this end, I do the socket programming.
The PC side as a client: (I ignore the exception handling code.)
public void sendTime()
{
class SendTask implements Runnable
{
public void run()
{
// Here: I store the host_socket in a member field which is:
// Socket host_socket = new Socket("localhost", 35000);
ObjectOutputStream oos = new ObjectOutputStream(this.host_socket.getOutputStream());
oos.writeObject(msg);
oos.flush();
}
}
// Here: private Executor exec = Executors.newCachedThreadPool();
this.exec.execute(new SendTask());
}
The Android phone side as server:
public void getReadyForSync()
{
ServerSocket server_socket = new ServerSocket();
server_socket.bind(new InetSocketAddress("localhost", 30000));
while (true)
{
final Socket client_socket = server_socket.accept();
Runnable receive_task = new Runnable()
{
public void run()
{
ObjectInputStream ois = new ObjectInputStream(client_socket.getInputStream());
Message msg = (Message) ois.readObject();
SyncTimeFragment.this.onReceive(msg);
}
};
// Here: private static final Executor exec = Executors.newCachedThreadPool();
exec.execute(receive_task);
}
}
In addition, the ServerSocket is established in a separate thread from the main Android thread using AsyncTask
and new ServerTask().execute()
:
public class ServerTask extends AsyncTask<String, Void, Void>
{
protected Void doInBackground(String... params)
{
getReadyForSync();
return null;
}
}
Problems:
In my test, the server socket in Android phone accepts connections from PC only once.
Specifically, some debug information is as follows:
(1) Each time (every 5 seconds) sendTime()
is called, the host_socket
reads:
Socket[addr=localhost/127.0.0.1,port=35000,localport=56520]
Notice: The localport
(s) here are the same for all sendTime()
calls in a single execution, but different across executions. (I am not sure whether this information is important or not.)
(2) The server_socket
reads:
Socket[addr=localhost/127.0.0.1,port=0,localport=30000]
(3) The client_socket
received (only once) by the server_socket
reads:
Socket[addr=/127.0.0.1,port=43890,localport=30000]
After creating receive_task
the code returns to final Socket client_socket = server_socket.accept();
So the server throws away the connection as the run()
will only grab one message. You would have to made a while
loop in run()
too.