I want to know if there is a way I can write a program .jar
, and write a C / C ++ program that calls the JVM to execute the .jar
file. It's possible? If so, can you give me an example code or an instruction how to do this?
I want to know if there is a way I can write a program .jar
, and write a C / C ++ program that calls the JVM to execute the .jar
file. It's possible? If so, can you give me an example code or an instruction how to do this?
The most standard solution would be to use the system()
function of the default library stdlib.h
.
BUT , from the point of view of *nix
systems, the use of system()
should be avoided:
1 - The call of the
system()
function executes the command interpreter (shell), which makes it much slower than calling afork()
followed byexec()
;2 - This is a potential security risk if you pass as a parameter an untrusted source string;
3 - Can not be used asynchronously, ie the system is blocked waiting for the child process to return;
4 - Double
fork()
andexec()
give us much more control before and between your calls.
The following example exemplifies running .jar
using fork()
, exec()
, and waitpid()
calls on a Linux
system.
Note that the child process prepares the environment by redirecting the output streams ( exec()
and STDERR
) to two output files: STDOUT
and stderr.txt
.
The parent process stream is purposely blocked with the stdout.txt
call, but could be "working" on another task:
#include <stdio.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/types.h>
#include <sys/stat.h>
#define MAX_CMD_TAM (1024)
int main( int argc, char * argv[] )
{
char cmd[ MAX_CMD_TAM + 1 ] = {0};
/* Verifica se o nome de arquivo .jar foi passado como parametro na linha de comando */
if( argc != 2 )
{
printf("Erro de sintaxe: %s [ARQUIVO_JAR]\n", argv[0] );
return 1;
}
/* Processo pai cria uma copia de si mesmo (cria um processo filho) */
pid_t child = fork();
/* Monta a linha de comando que sera executada */
snprintf( cmd, MAX_CMD_TAM, "java -jar %s", argv[1] );
if( child == 0 ) /* Fluxo do processo filho */
{
/* Abre/Cria arquivos para substituirem as saidss padroes: STDOUT e STDERR */
int fdout = open( "stdout.txt", O_RDWR | O_CREAT | O_APPEND, S_IRUSR | S_IWUSR );
int fderr = open( "stderr.txt", O_RDWR | O_CREAT | O_APPEND, S_IRUSR | S_IWUSR );
/* Redireciona o STDOUT e STDERR para os arquivos correspondentes */
dup2( fdout, STDOUT_FILENO );
dup2( fderr, STDERR_FILENO );
/* Depois de duplicados, os descritores dos arquivos nao sao mais necessarios */
close(fdout);
close(fderr);
/* Executa comando */
execlp( cmd, NULL );
}
else if( child > 0 ) /* Fluxo do processo pai */
{
/* Processo pai aguarda a execucao do processo filho */
printf( "Executando Comando: \"%s\"\n", cmd );
printf( "Aguardando a execucao do processo filho...\n");
waitpid(child);
printf("Sucesso!\n");
}
else
{
printf("fork() falhou!\n");
return 1;
}
return 0;
}
/* fim-de-arquivo */
I hope I have helped!