Messages, Handlers and Threading : Lego Mindstorms bluetooth communication - java

This question refers to writing an application that communicates with the NXT block on a lego mindstorms robot.
What I want to do
NXC (not exactly C, a language for writing programs for the NXT) supplies a function until(condition) that waits until condition evaluates to true. I want to implement this using the bluetooth messaging protocol, talking to the NXT via bluetooth from an android application.
What I can do so far:
I'm able to send an input query message (getInputValue(int in)), which sends a message to the NXT asking for the current status of the input in. The NXT then sends back a message with this information, which is then written to a global variable that holds the most recently asked input value (let's call it myValue).
What the problem is:
I'm using bits and pieces from the lego MINDroid application - in this class I have a separate communication thread which handles direct communication with the NXT. When it receives a message, it forwards it on to the main thread, via a Handler. The problem occurs when I try to busy wait for a reply - doing:
while(myValue != valueIWant) {
sleep(100);
getInputValue(in);
}
ends up busying the main thread, so that the handler never actually gets to receive any messages. The communication thread receives the messages from the NXT, forwards them to the main thread, but the handler never gets called because it's doing other stuff.
What's the best way to get around this? I can't get the thread to wait in any way because that would stop it receiving messages also :(
Any suggestions would be appreciated! I'll also happily elaborate on any bits of code.
Links that may be useful
http://bricxcc.sourceforge.net/nbc/nxcdoc/nxcapi/main.html
http://github.com/NXT/LEGO-MINDSTORMS-MINDdroid
http://mindstorms.lego.com/en-us/support/files/default.aspx (for the bluetooth docs)

Solved, using callbacks :) Happy to elaborate if needed.
Edit: (sorry for late reply!)
I ended up implementing a callback procedure, where I attached a 'callback' function to some list. When the handler receives a message, it would look in the list of callbacks and see if the message received matched any of the callback functions that are present - if so, it would execute the method inside the callback.
I then made a class around these callbacks, where I could create execution queues (doA; doB; doC;) and it would wrap those up into a callback chain (callBack({doA; callBack({doB; call...})})), which gave the impression that I was operating in a synchronous environment, when in fact it was operating asynchronously.

Related

Netty : Blocking call to get a connected Server Channel?

The call on ServerBootstrap.bind() returns a Channel but this is not in a Connected status and thus cannot be used for writing to client.
All the examples in Netty documentation show writing to a Channel from its ChannelHandler's events like channelConnected - I want to be able to get a connected Channel not in the event but as a reference outside the event , lets say some client code using my server component. One way is to manually code for waiting for channelConnected event and then copying the Channel reference.But this may be reinventing the wheel.
So the question is : Is there a blocking call available in Netty that returns a Connected Channel ?
edit : I am using Oio Channels , not Nio.
You could create a blocking call, but I think you maligned the event based approach too quickly. This is a contrived example, just to make sure I understand what you're trying to do:
Netty Server starts
A DataPusher service starts.
When a client connects, the DataPusher grabs a reference to the client channel and writes some data to it.
The client receives the pushed data shortly after connecting.
More or less correct ?
To do this, your DataPusher (or better yet, one of its minions) can be registered as a ChannelHandler in the server pipeline you create. Make it extend org.jboss.netty.channel.SimpleChannelHandler. The handler might look like this:
DataPusher dataPusher = getMyDataPusherReference();
public void channelConnected(ChannelHandlerContext ctx, ChannelStateEvent e) {
dataPusher.doYourThing(e.getChannel()); // do something in another thread....
}
If you are determined to make it a blocking call from the DataPusher's perspective, just have it wait on a latch and have the minion drop the latch.
Not sure if that's what your'e looking for.....
After all the exchanges above, I still don't see that any of this is necessary.
Surely all you have to do is just accept the connection from the external service; don't register it for any events; then, when the other client connects, register for I/O events on both channels.
The external service doesn't know or care whether you are blocked in a thread waiting for another connection, or just not responding for some other reason.
If he's writing to you, his writes will succeed anyway, up to the size of your socket receive buffer, whether you are blocking or not, as long as you aren't actually reading from him. When that buffer fills up, he will block until you read some of it.
If he is reading from you, he will block until you send something, and again what you are doing in the meantime is invisible to him.
So I think you just need to simplify your thinking, and align it more with the wonderful world of non-blocking I/O.

ConcurrentLinkedQueue does'n work as expected

I'm developing an Andoid App that is made of a Service running in Background and some Activities connected to that Service. The Service runs on it's own Process.
My Service mainly has 3 classes: ServiceMain, ServiceWorker,Message.
ServiceMain has all the functions that are used by the Activities like logIn,logOut,send ... and so on.
Message represents a message that is sent to our server or recieved. Simply a String and a bool where the String is the message and the bool is a flag saying if a response from server is needed.
ServiceWorker is a subclass of Thread and does all the sending an recieving of messages using Sockets.
ServiceMain contains 2 Queues:
Queue<Message> Sendingqueue= new ConcurrentLinkedQueue<Message>();
Queue<Message> Recievequeue = new ConcurrentLinkedQueue<Message>();
If the logIn method is called a ServiceWorker is created and started. In it's constructor it gets references to both queues and holds them.
private final Queue<Message> Sendingqueue;
private final Queue<Message> Recievequeue;
ServiceMain then creates some messages (M1,M2 for example) and adds them to the Sendingqueue.
The ServiceWorker builds the connection to our server and then runs into a loop where it looks for messages in Sendingqueue, sends them and doing some othe stuff like recieving ....
Hope the scenario is clear now.
Within ServiceWorker something strange happens on Sendingqueue:
Let's say ServiceMain added two messages, M1 and M2 to Sendingqueue while ServiceWorker is doing something time consuming or is not connected to our server.
Sendingqueue now contains two messages.
If the ServiceWorker next time gets the length of the Queue it sees 2 items. Ok so far.
Then it calls peek() (the message is removed only if it was successfull sent) on the Sendingqueue and should get M1 because it was added first.
But it gets M2.
The Sendingqueue seems to be reverted.
What's going wrong here ? What can I do to avoid this?
Thanks for any constructive reply.
Detlef
ConcurrentLinkedQueue doesn't make any guarantees about order, but the order of elements shouldn't change if you are adding to the end and taking from the start (or visa versa) thsi should work. You could run into a problem if you add and remove from the start or end as this will mean you are processing the newest rather than the oldest each time.
If you had a large powerful server, I would still suggest this approach is overkill. Instead of having a background thread to perform the processing, I would use the main thread.
Note: The socket is already an input and output queue on the client and on the server, so adding a third layer of queuing may be redundant in a large system and inefficient in a smaller device.

