xref: /netbsd-src/external/gpl2/gettext/dist/gettext-tools/gnulib-lib/javaversion.c (revision 95b39c65ca575fb40c6bb7083e0eb7ec28eabef1)
1946379e7Schristos /* Determine the Java version supported by javaexec.
2946379e7Schristos    Copyright (C) 2006 Free Software Foundation, Inc.
3946379e7Schristos    Written by Bruno Haible <bruno@clisp.org>, 2006.
4946379e7Schristos 
5946379e7Schristos    This program is free software; you can redistribute it and/or modify
6946379e7Schristos    it under the terms of the GNU General Public License as published by
7946379e7Schristos    the Free Software Foundation; either version 2, or (at your option)
8946379e7Schristos    any later version.
9946379e7Schristos 
10946379e7Schristos    This program is distributed in the hope that it will be useful,
11946379e7Schristos    but WITHOUT ANY WARRANTY; without even the implied warranty of
12946379e7Schristos    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13946379e7Schristos    GNU General Public License for more details.
14946379e7Schristos 
15946379e7Schristos    You should have received a copy of the GNU General Public License
16946379e7Schristos    along with this program; if not, write to the Free Software Foundation,
17946379e7Schristos    Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.  */
18946379e7Schristos 
19946379e7Schristos #include <config.h>
20946379e7Schristos 
21946379e7Schristos /* Specification.  */
22946379e7Schristos #include "javaversion.h"
23946379e7Schristos 
24946379e7Schristos #include <errno.h>
25946379e7Schristos #include <stdbool.h>
26946379e7Schristos #include <stdio.h>
27946379e7Schristos 
28946379e7Schristos #if ENABLE_RELOCATABLE
29946379e7Schristos # include "relocatable.h"
30946379e7Schristos #else
31946379e7Schristos # define relocate(pathname) (pathname)
32946379e7Schristos #endif
33946379e7Schristos 
34946379e7Schristos /* Get PKGDATADIR.  */
35*95b39c65Schristos #ifndef PKGDATADIR
36946379e7Schristos #include "configmake.h"
37*95b39c65Schristos #endif
38946379e7Schristos 
39946379e7Schristos #include "javaexec.h"
40946379e7Schristos #include "pipe.h"
41946379e7Schristos #include "wait-process.h"
42946379e7Schristos #include "error.h"
43946379e7Schristos #include "getline.h"
44946379e7Schristos #include "gettext.h"
45946379e7Schristos 
46946379e7Schristos #define _(str) gettext (str)
47946379e7Schristos 
48946379e7Schristos 
49946379e7Schristos struct locals
50946379e7Schristos {
51946379e7Schristos   /* OUT */
52946379e7Schristos   char *line;
53946379e7Schristos };
54946379e7Schristos 
55946379e7Schristos static bool
execute_and_read_line(const char * progname,const char * prog_path,char ** prog_argv,void * private_data)56946379e7Schristos execute_and_read_line (const char *progname,
57946379e7Schristos 		       const char *prog_path, char **prog_argv,
58946379e7Schristos 		       void *private_data)
59946379e7Schristos {
60946379e7Schristos   struct locals *l = (struct locals *) private_data;
61946379e7Schristos   pid_t child;
62946379e7Schristos   int fd[1];
63946379e7Schristos   FILE *fp;
64946379e7Schristos   char *line;
65946379e7Schristos   size_t linesize;
66946379e7Schristos   size_t linelen;
67946379e7Schristos   int exitstatus;
68946379e7Schristos 
69946379e7Schristos   /* Open a pipe to the JVM.  */
70946379e7Schristos   child = create_pipe_in (progname, prog_path, prog_argv, DEV_NULL, false,
71946379e7Schristos 			  true, false, fd);
72946379e7Schristos 
73946379e7Schristos   if (child == -1)
74946379e7Schristos     return false;
75946379e7Schristos 
76946379e7Schristos   /* Retrieve its result.  */
77946379e7Schristos   fp = fdopen (fd[0], "r");
78946379e7Schristos   if (fp == NULL)
79946379e7Schristos     {
80946379e7Schristos       error (0, errno, _("fdopen() failed"));
81946379e7Schristos       return false;
82946379e7Schristos     }
83946379e7Schristos 
84946379e7Schristos   line = NULL; linesize = 0;
85946379e7Schristos   linelen = getline (&line, &linesize, fp);
86946379e7Schristos   if (linelen == (size_t)(-1))
87946379e7Schristos     {
88946379e7Schristos       error (0, 0, _("%s subprocess I/O error"), progname);
89946379e7Schristos       return false;
90946379e7Schristos     }
91946379e7Schristos   if (linelen > 0 && line[linelen - 1] == '\n')
92946379e7Schristos     line[linelen - 1] = '\0';
93946379e7Schristos 
94946379e7Schristos   fclose (fp);
95946379e7Schristos 
96946379e7Schristos   /* Remove zombie process from process list, and retrieve exit status.  */
97946379e7Schristos   exitstatus = wait_subprocess (child, progname, true, false, true, false);
98946379e7Schristos   if (exitstatus != 0)
99946379e7Schristos     {
100946379e7Schristos       free (line);
101946379e7Schristos       return false;
102946379e7Schristos     }
103946379e7Schristos 
104946379e7Schristos   l->line = line;
105946379e7Schristos   return false;
106946379e7Schristos }
107946379e7Schristos 
108946379e7Schristos char *
javaexec_version(void)109946379e7Schristos javaexec_version (void)
110946379e7Schristos {
111946379e7Schristos   const char *class_name = "javaversion";
112946379e7Schristos   const char *pkgdatadir = relocate (PKGDATADIR);
113946379e7Schristos   const char *args[1];
114946379e7Schristos   struct locals locals;
115946379e7Schristos 
116946379e7Schristos   args[0] = NULL;
117946379e7Schristos   locals.line = NULL;
118946379e7Schristos   execute_java_class (class_name, &pkgdatadir, 1, true, NULL, args,
119946379e7Schristos 		      false, false, execute_and_read_line, &locals);
120946379e7Schristos 
121946379e7Schristos   return locals.line;
122946379e7Schristos }
123