I've written a Java application that is launched as a daemon (I daemonize redirecting stderr and stdout and closing stdin though bash). However, occasionally I would like to be able to message this application and inform it to change certain parts of its behavior. I need to be able to message the application from a terminal, so anything that requires a graphical utility is a no-go.
The change in behaviour is fairly simple. I need a toggle for the state of one thread in my application, and a way to gracefully close the application.
What are my options in achieving this? I know I could have a thread in the process that listens on a socket of some sort for messages, but this seems like overkill for the needs I have.
I'm not too familiar with Signals on Linux/Unix, so I'd like to ask if I could simply set up a custom handler for some signals, and have my code execute when the process receives a signal.
Are there any other options that I simply don't know about or haven't thought about?
Signals may be the easiest. You have SIGUSR1 and SIGUSR2 available for application use and you can write a handler for them to manage your toggle. Generally you don't want to do much in a handler so you can set a switch and your main loop (or whatever) needs to check the switch and act accordingly. Similarly the receipt of the signal could be programmed to read a config file that you changed.
Beyond that you can use any available IPC (fifos, sockets, MQs) but you are going to either have thread blocking on them or somehow incorporate them a select statement (or whatever the java equivalent of that is).
You basically need a small client that communicates with your application (server). So the default solution should be to use some IPC mechanism. Putting an IPC mechanism is a one time effort and is worth the trouble because it scales well with the requirements. Using signals for IPC is not recommended. I think sockets is a good way to go.
Personally, I like to use OS signals for this.
Use java.lang.Runtime.addShutdownHook and send a SIGTERM, SIGINT or SIGHUP.
Be aware that some signals are reserved for internal use, check out the docs for the JVM you are using.
The SignalHandler is not part of the supported, public interface, so your mileage may vary.
If you are instantiating a JVM from C code, simply set signal handlers (in C) before the JVM and you will be fine.
Related
I assume Java applications receive some sort of shutdown request when, for instance, an OS is trying to reboot. I would like to have some control over how my applications handle these requests. But, I do not know where to start. Some questions I have are:
Do all shutdown requests come from the JVM?
Are the requests different for containers, VMs, and bare metal OSs? I am especially interested on how this is handled inside a docker container.
And, of course, what libraries can I use to handle these requests?
It would be wonderful if someone could point to a resource where this is covered in depth, besides the raw documentation, such as a book or online course (does not have to be free). Although, a link to the documentation will definitely be appreciated as well. Thanks!
Update:
I know I need to be able handle an event like the power cord being yanked.
However, when I ask my Windows machine to shutdown, sometimes a window pops up saying something like "waiting for these application to close". So, I assume the OS tells the applications to shut themselves down before forcing them to stop. Is this an incorrect assumption?
What I want to accomplish is for the app to log information or update a database before shutdown.
I will take a look at the addShutdownHook. Thanks again!
You can add a shutdown hook via the Runtime class. Mind you, these are not guaranteed to run, such as if someone yanks the power cord.
Refer Oracle Documentation
I have written a java program that can read the epc code of rfid card when the card is shown to the sensor.
Now, I need a different program that can terminate the program which is reading the card.
In my program I have written a function that can stop reading the card, but I don't know how to use that function in other program to terminate the currently running program
This question is pretty open-ended and not really Java-specific. There are a lot of kinds of inter-process communication, take your pick.
A few options off the top:
Store the PID of the first process in a file when you start it, and then the second process can stop it by sending a kill signal. This is a lightweight option because it doesn't involve modifying the first process, but has the disadvantage of being platform-specific and not being able to cross a machine boundary.
Have the first process act as some kind of socket-based server and the second process access it as a client. This is nice because it works over the network, you can take advantage of the existing procotol if you end up needing to expand the scope of the IPC (e.g. to add authentication, additional functions beyond just termination, etc.), and you can leverage existing clients (e.g. if you use HTTP, maybe you just use curl instead of building something in Java for the second process).
Use a message-passing platform like Akka, or some RPC library. If you want to keep your mind inside the JVM and learn as little as possible about anything else, you might take one of these approaches, but you'd end up coupling the two processing together to an extent that doesn't sound necessary.
I need to pass information from a shell script (called from a linux based app) to a java application.
Named pipes are a pain because I can't start/stop either service without considering complex repercussions to the read/write ends of the pipes.
Sockets are tough because if the listening process is restarted there's no queuing mechanism, and simple implementations require new sockets be constantly created (else the shell script will get very complex with check-and-restart-socket, and queuing code).
I was recently reading about these System V/POSIX linux message queues. I'm running Fedora 12, and wonder if there's a good way to configure these message queues and interact with them from Java.
You can't use them directly, you'd have to do some JNI wizardry to interface them together.
What problems are you having with Pipes? Java sees those as just generic files. I haven't used them extensively, but I didn't have any real problems with Pipes. The only detail there was the pipe reader needs to continually reopen the pipe if the producers can't keep up.
But if either side fails, the other side just blocks waiting for the other to recover.
You just have to be careful with buffer reads from the pipe. If you read from the pipe in to a buffer, and then fail, that data is lost.
Alright, so I'm writing this program that essentially batch runs other java programs for me (multiple times, varying parameters, parallel executions, etc).
So far the running part works great. Using ProcessBuilder's .start() method (equivalent to the Runtime.exec() I believe), it creates a separate java process and off it goes.
Problem is I would like to be able to pause/stop these processes once they've been started. With simple threads this is generally easy to do, however the external process doesn't seem to have any inbuilt functionality for waiting/sleeping, at least not from an external point of view.
My question(s) is this: Is there a way to pause a java.lang.Process object? If not, does anyone know of any related exec libraries that do contain this ability? Barring all of that, is extending Process a more viable alternative?
My question(s) is this: Is there a way to pause a java.lang.Process object?
As you've probably discovered, there's no support for this in the standard API. Process for instance provides no suspend() / resume() methods.
If not, does anyone know of any related exec libraries that do contain this ability?
On POSIX compliant operating systems such as GNU/Linux or Mac OS you could use another system call (using Runtime.exec, ProcessBuilder or some natively implemented library) to issue a kill command.
Using the kill command you can send signals such as SIGSTOP (to suspend a process) and SIGCONT (to resume it).
(You will need to get hold of the process id of the external program. There are plenty of questions and answers around that answers this.)
You will need to create a system for sending messages between processes. You might do this by:
Sending signals, depending on OS. (As aioobe notes.)
Having one process occasionally check for presence/absence of a file that another process can create/delete. (If the file is being read/written, you will need to use file locking.)
Have your "main" process listen on a port, and when it launches the children it tells them (via a comamnd-line argument) how to "phone home" as they start up. Both programs alternate between doing work and checking for handling messages.
From what you have described (all Java programs in a complex batch environment) I would suggest #3, TCP/IP communication.
While it certainly involves extra work, it also gives you the flexibility to send commands or information of whatever kind you want between different processes.
A Process represents a separate process running on the machine. Java definitely does not allow you to pause them through java.lang.Process. You can forcibly stop them using Process.destroy(). For pausing, you will need the co-operation of the spawned process.
What sorts of processes are these? Did you write them?
I would like to know if it is possible to automatically invoke a Java method when a hardware interrupt is raised.
There may be an alternative.
I'm doing something similar: In an application I monitor 4 mice for clicks. Those clicks generate interrupts but I'm happy enough not to deal with them directly from Java.
Under Linux, it turns out there are device files (/dev/input/mouse#) that spew a bunch of characters when something happens with the mouse. I have a Thread for each one with a FileReader blocking on a read. Once characters arrive, the appertaining thread unblocks and I can do whatever processing I like.
So the idea is: If possible, find a way to get a device driver to make the data accessible to you in file/device form, then you can access it from Java using just IO calls from the Java library, with no weird bit-twiddling code and C required in between.
In principle yes, but it will require some C code and JNI to tie that to Java. If you are very lucky perhaps already someone has already built a suitable library for the paltform you are interested in.
Bottom line: if it can be done in C you can hook that to Java.
If you would like to directly respond to an interrupt from Java, then the VM would have to run in kernel space (or on some systems with user space drivers, in a driver context). The JamaicaVM runs in this mode on some RTOSes such as Thread-X or VxWorks as a DKM. The next release of the RTSJ will support writing interrupt service routines in Java.
The RTSJ can be used to run second level interrupt handlers even in user space. This requires a small device driver that either sends a POSIX signal to the VM or provides a character device interface where one thread in the VM blocks on a read of the device. In the first case, an AsyncEventHandler can be assoicated with the POSIX signal. In the second, the tread that blocks on a read of the device can fire an AsyncEvent each time a byte is read from the device. Then any AsyncEventHandler attached to the AsyncEvebt would be released.
If you would like to try this under Linux, you can download the JamaicaVM personal edition: "http://www.aicas.com/jamaica-pe.html". JamaicaVM has a realtime garbage collector and code can be compiled statically to ensure realtime performance. This is a different deployment model than a conventional JVM.
Here is a paper that handles the same topic. And you may have a look at SWT, I think they're dealing with hardware interrupts aswell, although they may rely on the operating systems API.
It's standard on embedded realtime java. go to www.ajile.com, or systrmonx.com and buy an eval board.
Embedded java is not standard on pc's. you can get realtime java on PC hardware, but not the embedded bit.
Take a look at Swig. The Java implementation has Directors that will allow you to call into Java from C/C++.
I've used this technology to handle interrupts calling into C#, and it worked great. Shouldn't be much different calling Java.