Handling Java Interupts

I am making an application that will work much like a real time chat. A user will be constantly writing on lets say a text area and messages will be send to other users. On the communications class I have set up a receiver. When a message from someone reaches the client, the receive method will be invoked and will get the message. What I can't understand is how the code will be executed. What happens if, while the user is typing/sending a message the receive message is invoked ? What do I need to do in order for this to work properly ?
Hope the question is clear enough.
ps : Im still in the design phase thats why I haven't tested it to see what happens.
Also atm I only use a second thread to receive messages which calls the receive method.
There should not be a problem at all.
When a message from someone reaches the client, the receive method
will be invoked and will get the message. What I can't understand is
how the code will be executed?
You should have a Receiver class that will encapsulate a socket (from which your receive data) and keep a set of listeners (see Observer pattern). A GUI can be one of the listeners. When a message is received via the socket, you need to notify all listeners by forwarding the data received. This way, you have a clean and nice way to notify the GUI about new messages arrivals.
What happens if, while the user is typing/sending a message the
receive message is invoked ?
This depends on the type of IP protocol you are using but in general your don't have to worry about this although I suggest you protect your sockets using lock mechanisms.
What do I need to do in order for this to work properly ?
Here is a nice example that can give you some inspiration :)
EDIT: As for your question regarding execution flow, sending and receiving are two different and uncorrelated operations that can happen at the same time. This can be achieved by implementing send and receive operations in two different threads. Here is an article on socket communications and multithreading.
You should either do what traditional Java EE app servers have done, which is assign a separate thread for processing each incoming message, or try a Java NIO solution along the lines of Netty.

Communication between Servlets

I would like to write a method which handles the flow of communication on XMPP. The sequence of things I'd like to do is:
Send message.
Wait for response.
Process the response.
Since we could be waiting longer than 30s for the response (step 2) I'll be teeing up a task to take care of this. This task will need to send the message and then wait for a response on the XMPP servlet handling the incoming message. My question is: How do I wait in the task servlet thread for the response to arrive in the XMPP Servlet?
I'd normally use a listener pattern where the listener would store the message in a field in the Task object and then trigger a Semaphore to signal that a message has arrived. Like this:
Install listener in XMPP servlet in a static field.
Send message.
Wait for semaphore. ........ Meanwhile, in the XMPP servlet thread, a response will arrive and it will call the listener's callback method which stores the message and releases the semaphore.
Get message from field and process.
I tried this and it worked fine on the development server. However, when I uploaded to the cloud I found that I'd install the listener on the XMPP servlet (step 1) but then a new instance of the servlet would be instantiated when the message came in and there would no longer be a reference to the listener to call, event through the listener is a static field. My conclusion is XMPPServlet is run in a completely different VM meaning the static field is not shared between that servlet and the task one. Is this correct?
In general what is the best practice for communication between these servlets? How to I share data (normally I would've stored it in an object's field) and how do I signal from one to the other when events occur (normally I would've used a semaphore)?
Sorry about the long winded question. Tell me if it's not clear and I'll refine it a bit.
Reposting my answer to the same question you asked on the mailing list:
You can't [wait for a response in the sending process]. Instead, you
should use an asynchronous pattern: Send the message, and register a
handler for incoming XMPP messages. That handler should match up the
response to the corresponding request (stored in the datastore if
necessary) and perform appropriate processing on it.
An App Engine app can be run on any number of machines;
synchronization primitives designed for communication between threads
will not work.

Looking for some Java good practice advice regarding distributed applications and message passing

Some background information. This is a distributed application with multiples nodes. A 'communication' thread sends and receives all messages sent between these nodes. This cannot be changed.
A 'doStuff' thread asks the 'communication' thread to send a message to a node. It then needs to wait for a response from the other node. The 'communication' thread will receive this response message. It then needs to deliver this message to the correct 'doStuff' thread.
I am unsure what sort of information needs to be stored at the node or within the message to ensure that the correct thread always receives the response message.
Looking for some advice upon how to achieve this. Thanks for reading :)
You probably want to attach some sort of message id to the outgoing message to be included in the response. A sequential number or a UUID would probably do the job. Your communicator thread can then keep track (a map?) of what "doStuff" thread was waiting for a given response and pass it back.
You could also keep track of when the request was sent so that if a response isn't received the communicator thread can notify the doStuff thread that the response wasn't received.
It doesn't seem very difficult
Use either a thread id, or other opaque token invented by the doStuff thread which is stored by the Communication thread (mapped to the calling thread id) and returned with the response The communication thread looks it up in the Map to identify the corresponding thread.
Or am I missing something?
Is using JMS an option at all? If so, you might find that more practical than doing "roll your own." Asynchronous message passing, in general, is a solved problem. If JMS is an option, look at TopicRequestor and/or QueueRequestor in particular.

Categories