I am writing a java program that needs to continuously accept serialized objects throughout the run of the application. The objects are sent by a server as requested by the user.
My main application initializes the tcp client (extends thread) in its run method, but I am trying to read objects from the line from a function.
Pseudocode follows:
*tcp client extends thread
*global vars: ip, port, socket, oi stream, oo stream, object reference
*run()
make connection
*getObject()
object reference = (object).readobject()
return object
My main application calls client.getObject() in an update loop. there may or not be an object waiting.
Am I going about this the wrong way?
Are you trying to do "classic" server behavior or non-blocking IO?
If it's the former, I'd recommend a blocking queue on the server to accept incoming requests and a pool of threads to process them. Have the server assign a thread to process the request when it comes in until the thread pool is exhausted; queue up requests until threads are freed up and returned to the pool.
Non-blocking IO is another matter entirely. Look at how Netty and node.js are designed and implemented for that.
I would never have a class extend Thread - it's unlikely that you'll add significant new behavior. Implement Runnable instead and give it to a Thread instance to run.
I would suggest your run() method reads all the objects and adds them to a queue.
getOject() takes the next object from the queue.
You can also have a int queueLength() to check how any are waiting.
Related
I am developing a stateless Agent in Java that takes informations from one Server and transfer it to another client. It means that the agent is located between a client and a server. So I am thinking to run two threads simultaneously on the agent: one thread (thread1) runs a serverSocket and get request from client while another threads (thread2)is runnning and makes communication with the server. The problem consists in synchronizing between the two threads. I am thinking in making thread 1 asking whole the time thread 2 about a new Information. If thread 2 has nothing new, he will not answer it. What is the best way to synchronize between them. Should I use a global variable (a flag) to synchronize between them? Can I save Information when I have a stateless agent?
I think you should modify your app into async model.
Your app needs:
- an entry point to accept incoming connections -> a good example is an async servlet (or one dedicated thread).
- a ThreadPoolExecutor that provides fixed numbers of workers and a blocking queue (use this constructor).
The workflow:
Accept incomming request.
Wrapp incoming request into (Runnable) task.
Put task into blocking queue.
If ThreadPoolExecutor has a free worker starts processing the task
An advantage of such a model is that you are able to handle one request using one thread. So there is no need to manually synchronize anything.
I would like to use Java Netty to create a TCP server for a large number of persistent connections from a clients. In other words, imaging that there are 1000 client devices out there, and all of them create and maintain a persistent connection to the TCP server. There will be a reasonable amount of traffic (mostly lines of text) that go back and forth across each of these persistent connections. How can I determine the best number of threads to use in the boss and worker groups for NioEventLoopGroup?
My understanding is that when the connection is created, Netty creates a SimpleChannelInboundHandler<String> object to handle the connection. When the connection is created then the handler channelActive method is called, and every time it gets a new message from the client, the method messageReceived gets called (or channelRead0 method in Netty 4.0.24).
Is my understanding correct?
What happens if I have long running code to run in messageReceived -
do I need to launch this code in yet another thread
(java.util.Thread)?
What happens if my messageReceived method blocks on something or
takes a long time to complete? Does that bring Netty to a grinding
halt?
Basically I need to write a TCP socket server that can serve a large number of persistent connections as quickly as possible.
Is there any guidance available on number of threads for NioEventLoopGroup and on how to use any threads inside the handler?
Any help would be greatly appreciated.
How can I determine the best number of threads to use in the boss and worker groups for NioEventLoopGroup?
About Boss Thread,if you are saying that you need persistent connections , there is no sense to use a lot of boss threads, because boss threads only responsible for accepting new connections. So I would use only one boss thread.
The number of worker threads should depends on your processor cores.
Don't forget to add -XmsYYYYM and -XmxYYYYM as your VM attributes, because without them you can face the case, when your JVM are not using all cores.
What happens if I have long running code to run in messageReceived - do I need to launch this code in yet another thread (java.util.Thread)?
Do you really need to do it? Probably you should think of doing your logic another way, if not then probably you should consider OIO with new thread for each connection.
What happens if my messageReceived method blocks on something or takes a long time to complete?
You should avoid using thread blocking actions in your handlers.
Does that bring Netty to a grinding halt?
Yep, it does.
I am working on creating a chat client based on UDP. The main structure is that there is a server where clients register and where clients can also request to form a connection with another client that is registered with the server. The clients are structures as follows using pseudo code:
public UDPClient() {
// Create datagram socket
// Execute RECEIVE thread using datagram socket above
// Execute SEND thread using datagram socket above
}
The idea is to have the send and receive executing on separate threads so I don't get blocked I/O on the receive. Both of these threads have loops within their run methods that allow you to continually send and receive messages. The problem I have is this. If a message comes in on the RECEIVE thread that changes how my SEND should be executing, how do I communicate this to the SEND thread? Do I have to shoot a datagram off to myself or can I communicate this in the code somehow?
Assuming boths threads have no reference to each other, create a third singleton class, which both read/send threads (classes) reference, that has a volatile member field to store the state data you want shared and which has synchronized access.
The volatile keyword, combined with synchronized access, guarantees that a change made to the field by one thread will be seen by another thread. Without this, changes may not be visible due to the java memory model specification.
Edited:
Following "separation of concerns" design guideline, it would be better to not have the read/send threads know about each other and to use a third class to orchestrate their activities/behaviour. Add methods to your read/send classes to stop(), start() etc and call these from the other class.
Using a separate class would also allow:
Behaviour control by other means, for example a "stop sending" button on an admin web page
Allowing multiple threads of each type, yet still having proper control through a central point, perhaps using a pool of such threads (without a separate class, you would have a many-to-many nightmare and lots of code that has nothing to do with the job at hand: ie ending and receiving)
Easier testing of your worker classes, because they do less and are more focused
porting/embedding them stand-alone for other uses
your SEND thread should have public (accesible) method (synchronized if possible) that you should be able to access from your RECEIVE thread. You could use this method to create a boolean flag, string message, etc. that you should always read before you .send(yourPacket); from your SEND thread.
Have a member variable in your READ method that your code can read from and change the SEND method based on that variable.
I'm developing a simple network client/server. The client has a MainConnection class which maintains the connection to the server and starts worker threads based on information coming in. I want the worker threads to send feedback on their progress to the server via the main connection. I’m not sure if I should have a public static synchronized method in MainConnection for sending data, or pass a Session object to the threads which would contain the Socket and a synchronized method for sending data.
It does not matter which design will you choose. It is really up to you. The only thing you should care about is to avoid 2 threads writing to the same stream concurrently. So, you can create your own layer that is synchoronized and used by several threads. Alternatively you can create synchronized output stream and pass it to all threads. This is probably the best approach: in this case each thread just knows to write stuff to the stream. The only layer that knows that stream is synchronized is a factory that creates it.
I'm currently busy working on an IP ban tool for the early versions of Call of Duty 1. (Apparently such a feature wasn't implemented in these versions).
I've finished a single threaded application but it won't perform well enough for multiple servers, which is why I am trying to implement threading.
Right now, each server has its own thread. I have a Networking class, which has a method; "GetStatus" -- this method is synchronized. This method uses a DatagramSocket to communicate with the server. Since this method is static and synchronized, I shouldn't get in trouble and receive a whole bunch of "Address already in use" exceptions.
However, I have a second method named "SendMessage". This method is supposed to send a message to the server. How can I make sure "SendMessage" cannot be invoked when there's already a thread running in "GetStatus", and the other way around? If I make both synchronized, I will still get in trouble if Thread A is opening a socket on Port 99999 and invoking "SendMessage" while Thread B is opening a socket on the same port and invoking "GetStatus"? (Game servers are usually hosted on the same ports)
I guess what I am really after is a way to make an entire class synchronized, so that only one method can be invoked and run at a time by a single thread.
Hope that what I am trying to accomplish/avoid is made clear in this text.
Any help is greatly appreciated.
Right now, each server has its own thread.
Why do you need two servers in the same application?!? If you break both of the servers out into separate application, then you're still going to have the same issue if both of them try to use the same port... i.e. you have to dedicate a port for each server. If it's really a problem with the threading, then read below for ideas on how to fix this.
It's not possible for two threads to execute properly synchronized methods of the same class... if you have proper synchronization then there is no way to experience what you're describing. Here is what your class should look like:
class Networking
{
public synchronized Status getStatus() {
Status stat = new Status();
// ...
// Get status logic
// ...
return stat;// return the status
}
public synchronized void sendMessage(Message msg) {
// ...
// Send the message logic
// ...
}
}
So as long as you're invoking those methods on the same Networking instance (i.e. you don't have a separate instance of the Networking class for each thread), then you should not see any issues. Here is what the synchronized keyword does for you:
First, it is not possible for two invocations of synchronized methods on
the same object to interleave. When
one thread is executing a synchronized
method for an object, all other
threads that invoke synchronized
methods for the same object block
(suspend execution) until the first
thread is done with the object.
Second, when a synchronized method exits, it automatically establishes a
happens-before relationship with any
subsequent invocation of a
synchronized method for the same
object. This guarantees that changes
to the state of the object are visible
to all threads. (ref)
If you want to have synchronization of the methods across all of the instances of the Networking class then you need to use synchronization statements:
class Networking
{
private static final Object lock = new Object();
public synchronized Status getStatus() {
synchronized(lock){
Status stat = new Status();
// ...
// Get status logic
// ...
return stat;// return the status
}
}
public synchronized void sendMessage(Message msg) {
synchronized(lock){
// ...
// Send the message logic
// ...
}
}
}
will [ I ] still get in trouble if Thread A
is opening a socket on Port 99999 and
invoking "SendMessage" while Thread B
is opening a socket on the same port
and invoking "GetStatus"?
There are two separate issues here. ( beyond the fact that 99999 is not a valid port # )
UDP by it's nature is meant for multiplexed one to many style communications. You can open a single socket and use that single socket to communicate with as many servers as you want. You don't have to worry about synchronization in the sense of one thread sending and another receiving on the same socket or two threads trying to send simultaneously because the read and write operations to the socket are atomic from the applications point of view. When you send on a UDP socket you are invoking a system call which copies N bytes of data from the application's memory space into a buffer in the OS kernel's memory space, and the kernel assembles that data into a UDP packet which is put on a queue for sending - all in a manner which looks atomic to the application. The same occurs when reading from a UDP socket except in reverse; distinct packets exist in a receive buffer in the kernel and when your application reads the socket the data in those packets is atomically copied from the kernel buffer into your application's buffer, one packet per read operation.
The second issue is managing incoming and outgoing data to specific servers. It sounds like you want to have one thread per server which maintains state / status regarding that server. When sending, you don't have to worry about synchronization at all. All the threads can send from the same socket and synchronization is effectively handled by the OS kernel.
However, receiving is a completely different issue. I would recommend having one thread whose only job is to read incoming packets off the socket and de-multiplex them. Each server thread would have a thread safe queue into which the reader thread would copy the incoming packets. Then each server thread doesn't have to worry about anything other than reading packets out of it's own incoming packets queue - it doesn't have to deal with reading from the socket at all.
I think you may be misunderstanding how sockets work and getting client and server ends of sockets confused. If you're sending a message, that usually done from a client socket. These are not bound to a static port number - it's the server socket (the one you call accept() on) that is bound to a specific port.
You can have as many clients as you need (up to some reasonable limit - there is a max of ca. 60,000 client connections) from any one network interface.
For an introduction to client and server-side sockets, see the Sun Lesson: All About Sockets