From a3ff75e35e80cc43b258f47aeda15022b5936945 Mon Sep 17 00:00:00 2001 From: gumartinm Date: Wed, 18 Jan 2012 02:19:01 +0100 Subject: [PATCH] Launch commands without using fork from the JVM. Sometimes you may receive a nice OutofMemory exception because of the overcommitting memory allocation, although you could have still enough memory. Issues related to fork and virtual memory. See: http://developers.sun.com/solaris/articles/subprocess/subprocess.html --- JavaFork/Daemon/README.txt | 3 + JavaFork/Daemon/javafork | Bin 0 -> 22009 bytes JavaFork/Daemon/javafork.c | 347 +++++++++++ JavaFork/Daemon/javafork.h | 7 + JavaFork/JavaExample/javafork-example/pom.xml | 22 + .../src/main/java/de/fork/java/ForkDaemon.java | 166 ++++++ .../src/main/java/de/fork/java/ForkParser.java | 141 +++++ .../main/java/de/fork/java/LauncherProcesses.java | 275 +++++++++ .../src/main/java/de/fork/java/MainJavaFork.java | 35 ++ JavaFork/JavaExample/pom.xml | 663 +++++++++++++++++++++ 10 files changed, 1659 insertions(+) create mode 100644 JavaFork/Daemon/README.txt create mode 100755 JavaFork/Daemon/javafork create mode 100644 JavaFork/Daemon/javafork.c create mode 100644 JavaFork/Daemon/javafork.h create mode 100644 JavaFork/JavaExample/javafork-example/pom.xml create mode 100644 JavaFork/JavaExample/javafork-example/src/main/java/de/fork/java/ForkDaemon.java create mode 100644 JavaFork/JavaExample/javafork-example/src/main/java/de/fork/java/ForkParser.java create mode 100644 JavaFork/JavaExample/javafork-example/src/main/java/de/fork/java/LauncherProcesses.java create mode 100644 JavaFork/JavaExample/javafork-example/src/main/java/de/fork/java/MainJavaFork.java create mode 100644 JavaFork/JavaExample/pom.xml diff --git a/JavaFork/Daemon/README.txt b/JavaFork/Daemon/README.txt new file mode 100644 index 0000000..604f093 --- /dev/null +++ b/JavaFork/Daemon/README.txt @@ -0,0 +1,3 @@ +Launch: + +javafork IPADDRESS TCP_PORT MAX_LISTEN diff --git a/JavaFork/Daemon/javafork b/JavaFork/Daemon/javafork new file mode 100755 index 0000000000000000000000000000000000000000..6ad921297f574f913c3ba6f301a8c73dfd5e5f51 GIT binary patch literal 22009 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 T$WcfAd&90M_l@n4YNr1Slu6Pj literal 0 HcmV?d00001 diff --git a/JavaFork/Daemon/javafork.c b/JavaFork/Daemon/javafork.c new file mode 100644 index 0000000..6d78c0c --- /dev/null +++ b/JavaFork/Daemon/javafork.c @@ -0,0 +1,347 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include "javafork.h" + + +int main (int argc, char *argv[]) { + pid_t pid; + + if ((pid = fork()) == -1) { + perror("fork: "); + return -1; + } + else { + if (pid == 0) { + /*child process*/ + main_child(argc, argv); + } + } + + return 0; +} + + +int main_child (int argc, char *argv[]) { + struct protoent *protocol; + struct sockaddr_in addr_server; + struct sockaddr_in addr_client; + int sockfd; + int sockclient; + pthread_t idThread; + int clilen; + + + daemonize(argv[0], LOG_SYSLOG, LOG_PID); + setsid(); + + signal(SIGPIPE,SIG_IGN); + + /*Retrieve protocol number from /etc/protocols file */ + protocol=getprotobyname("tcp"); + if (protocol == NULL) { + syslog(LOG_ERR, "cannot map \"tcp\" to protocol number"); + exit (1); + } + + bzero((char*) &addr_server, sizeof(addr_server)); + addr_server.sin_family = AF_INET; + if (inet_pton(AF_INET, argv[1], &addr_server.sin_addr.s_addr) <= 0) + syslog (LOG_ERR, "error inet_pton"); + + addr_server.sin_port = htons(atol(argv[2])); + + if ((sockfd = socket(AF_INET, SOCK_STREAM, 0)) < 0) { + syslog (LOG_ERR, "socket creation failed"); + exit(1); + } + + if (bind(sockfd, (struct sockaddr *) &addr_server, sizeof(addr_server)) < 0) { + syslog (LOG_ERR, "socket bind failed"); + exit(1); + } + + if (listen (sockfd, atoi(argv[3])) < 0 ) { + syslog (LOG_ERR, "socket listen failed"); + exit(1); + } + + while(1) { + clilen = sizeof(addr_client); + if ((sockclient = accept (sockfd, (struct sockaddr *) &addr_client, &clilen)) < 0) { + syslog (LOG_ERR, "socket accept failed"); + exit(1); + } + if (pthread_create (&idThread, NULL, serverThread, (void *)sockclient) != 0 ) { + syslog (LOG_ERR, "thread creation failed"); + } + } +} + + +int daemonize(const char *pname, int facility, int option) { + int fd; + + if ( (fd = open( "/dev/tty", O_RDWR, 0) ) == -1) { + /*We already have no tty control*/ + close(fd); + return 0; + } + + /*Sending messages to log*/ + openlog(pname, option, facility); + + ioctl(fd, TIOCNOTTY, (caddr_t)0); + close(fd); + + if((fd = open( "/dev/null", O_RDWR, 0) ) == -1) { + close(fd); + return 0; + } + dup2(fd,0); + dup2(fd,1); + dup2(fd,2); + close(fd); + + return 0; +} + +void *serverThread (void * arg) { + int sockclient; + int n; + char buf[512]; + + sockclient = (int) arg; + pthread_detach(pthread_self()); + + n = recv(sockclient, buf, sizeof(buf), 0); + if(n > 0){ + buf[n] = '\0'; + fork_system(sockclient, buf); + } + + close(sockclient); + + pthread_exit(0); +} + + +int fork_system(int socket, char *command) { + int pid; + int pfdOUT[2]; + int pfdERR[2]; + char buf[2000]; + char string[100]; + struct pollfd polls[2]; + int returnstatus; + int n; + + sem_t * semaphore; + /*Required variables in order to share memory between processes*/ + key_t keyvalue; + int idreturnst; + int *returnst; + + if (pipe(pfdOUT) == -1) { + syslog (LOG_ERR, "pipe for stdout failed"); + close(pfdOUT[0]); + close(pfdOUT[1]); + return -1; + } + if (pipe(pfdERR) == -1) { + syslog (LOG_ERR, "pipe for stderr failed"); + close(pfdOUT[0]); + close(pfdOUT[1]); + close(pfdERR[0]); + close(pfdERR[1]); + return -1; + } + + if ((semaphore = sem_open("javaforksem", O_CREAT, 0644, 1)) == SEM_FAILED) { + syslog (LOG_ERR, "semaphore open failed"); + close(pfdOUT[0]); + close(pfdOUT[1]); + close(pfdERR[0]); + close(pfdERR[1]); + if (sem_close(semaphore) <0 ) { + syslog (LOG_ERR, "semaphore open failed and close failed"); + } + if (sem_unlink("javaforksem") < 0) { + syslog (LOG_ERR, "semaphore open failed and unlink failed"); + } + return -1; + } + + if (sem_init(semaphore, 1, 1) < 0) { + syslog (LOG_ERR, "semaphore initialization failed"); + close(pfdOUT[0]); + close(pfdOUT[1]); + close(pfdERR[0]); + close(pfdERR[1]); + if (sem_close(semaphore) <0 ) { + syslog (LOG_ERR, "semaphore open failed and close failed"); + } + if (sem_unlink("javaforksem") < 0) { + syslog (LOG_ERR, "semaphore open failed and unlink failed"); + } + return -1; + } + + if (sem_wait(semaphore) < 0) { + syslog (LOG_ERR, "semaphore wait failed"); + } + + /*Allocate shared memory*/ + keyvalue=ftok("/bin/ls", SHAREMEMKEY); /*the /bin/ls must exist otherwise this does not work... */ + if (keyvalue == -1) { + syslog (LOG_ERR, "ftok failed"); + /*TODO: Close again pipes and semaphore.*/ + return -1; + } + /*Attach shared memory*/ + idreturnst=shmget(keyvalue,sizeof(int), 0660 | IPC_CREAT); + if (idreturnst == -1) { + syslog (LOG_ERR, "shmget failed"); + /*TODO: Close again pipes and semaphore.*/ + return -1; + } + returnst = (int *)shmat(idreturnst, (void *)0, 0); + if ((*returnst)== -1) { + syslog (LOG_ERR, "shmat failed"); + /*TODO: Close again pipes and semaphore.*/ + return -1; + } + + /*By default*/ + (*returnst) = 0; + + if ((pid=fork()) == -1) { + perror("fork: "); + close(pfdOUT[0]); + close(pfdOUT[1]); + close(pfdERR[0]); + close(pfdERR[1]); + if (sem_close(semaphore) <0 ) { + syslog (LOG_ERR, "semaphore open failed and close failed"); + } + if (sem_unlink("javaforksem") < 0) { + syslog (LOG_ERR, "semaphore open failed and unlink failed"); + } + return -1; + } + else { + /*Child process*/ + if (pid == 0) { + if (dup2(pfdOUT[1],1) < 0) { + syslog (LOG_ERR, "child: dup2 pfdOUT failed"); + exit(-1); + } + if (dup2(pfdERR[1],2) < 0) { + syslog (LOG_ERR, "child: dup2 pfdERR failed"); + exit(-1); + } + if (sem_wait(semaphore) < 0) { + syslog (LOG_ERR, "child: semaphore wait failed"); + } + returnstatus=system(command); + if (WIFEXITED(returnstatus) == 1) { + (*returnst) = WEXITSTATUS(returnstatus); + } + else { + (*returnst) = -1; + } + exit(0); + } + else { + /*Parent process*/ + polls[0].fd=pfdOUT[0]; + polls[1].fd=pfdERR[0]; + polls[0].events=POLLIN; + polls[1].events=POLLIN; + sprintf(string,""); + send(socket,string,strlen(string),0); + sprintf(string,""); + send(socket,string,strlen(string),0); + /*The child will be woken up*/ + if (sem_post(semaphore) < 0 ) { + syslog (LOG_ERR, "error waiking up child process"); + /*TODO: exit closing the descriptors*/ + } + while(1){ + if(poll(polls,2,100)){ + if(polls[0].revents&&POLLIN) { + bzero(buf,2000); + n=read(pfdOUT[0],buf,1990); + sprintf(string,""); + send(socket,string,strlen(string),0); + } + if(polls[1].revents&&POLLIN) { + bzero(buf,2000); + n=read(pfdERR[0],buf,1990); + sprintf(string,""); + send(socket,string,strlen(string),0); + } + if(!polls[0].revents&&POLLIN && !polls[1].revents&&POLLIN) { + syslog (LOG_ERR, "Error polling pipes"); + break; + } + } + else { + /*When timeout*/ + if(waitpid(pid,NULL,WNOHANG)) { + /*Child is dead, we can finish the connection*/ + break; + } + /*The child process is not dead, keep polling more data from stdout or stderr streams*/ + } + } + + /*We reach this code when the child process is dead or because of an error polling pipes*/ + /*In the second case the result stored in *returnst could be wrong, anyway there was*/ + /*an error so, the result is unpredictable.*/ + /*TODO: if error while polling pipes do not reach this code an exit with -1*/ + sprintf(string,"", (*returnst)); + send(socket,string,strlen(string),0); + sprintf(string,""); + send(socket,string,strlen(string),0); + + close(pfdOUT[0]); + close(pfdOUT[1]); + close(pfdERR[0]); + close(pfdERR[1]); + if (sem_close(semaphore) <0 ) { + syslog (LOG_ERR, "semaphore close failed"); + } + if (sem_unlink("javaforksem") < 0) { + syslog (LOG_ERR, "semaphore unlink failed"); + } + + shmdt ((int *)returnst); + shmctl (idreturnst, IPC_RMID, (struct shmid_ds *)NULL); + } + } + + return 0; +} diff --git a/JavaFork/Daemon/javafork.h b/JavaFork/Daemon/javafork.h new file mode 100644 index 0000000..d6321a0 --- /dev/null +++ b/JavaFork/Daemon/javafork.h @@ -0,0 +1,7 @@ +/*System V IPC key*/ +#define SHAREMEMKEY 1 + +void *serverThread (void *arg); +int daemonize(const char *pname, int facility, int option); +int main_child (int argc, char *argv[]); +int fork_system(int socket, char *command); diff --git a/JavaFork/JavaExample/javafork-example/pom.xml b/JavaFork/JavaExample/javafork-example/pom.xml new file mode 100644 index 0000000..f24711c --- /dev/null +++ b/JavaFork/JavaExample/javafork-example/pom.xml @@ -0,0 +1,22 @@ + + + + + 4.0.0 + + javafork + de.fork.java + 2.0-SNAPSHOT + + + javafork-example + javafork-example + http://gumartinm.name + + + + + diff --git a/JavaFork/JavaExample/javafork-example/src/main/java/de/fork/java/ForkDaemon.java b/JavaFork/JavaExample/javafork-example/src/main/java/de/fork/java/ForkDaemon.java new file mode 100644 index 0000000..074318f --- /dev/null +++ b/JavaFork/JavaExample/javafork-example/src/main/java/de/fork/java/ForkDaemon.java @@ -0,0 +1,166 @@ +package de.fork.java; + +import java.io.IOException; +import java.io.PrintWriter; +import java.net.InetAddress; +import java.net.Socket; +import java.net.UnknownHostException; +import javax.xml.parsers.FactoryConfigurationError; +import javax.xml.parsers.ParserConfigurationException; +import javax.xml.parsers.SAXParser; +import javax.xml.parsers.SAXParserFactory; +import org.xml.sax.SAXException; + +/** + *

