]> git.ipfire.org Git - thirdparty/gettext.git/commitdiff
Executing C# programs in a portable way.
authorBruno Haible <bruno@clisp.org>
Thu, 8 Jan 2004 11:46:09 +0000 (11:46 +0000)
committerBruno Haible <bruno@clisp.org>
Tue, 23 Jun 2009 10:11:34 +0000 (12:11 +0200)
gettext-tools/lib/csharpexec.c [new file with mode: 0644]
gettext-tools/lib/csharpexec.h [new file with mode: 0644]
gettext-tools/lib/csharpexec.sh.in [new file with mode: 0644]
gettext-tools/m4/csharpexec.m4 [new file with mode: 0644]

diff --git a/gettext-tools/lib/csharpexec.c b/gettext-tools/lib/csharpexec.c
new file mode 100644 (file)
index 0000000..e4a2034
--- /dev/null
@@ -0,0 +1,198 @@
+/* Execute a C# program.
+   Copyright (C) 2003 Free Software Foundation, Inc.
+   Written by Bruno Haible <bruno@clisp.org>, 2003.
+
+   This program is free software; you can redistribute it and/or modify
+   it under the terms of the GNU General Public License as published by
+   the Free Software Foundation; either version 2, or (at your option)
+   any later version.
+
+   This program is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
+
+   You should have received a copy of the GNU General Public License
+   along with this program; if not, write to the Free Software Foundation,
+   Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
+
+#ifdef HAVE_CONFIG_H
+# include <config.h>
+#endif
+#include <alloca.h>
+
+/* Specification.  */
+#include "csharpexec.h"
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include "execute.h"
+#include "sh-quote.h"
+#include "xallocsa.h"
+#include "error.h"
+#include "gettext.h"
+
+/* Handling of MONO_PATH is just like Java CLASSPATH.  */
+#define CLASSPATHVAR "MONO_PATH"
+#define new_classpath new_monopath
+#define set_classpath set_monopath
+#define reset_classpath reset_monopath
+#include "classpath.h"
+#include "classpath.c"
+
+#define _(str) gettext (str)
+
+
+/* Survey of CIL interpreters.
+
+   Program    from
+
+   ilrun      pnet
+   mono       mono
+
+   With Mono, the MONO_PATH is a colon separated list of pathnames. (On
+   Windows: semicolon separated list of pathnames.)
+
+   We try the CIL interpreters in the following order:
+     1. "ilrun", because it is a completely free system.
+     2. "mono", because it is a partially free system but doesn't integrate
+        well with Unix.
+ */
+
+bool
+execute_csharp_program (const char *assembly_path,
+                       const char * const *libdirs,
+                       unsigned int libdirs_count,
+                       const char * const *args,
+                       bool verbose, bool quiet,
+                       execute_fn *executer, void *private_data)
+{
+  unsigned int nargs;
+
+  /* Count args.  */
+  {
+    const char * const *arg;
+
+    for (nargs = 0, arg = args; *arg != NULL; nargs++, arg++)
+     ;
+  }
+
+  {
+    static bool ilrun_tested;
+    static bool ilrun_present;
+
+    if (!ilrun_tested)
+      {
+       /* Test for presence of ilrun:
+          "ilrun --version >/dev/null 2>/dev/null"  */
+       char *argv[3];
+       int exitstatus;
+
+       argv[0] = "ilrun";
+       argv[1] = "--version";
+       argv[2] = NULL;
+       exitstatus = execute ("ilrun", "ilrun", argv, false, false, true, true,
+                             true, false);
+       ilrun_present = (exitstatus == 0);
+       ilrun_tested = true;
+      }
+
+    if (ilrun_present)
+      {
+       unsigned int argc;
+       char **argv;
+       char **argp;
+       unsigned int i;
+       bool err;
+
+       argc = 1 + 2 * libdirs_count + 1 + nargs;
+       argv = (char **) xallocsa ((argc + 1) * sizeof (char *));
+
+       argp = argv;
+       *argp++ = "ilrun";
+       for (i = 0; i < libdirs_count; i++)
+         {
+           *argp++ = "-L";
+           *argp++ = (char *) libdirs[i];
+         }
+       *argp++ = (char *) assembly_path;
+       for (i = 0; i < nargs; i++)
+         *argp++ = (char *) args[i];
+       *argp = NULL;
+       /* Ensure argv length was correctly calculated.  */
+       if (argp - argv != argc)
+         abort ();
+
+       if (verbose)
+         {
+           char *command = shell_quote_argv (argv);
+           printf ("%s\n", command);
+           free (command);
+         }
+
+       err = executer ("ilrun", "ilrun", argv, private_data);
+
+       freesa (argv);
+
+       return err;
+      }
+  }
+
+  {
+    static bool mono_tested;
+    static bool mono_present;
+
+    if (!mono_tested)
+      {
+       /* Test for presence of mono:
+          "mono --version >/dev/null 2>/dev/null"  */
+       char *argv[3];
+       int exitstatus;
+
+       argv[0] = "mono";
+       argv[1] = "--version";
+       argv[2] = NULL;
+       exitstatus = execute ("mono", "mono", argv, false, false, true, true,
+                             true, false);
+       mono_present = (exitstatus == 0);
+       mono_tested = true;
+      }
+
+    if (mono_present)
+      {
+       char *old_monopath;
+       char **argv = (char **) xallocsa ((2 + nargs + 1) * sizeof (char *));
+       unsigned int i;
+       bool err;
+
+       /* Set MONO_PATH.  */
+       old_monopath = set_monopath (libdirs, libdirs_count, false, verbose);
+
+       argv[0] = "mono";
+       argv[1] = (char *) assembly_path;
+       for (i = 0; i <= nargs; i++)
+         argv[2 + i] = (char *) args[i];
+
+       if (verbose)
+         {
+           char *command = shell_quote_argv (argv);
+           printf ("%s\n", command);
+           free (command);
+         }
+
+       err = executer ("mono", "mono", argv, private_data);
+
+       /* Reset MONO_PATH.  */
+       reset_monopath (old_monopath);
+
+       freesa (argv);
+
+       return err;
+      }
+  }
+
+  if (!quiet)
+    error (0, 0, _("C# virtual machine not found, try installing pnet"));
+  return true;
+}
diff --git a/gettext-tools/lib/csharpexec.h b/gettext-tools/lib/csharpexec.h
new file mode 100644 (file)
index 0000000..17efc01
--- /dev/null
@@ -0,0 +1,44 @@
+/* Execute a C# program.
+   Copyright (C) 2003 Free Software Foundation, Inc.
+   Written by Bruno Haible <bruno@clisp.org>, 2003.
+
+   This program is free software; you can redistribute it and/or modify
+   it under the terms of the GNU General Public License as published by
+   the Free Software Foundation; either version 2, or (at your option)
+   any later version.
+
+   This program is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
+
+   You should have received a copy of the GNU General Public License
+   along with this program; if not, write to the Free Software Foundation,
+   Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
+
+#ifndef _CSHARPEXEC_H
+#define _CSHARPEXEC_H
+
+#include <stdbool.h>
+
+typedef bool execute_fn (const char *progname,
+                        const char *prog_path, char **prog_argv,
+                        void *private_data);
+
+/* Execute a C# program.
+   assembly_path is the assembly's pathname (= program name with .exe).
+   libdirs is a list of directories to be searched for libraries.
+   args is a NULL terminated list of arguments to be passed to the program.
+   If verbose, the command to be executed will be printed.
+   Then the command is passed to the execute function together with the
+   private_data argument.  This function returns false if OK, true on error.
+   Return false if OK, true on error.
+   If quiet, error messages will not be printed.  */
+extern bool execute_csharp_program (const char *assembly_path,
+                                   const char * const *libdirs,
+                                   unsigned int libdirs_count,
+                                   const char * const *args,
+                                   bool verbose, bool quiet,
+                                   execute_fn *executer, void *private_data);
+
+#endif /* _CSHARPEXEC_H */
diff --git a/gettext-tools/lib/csharpexec.sh.in b/gettext-tools/lib/csharpexec.sh.in
new file mode 100644 (file)
index 0000000..20a3c67
--- /dev/null
@@ -0,0 +1,84 @@
+#!/bin/sh
+# Execute a C# program.
+
+# Copyright (C) 2003 Free Software Foundation, Inc.
+# Written by Bruno Haible <bruno@clisp.org>, 2003.
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2, or (at your option)
+# any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software Foundation,
+# Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
+
+# This uses the same choices as csharpexec.c, but instead of relying on the
+# environment settings at run time, it uses the environment variables
+# present at configuration time.
+#
+# This is a separate shell script, because the various C# interpreters have
+# different command line options.
+#
+# Usage: /bin/sh csharpexec.sh [OPTION] program.exe [ARGUMENTS]
+# Options:
+#   -L DIRECTORY      search for C# libraries also in DIRECTORY
+
+sed_quote_subst='s/\([|&;<>()$`"'"'"'*?[#~=%   \\]\)/\\\1/g'
+options_ilrun=
+libdirs_mono=
+prog=
+while test $# != 0; do
+  case "$1" in
+    -L)
+      options_ilrun="$options_ilrun -L "`echo "$2" | sed -e "$sed_quote_subst"`
+      libdirs_mono="${libdirs_mono:+$libdirs_mono@MONO_PATH_SEPARATOR@}$2"
+      shift
+      ;;
+    -*)
+      echo "csharpexec: unknown option '$1'" 1>&2
+      exit 1
+      ;;
+    *)
+      prog="$1"
+      break
+      ;;
+  esac
+  shift
+done
+if test -z "$prog"; then
+  echo "csharpexec: no program specified" 1>&2
+  exit 1
+fi
+case "$prog" in
+  *.exe) ;;
+  *)
+    echo "csharpexec: program is not a .exe" 1>&2
+    exit 1
+    ;;
+esac
+
+if test -n "@HAVE_ILRUN@"; then
+  test -z "$CSHARP_VERBOSE" || echo ilrun $options_ilrun "$@"
+  exec ilrun $options_ilrun "$@"
+else
+  if test -n "@HAVE_MONO@"; then
+    CONF_MONO_PATH='@MONO_PATH@'
+    if test -n "$libdirs_mono"; then
+      MONO_PATH="$libdirs_mono${CONF_MONO_PATH:+@MONO_PATH_SEPARATOR@$CONF_MONO_PATH}"
+    else
+      MONO_PATH="$CONF_MONO_PATH"
+    fi
+    export MONO_PATH
+    test -z "$CSHARP_VERBOSE" || echo mono "$@"
+    exec mono "$@"
+  else
+    echo 'C# virtual machine not found, try installing pnet, then reconfigure' 1>&2
+    exit 1
+  fi
+fi
diff --git a/gettext-tools/m4/csharpexec.m4 b/gettext-tools/m4/csharpexec.m4
new file mode 100644 (file)
index 0000000..33c94a4
--- /dev/null
@@ -0,0 +1,48 @@
+# csharpexec.m4 serial 1 (gettext-0.13.2)
+dnl Copyright (C) 2003 Free Software Foundation, Inc.
+dnl This file is free software, distributed under the terms of the GNU
+dnl General Public License.  As a special exception to the GNU General
+dnl Public License, this file may be distributed as part of a program
+dnl that contains a configuration script generated by Autoconf, under
+dnl the same distribution terms as the rest of that program.
+
+# Prerequisites of csharpexec.sh.
+# Sets HAVE_CSHARPEXEC to nonempty if csharpexec.sh will work.
+
+AC_DEFUN([gt_CSHARPEXEC],
+[
+  AC_MSG_CHECKING([for C[#] program execution engine])
+  AC_EGREP_CPP(yes, [
+#if defined _WIN32 || defined __WIN32__ || defined __EMX__ || defined __DJGPP__
+  yes
+#endif
+], MONO_PATH_SEPARATOR=';', MONO_PATH_SEPARATOR=':')
+  HAVE_CSHARPEXEC=1
+  pushdef([AC_MSG_CHECKING],[:])dnl
+  pushdef([AC_CHECKING],[:])dnl
+  pushdef([AC_MSG_RESULT],[:])dnl
+  AC_CHECK_PROG(HAVE_ILRUN_IN_PATH, ilrun, yes)
+  AC_CHECK_PROG(HAVE_MONO_IN_PATH, mono, yes)
+  popdef([AC_MSG_RESULT])dnl
+  popdef([AC_CHECKING])dnl
+  popdef([AC_MSG_CHECKING])dnl
+  if test -n "$HAVE_ILRUN_IN_PATH" \
+     && ilrun --version >/dev/null 2>/dev/null; then
+    HAVE_ILRUN=1
+    ac_result="ilrun"
+  else
+    if test -n "$HAVE_MONO_IN_PATH" \
+       && mono --version >/dev/null 2>/dev/null; then
+      HAVE_MONO=1
+      ac_result="mono"
+    else
+      HAVE_CSHARPEXEC=
+      ac_result="no"
+    fi
+  fi
+  AC_MSG_RESULT([$ac_result])
+  AC_SUBST(MONO_PATH)
+  AC_SUBST(MONO_PATH_SEPARATOR)
+  AC_SUBST(HAVE_ILRUN)
+  AC_SUBST(HAVE_MONO)
+])