+ * With this class we can run processes using the intended daemon which is + * waiting for TCP connections in a specified port. + *

+ *

+ * Receiving the results in a XML format from the daemon where we can find three + * kinds of different fields: error, out and ret. Every field is related to the + * stderr, stdout and return code respectively.
+ *

+ *

+ *

+ * Example, stream received from daemon:
+ * {@code
+ * 
+ * }
+ * 
+ *

+ *

+ * This class has to process the above stream and it offers two methods wich can be used + * to retrieve the stderr and stdout in a right way without having to know about the XML stream + * received from the daemon. The user does not have to know about how the daemon sends the data, + * he or she will work directly with the strings related to each stream. Those methods + * are {@link ForkDaemon#getStdout()} and {@link ForkDaemon#getStderr()} The return code from the command + * executed by the daemon can be retrieved as a return parameter from the method + * {@link ForkDaemon#exec(String, String, int)} + *

+ *

+ * Instances of this class are mutable. To use them concurrently, clients must surround each + * method invocation (or invocation sequence) with external synchronization of the clients choosing. + *

+ */ +public class ForkDaemon { + private final ForkParser handler; + + + /** + * Simple constructor. + * Nothing special here. + * + */ + public ForkDaemon () { + handler = new ForkParser(); + } + + + /** + * This method sends commands to the daemon. + *
+ * It uses a TCP connection in order to send commands to the daemon and receive + * the results related to that command. + *
+ * The mehtod retrieves the stdout, stderr and the return code of that command. + * + *

The host name can either be a machine name, such as + * "java.sun.com", or a textual representation of its + * IP address. If a literal IP address is supplied, only the + * validity of the address format is checked. + *

+ *

For host specified in literal IPv6 address, + * either the form defined in RFC 2732 or the literal IPv6 address + * format defined in RFC 2373 is accepted. IPv6 scoped addresses are also + * supported. See here for a description of IPv6 + * scoped addresses. + *

+ * @param command the command to be executed by the daemon. + * @param host the specified host. + * @param port the TCP port where the daemon accepts connections. + * + * @return the executed command's return code. + * + * @throws UnknownHostException if no IP address for the + * host could be found, or if a scope_id was specified + * @throws SecurityException if a security manager exists + * and its checkConnect method doesn't allow the operation + * @throws IOException if an I/O error occurs when creating the socket. + * @throws SAXException + * @throws FactoryConfigurationError if the implementation is not available or cannot be instantiated. + * @throws SAXException If any SAX errors occur during processing. + * @throws ParserConfigurationException + */ + public int exec(final String command, String host, int port) + throws UnknownHostException, IOException, SAXException, ParserConfigurationException { + final SAXParserFactory spf = SAXParserFactory.newInstance(); + final SAXParser saxParser = spf.newSAXParser(); + PrintWriter out = null; + + final Socket socket = new Socket(InetAddress.getByName(host), port); + try { + out = new PrintWriter(socket.getOutputStream(), true); + out.println(command); + saxParser.parse(socket.getInputStream(), handler); + } + finally { + if (out != null) { + out.close(); + } + socket.close(); + } + + //Just for testing the parser by using a file instead of a TCP connection. + //InputSource input = new InputSource(new FileReader("/tmp/xmlfromdaemon.xml")); + //saxParser.parse(input, handler); + + return new Integer(handler.getReturnValue()).intValue(); + } + + + /** + * Retrieve the standard output. + * + * @see {@link ForkDaemon#getStderr()} + * @return stdout + */ + public String getStdout() { + return handler.getStdout(); + } + + + /** + *

+ * Retrieve the standard error. + *

+ *

+ *

+	 * Example, stream received from daemon:
+	 * {@code
+	 * 
+	 * }
+	 * 
+ *

+ *

+ *

+	 * From that example with this method we are going to obtain this return parameter:
+	 * {@code
+	 * ls: no se puede acceder a bbb: No existe el fichero o el directorio
+	 * ls: no se puede acceder a aaa: No existe el fichero o el directorio
+	 * ls: no se puede acceder a dddd: No existe el fichero o el directorio
+	 * }
+	 * 
+ *

+ * @return stderr + */ + public String getStderr() { + return handler.getStderr(); + } +} \ No newline at end of file diff --git a/JavaFork/JavaExample/javafork-example/src/main/java/de/fork/java/ForkParser.java b/JavaFork/JavaExample/javafork-example/src/main/java/de/fork/java/ForkParser.java new file mode 100644 index 0000000..c20ba15 --- /dev/null +++ b/JavaFork/JavaExample/javafork-example/src/main/java/de/fork/java/ForkParser.java @@ -0,0 +1,141 @@ +package de.fork.java; + +import org.apache.log4j.Logger; +import org.xml.sax.Attributes; +import org.xml.sax.SAXException; +import org.xml.sax.SAXParseException; +import org.xml.sax.ext.DefaultHandler2; + +/** + *

+ * Class intended to parse the XML stream received from the daemon which is + * waiting to run commands. These commands are sent by the method + * {@link es.dia.pos.n2a.util.os.unix.ForkDaemon#exec(String, String, int)} + *

+ *

+ * After processing one command the daemon sends a XML stream with the stderr, + * stdout and return status of that command. With this class we extract those values + * and we can retrieve them using the methods {@link #getStderr() }, {@link #getStdout()} + * and {@link #getReturnValue()} + *

+ *

+ *

+ * Example, stream received from daemon:
+ * {@code
+ * 
+ * }
+ * 
+ *

+ */ +public class ForkParser extends DefaultHandler2{ + private static final Logger logger = Logger.getLogger(ForkParser.class); + private StringBuffer accumulator = new StringBuffer(); + private String stderr = new String(); + private String stdout = new String(); + private String returnCode = new String(); + + + @Override + public void endElement (String uri, String localName, String qName) { + if (qName.equals("error")) { + // After , we've got the stderror + stderr = stderr + accumulator.toString(); + } else if (qName.equals("out")) { + // After , we've got the stdout + stdout = stdout + accumulator.toString(); + } else if (qName.equals("ret")) { + returnCode = returnCode + accumulator.toString(); + } + } + + + @Override + public void endDocument () throws SAXException + { + if (stderr.length() != 0) { + String lastStderr = stderr.replaceFirst("\\\n$", ""); + stderr = lastStderr; + } + else { + stderr = null; + } + if (stdout.length() != 0) { + String lastStdout = stdout.replaceFirst("\\\n$", ""); + stdout = lastStdout; + } + else { + stdout = null; + } + } + + /** + * Retrieve the standard error. + * + *
+	 * From the above example with this method we are going to obtain this return parameter:
+	 * {@code
+	 * ls: no se puede acceder a bbb: No existe el fichero o el directorio
+	 * ls: no se puede acceder a aaa: No existe el fichero o el directorio
+	 * ls: no se puede acceder a dddd: No existe el fichero o el directorio
+	 * }
+	 * 
+ * + * @return stderr + */ + public String getStderr() { + return stderr; + + } + + + /** + * Retrieve the standard output. + * + * @see {@link ForkParser#getStderr()} + * @return stdout + */ + public String getStdout() { + return stdout; + } + + + /** + * Retrieve the return code from the executed command. + * + * @return return status, usually 0 means the command went OK. + */ + public String getReturnValue() { + return returnCode; + } + + + @Override + public void startElement (String uri, String localName, String qName, Attributes attributes) { + accumulator.setLength(0); + } + + + @Override + public void characters(char[] buffer, int start, int length) { + accumulator.append(buffer, start, length); + } + + @Override + public void warning(SAXParseException exception) { + logger.error("WARNING line:" + exception.getLineNumber(), exception); + } + + @Override + public void error(SAXParseException exception) { + logger.error("ERROR line:" + exception.getLineNumber(), exception); + } + + @Override + public void fatalError(SAXParseException exception) throws SAXException { + logger.error("FATAL ERROR line:" + exception.getLineNumber(), exception); + throw (exception); + } +} \ No newline at end of file diff --git a/JavaFork/JavaExample/javafork-example/src/main/java/de/fork/java/LauncherProcesses.java b/JavaFork/JavaExample/javafork-example/src/main/java/de/fork/java/LauncherProcesses.java new file mode 100644 index 0000000..0f93fe2 --- /dev/null +++ b/JavaFork/JavaExample/javafork-example/src/main/java/de/fork/java/LauncherProcesses.java @@ -0,0 +1,275 @@ +package de.fork.java; + +import java.io.ByteArrayInputStream; +import java.io.IOException; +import java.io.InputStream; +import java.io.PrintStream; +import java.net.UnknownHostException; +import javax.xml.parsers.ParserConfigurationException; +import org.apache.log4j.Logger; +import org.xml.sax.SAXException; + + +public class LauncherProcesses { + + private static final Logger logger = Logger.getLogger(LauncherProcesses.class); + + // Exit process status + private static final int STATUS_ERR = -1; + + private static final int DEFAULT_PORT = 5193; + private static final String DEFAULT_HOST = "127.0.0.1"; + + /** + * Run a process. + * + * @param command system command to be executed. + * + * @return return code. + */ + public static int exec(final String command) throws IOException, InterruptedException { + + return exec(command, null, null); + } + + /** + * Run a process. + * + * @param command system command to execute. + * @param standarOutPut if not null, the standard output is redirected to this parameter. + * + * @return return code. + */ + public static int exec(final String command, final PrintStream standarOutPut) throws IOException, InterruptedException { + + return exec(command, standarOutPut, null); + } + + + /** + * Run a process. + * + * @param command system command to be executed. + * @param standarOutPut if not null, the standard output is redirected to this parameter. + * @param errorOutPut if not null, the error output is redirected to this parameter. + * + * @return return code from the executed system command. + */ + public static int exec(final String command, final PrintStream standarOutPut, final PrintStream errorOutPut) throws IOException, InterruptedException { + + return exec(command, standarOutPut, errorOutPut, DEFAULT_HOST, DEFAULT_PORT); + } + + /** + * Run a process. + * + * @param command system command to be executed. + * @param aLogger send the information to log. + */ + public static int exec(final String command, final Logger aLogger) throws IOException, InterruptedException { + + //calling private method to handle logger input/ouput in a common method + return execHandlingLogger(command, aLogger, DEFAULT_HOST, DEFAULT_PORT); + } + + + /** + * @param commandAndArguments String array containing system command and its + * arguments to be executed.
+ * For example: + *
+	 * commandAndArguments[0]="ls";
+	 * commandAndArguments[1]="-lr";
+	 * 
+ * @param aLogger + * + * @return return code from the executed system command. + * + * @throws IOException + * @throws InterruptedException + */ + public static int exec(final String[] commandAndArguments, final Logger aLogger) throws IOException, InterruptedException { + String wholeCommand=""; + + for(String argument : commandAndArguments) { + wholeCommand = wholeCommand + " " + argument; + } + + //calling private method to handle logger input/ouput in a common method + return execHandlingLogger(wholeCommand, aLogger, DEFAULT_HOST, DEFAULT_PORT); + } + + + /** + * + * @param command system command to be executed. + * @param standarOutPut the stdout stream from that command as a PrintStream + * @param errorOutPut the stderr stream from that command as a PrintStream + * @param host the specified host. + * @param port the TCP port where the daemon accepts connections. + * + *

The host name can either be a machine name, such as + * "java.sun.com", or a textual representation of its + * IP address. If a literal IP address is supplied, only the + * validity of the address format is checked. + *

+ *

For host specified in literal IPv6 address, + * either the form defined in RFC 2732 or the literal IPv6 address + * format defined in RFC 2373 is accepted. IPv6 scoped addresses are also + * supported. See here for a description of IPv6 + * scoped addresses. + *

+ * + * @return the executed command's return code. + * + * @throws UnknownHostException + * @throws IOException + */ + public static int exec(final String command, final PrintStream standarOutPut, + final PrintStream errorOutPut, final String host, int port) throws IOException { + int exitStatus = LauncherProcesses.STATUS_ERR; + + ForkDaemon process = new ForkDaemon(); + try { + exitStatus = process.exec(command, host, port); + } catch (SAXException e) { + // This is not a crazy thing, we are trying to insert this new method without + // breaking the old methods which did not throw SAXException or ParserConfigurationException + //[§EJ Item 61] Do not blame me. + throw new IOException(e); + } catch (ParserConfigurationException e) { + // This is not a crazy thing, we are trying to insert this new method without + // breaking the old methods which did not throw SAXException or ParserConfigurationException + //[§EJ Item 61] Do not blame me. + throw new IOException(e); + } + + if (standarOutPut != null) { + if (process.getStdout() != null) { + standarOutPut.println(process.getStdout()); + } + } + + if (errorOutPut != null) { + if (process.getStderr() != null) { + errorOutPut.println(process.getStderr()); + } + } + + return exitStatus; + } + + + /** + * + * @param command system command to be executed. + * @param aLogger + * @param host the specified host. + * @param port the TCP port where the daemon accepts connections. + * + * @return the executed command's return code. + * + * @throws IOException + * @throws InterruptedException + */ + private static int execHandlingLogger(final String command, final Logger aLogger, + final String host, int port) throws IOException, InterruptedException { + int exitStatus = LauncherProcesses.STATUS_ERR; + + ForkDaemon process = new ForkDaemon(); + try { + exitStatus = process.exec(command, host, port); + } catch (SAXException e) { + // This is not a crazy thing, we are trying to insert this new method without + // breaking the old methods which did not throw SAXException or ParserConfigurationException + // Do not blame me. + throw new IOException(e); + } catch (ParserConfigurationException e) { + // This is not a crazy thing, we are trying to insert this new method without + // breaking the old methods which did not throw SAXException or ParserConfigurationException + // Do not blame me. + throw new IOException(e); + } + + if (process.getStdout() != null) { + aLogger.info(process.getStdout()); + } + if (process.getStderr() != null) { + aLogger.error(process.getStderr()); + } + + return exitStatus; + } + + + /** + * @param command command and its arguments to be executed.
+ * For example: + *
+	 * commandAndArguments[0]="ls";
+	 * commandAndArguments[1]="-lr";
+	 * 
+ * @param aLogger send information to log + * + * @return the executed command's return code. + * + * @throws IOException + * @throws InterruptedException + */ + public static InputStream execStream (final String [] command, final Logger aLogger) + throws IOException, InterruptedException { + int exitStatus = LauncherProcesses.STATUS_ERR; + + InputStream stdInput = null; + + String wholeCommand=""; + for(String argument : command) { + wholeCommand = wholeCommand + " " + argument; + } + + ForkDaemon process = new ForkDaemon(); + try { + exitStatus = process.exec(wholeCommand, DEFAULT_HOST, DEFAULT_PORT); + } catch (SAXException e) { + // This is not a crazy thing, we are trying to insert this new method without + // breaking the old methods which did not throw SAXException or ParserConfigurationException + throw new IOException(e); + } catch (ParserConfigurationException e) { + // This is not a crazy thing, we are trying to insert this new method without + // breaking the old methods which did not throw SAXException or ParserConfigurationException + throw new IOException(e); + } + + if(exitStatus == 0) { + stdInput = new ByteArrayInputStream(process.getStdout().getBytes("UTF-8")); + } + else { + aLogger.error(process.getStderr()); + } + + + return stdInput; + } + + /** + *

The command is lunched from location + *

  • #>cd location
  • + *
  • #location> command
  • + * + * @param command the command to be executed by the daemon. + * @param location + * + * @return the executed command's return code.
    + * Usually 0 if execution is OK, otherwise !=0 + * + * @throws IOException + * @throws InterruptedException + */ + public static int execInLocation (final String command, final String location) throws IOException, InterruptedException { + int exitStatus = LauncherProcesses.STATUS_ERR; + final String wholeCommand = "cd " + location + " && " + command; + + exitStatus = exec(wholeCommand, null, null, DEFAULT_HOST, DEFAULT_PORT); + return exitStatus; + } +} \ No newline at end of file diff --git a/JavaFork/JavaExample/javafork-example/src/main/java/de/fork/java/MainJavaFork.java b/JavaFork/JavaExample/javafork-example/src/main/java/de/fork/java/MainJavaFork.java new file mode 100644 index 0000000..bed6b6a --- /dev/null +++ b/JavaFork/JavaExample/javafork-example/src/main/java/de/fork/java/MainJavaFork.java @@ -0,0 +1,35 @@ +package de.fork.java; + +import java.io.ByteArrayOutputStream; +import java.io.FileNotFoundException; +import java.io.IOException; +import java.io.PrintStream; +import javax.xml.parsers.ParserConfigurationException; +import org.xml.sax.SAXException; + + +public class MainJavaFork { + + /** + * @param args + * @throws SAXException + * @throws ParserConfigurationException + * @throws FileNotFoundException + */ + public static void main(String[] args) + throws ParserConfigurationException, SAXException, FileNotFoundException, IOException { + + final ByteArrayOutputStream stdoutByteOut = new ByteArrayOutputStream(); + final PrintStream stdout = new PrintStream(stdoutByteOut); + final String command = "ls -lah; ls -lah bbb aaa ccc; ls -lah"; + final ByteArrayOutputStream stderrByteOut = new ByteArrayOutputStream(); + final PrintStream stderr = new PrintStream(stderrByteOut); + int result; + + result = LauncherProcesses.exec(command,stdout, stderr, "127.0.0.1", 5193); + System.out.println(result); + System.out.println("Stdout: " + stdoutByteOut.toString()); + System.out.println("Stderr: " + stderrByteOut.toString()); + } + +} \ No newline at end of file diff --git a/JavaFork/JavaExample/pom.xml b/JavaFork/JavaExample/pom.xml new file mode 100644 index 0000000..aaf5867 --- /dev/null +++ b/JavaFork/JavaExample/pom.xml @@ -0,0 +1,663 @@ + + + + 4.0.0 + de.fork.java + javafork + 2.0-SNAPSHOT + javafork + http://www.gumartinm.name + Java fork with Linux daemon + + MyOrganization + http://www.gumartinm.name + + pom + + trac + http://gumartinm.name/trac + + + jenkins + http://gumartinm.name//jenkins/ + + + scm:svn:http://gumartinm.name + http://gumartinm.name + + + + com.sun.jdmk + jmxtools + 1.2.1 + + + javax.activation + activation + 1.1 + + + log4j + log4j + 1.2.15 + + + com.sun.jdmk + jmxtools + + + com.sun.jmx + jmxri + + + javax.mail + mail + + + javax.jms + jms + + + + + junit + junit + 4.4 + test + + + + + + c3p0 + c3p0 + 0.9.1.2 + + + cglib + cglib-nodep + 2.1_3 + + + commons-collections + commons-collections + 3.2.1 + + + commons-configuration + commons-configuration + 1.6 + + + commons-dbcp + commons-dbcp + 1.2.2 + + + commons-io + commons-io + 1.4 + + + commons-lang + commons-lang + 2.4 + + + commons-logging + commons-logging + 1.1.1 + + + commons-net + commons-net + 2.0 + + + commons-pool + commons-pool + 1.3 + + + com.h2database + h2 + 1.2.130 + + + dom4j + dom4j + 1.6.1 + + + xml-apis + xml-apis + + + + + hsqldb + hsqldb + 1.8.0.7 + + + javatar + javatar + 2.5 + + + jpos + jpos + 1.12.2 + provided + + + jpos + jpos-controls + 1.12.2 + provided + + + org.python + jython + 2.5.2b2 + + + urbanophile + java-getopt + 1.0.13 + + + mysql + mysql-connector-java + 5.1.6 + + + org.apache.ibatis + ibatis-sqlmap + 2.3.4.726 + + + org.apache.mina + mina-core + 2.0.0-M6 + + + org.aspectj + aspectjrt + 1.6.5 + + + org.aspectj + aspectjweaver + 1.6.5 + + + org.dbunit + dbunit + 2.4.4 + test + + + org.eclipse.jetty + jetty-continuation + 7.0.0.v20091005 + + + org.eclipse.jetty + jetty-http + 7.0.0.v20091005 + + + org.eclipse.jetty + jetty-io + 7.0.0.v20091005 + + + org.eclipse.jetty + jetty-security + 7.0.0.v20091005 + + + org.eclipse.jetty + jetty-server + 7.0.0.v20091005 + + + org.eclipse.jetty + jetty-servlet + 7.0.0.v20091005 + + + org.eclipse.jetty + jetty-webapp + 7.0.0.v20091005 + + + org.eclipse.jetty + jetty-util + 7.0.0.v20091005 + + + org.eclipse.jetty + jetty-xml + 7.0.0.v20091005 + + + org.slf4j + slf4j-api + 1.5.2 + + + org.slf4j + slf4j-log4j12 + 1.5.2 + + + log4j + log4j + + + + + org.springframework + spring-aop + ${spring.version} + + + org.springframework + spring-beans + ${spring.version} + + + org.springframework + spring-core + ${spring.version} + + + org.springframework + spring-context + ${spring.version} + + + org.springframework + spring-jdbc + ${spring.version} + + + org.springframework + spring-tx + ${spring.version} + + + org.springframework + spring-web + ${spring.version} + + + org.springframework + spring-webmvc + ${spring.version} + + + org.springframework + spring-context-support + ${spring.version} + + + org.springframework + spring-test + ${spring.version} + test + + + org.springframework.batch + spring-batch-test + 2.0.4.RELEASE + + + org.springframework.batch + spring-batch-core + 2.0.4.RELEASE + + + org.springframework.batch + spring-batch-infrastructure + 2.0.4.RELEASE + + + org.springframework + spring-orm + ${spring.version} + + + net.sf.ehcache + ehcache + 1.6.2 + + + org.springmodules + spring-modules-cache + 0.9 + + + p6spy + p6spy + 1.3 + + + javax.transaction + jta + 1.0.1B + + + javax.servlet + servlet-api + 2.5 + + + com.caucho + hessian + 3.1.6 + + + org.codehaus.jettison + jettison + 1.0 + + + com.thoughtworks.xstream + xstream + 1.3 + + + org.ini4j + ini4j + 0.5.1 + + + org.easymock + easymock + 2.4 + test + + + org.easymock + easymockclassextension + 2.4 + test + + + + org.apache.commons + commons-compress + 1.0 + + + org.apache.commons + commons-math + 2.0 + + + dtgjpos_forms + dtgjpos_forms + 1.4.12 + provided + + + org.codehaus.castor + castor-xml + 1.3.1 + + + org.apache.xmlbeans + xmlbeans + 2.5.0 + + + org.apache.velocity.tools + velocity-tools-generic + 1.4 + + + org.apache.velocity + velocity + 1.6.2 + + + org.tmatesoft.svnkit + svnkit + 1.3.1 + + + + + javafork-example + + + + + org.apache.maven.plugins + maven-compiler-plugin + 2.0.2 + + 1.6 + 1.6 + ${project.build.sourceEncoding} + + + + + org.apache.maven.plugins + maven-javadoc-plugin + 2.6 + + + org.apache.maven.plugins + maven-surefire-plugin + 2.4.2 + + true + + + + org.codehaus.mojo + jdepend-maven-plugin + 2.0-beta-2 + + + org.apache.maven.plugins + maven-jar-plugin + 2.3.1 + + + + ${project.description} + ${project.version} + ${project.organization.name} + ${project.description} + ${project.version} + ${project.organization.name} + ${BUILD_TAG} + ${BUILD_ID} + ${BUILD_NUMBER} + ${prefix.committedRevision} + ${prefix.repository} + ${prefix.path} + + + + + + com.google.code.maven-svn-revision-number-plugin + maven-svn-revision-number-plugin + 1.6 + + + + revision + + + + + + + prefix + + + + + + + + + + releases + releases + http://noserver/artifactory/custom-annotations-libs-releases-local + + + snapshots-releases + snapshots-releases + http://noserver/artifactory/custom-annotations-libs-snapshots-local + + + noserver + file:///mnt/sdb1/data/downloads/jenkins/ + + + + + + + org.apache.maven.plugins + maven-project-info-reports-plugin + 2.1.2 + + + + index + dependencies + cim + issue-tracking + scm + summary + project-team + + + + + + org.apache.maven.plugins + maven-javadoc-plugin + 2.6.1 + + + html + + MYPROJECT API for ${project.name} ${project.version} + MYPROJECT API for ${project.name} ${project.version} + + + javadoc + aggregate + + + + + + org.codehaus.mojo + taglist-maven-plugin + 2.3 + + + TODO + @todo + FIXME + XXX + + + + + org.apache.maven.plugins + maven-surefire-report-plugin + 2.4.3 + + + integration-tests + + report-only + + + failsafe-report + + target/failsafe-reports + + + + + junit-tests + + report-only + + + surefire-report + + target/surefire-reports + + + + + + + + + UTF-8 + 2.5.6 + + + + + + + + -- 2.1.4