diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/buildos2.sh glib-2.6.5.os2/buildos2.sh
--- glib-2.6.5/buildos2.sh	Thu Jan  1 00:00:00 1970
+++ glib-2.6.5.os2/buildos2.sh	Thu Jul 28 20:34:02 2005
@@ -0,0 +1,13 @@
+#!bash.exe
+export ac_executable_extensions=".exe"
+export LANG=C
+export CFLAGS="-O2 -Zmtd -Zsysv-signals -Zbin-files -D__ST_MT_ERRNO__"
+export LDFLAGS="-O2 -Zmtd -Zsysv-signals -Zbin-files -D__ST_MT_ERRNO__"
+export EMXSHELL=bash.exe
+#libtoolize --force; aclocal --force; autoconf --force; automake --force
+#./configure --prefix=/usr --sysconfdir=/etc --disable-libtool-locking --with-threads=none --disable-largefile SHELL=bash.exe LIBS="-liconv_s -lshm -lemxfix -lgcc"
+#/usr/bin/make.exe MAKE=/usr/bin/make.exe SHELL=bash.exe 2>&1 |tee make.log
+#/usr/bin/make.exe MAKE=/usr/bin/make.exe SHELL=bash.exe check 2>&1 |tee check.log
+#/usr/bin/make.exe MAKE=/usr/bin/make.exe SHELL=bash.exe install 2>&1 |tee inst.log
+/usr/bin/make.exe MAKE=/usr/bin/make.exe SHELL=bash.exe DESTDIR=/x11install/glib2 install 2>&1 |tee inst.log
+#/usr/bin/make.exe MAKE=/usr/bin/make.exe SHELL=bash.exe distclean 2>&1 |tee make.log
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/configure.in glib-2.6.5.os2/configure.in
--- glib-2.6.5/configure.in	Wed May 18 06:12:32 2005
+++ glib-2.6.5.os2/configure.in	Sun Jul 31 17:14:26 2005
@@ -147,17 +147,32 @@
     glib_pid_type=int
     ;;
 esac
+
+AC_MSG_CHECKING([for Linux])
 case $host in
   *-*-linux*)
     glib_os_linux=yes
     ;;
+  *)
+    glib_os_linux=no
+    ;;
 esac
 
+AC_MSG_CHECKING([for OS/2])
+case $host in
+  *-*-os2*)
+    glib_os_os2=yes
+    ;;
+  *)
+    glib_os_os2=no
+    ;;
+esac
 
 AC_MSG_RESULT([$glib_native_win32])
 AM_CONDITIONAL(OS_WIN32, [test "$glib_native_win32" = "yes"])
 AM_CONDITIONAL(OS_UNIX, [test "$glib_native_win32" != "yes"])
 AM_CONDITIONAL(OS_LINUX, [test "$glib_os_linux" = "yes"])
+AM_CONDITIONAL(OS_OS2, [test "$glib_os_os2" = "yes"])
 AC_SUBST(G_LIB_WIN32_RESOURCE)
 AC_SUBST(G_MODULE_WIN32_RESOURCE)
 AC_SUBST(G_OBJECT_WIN32_RESOURCE)
@@ -1235,7 +1250,7 @@
   hpux9* | hpux10* | hpux11*)  # taken from ltconfig
     glib_gmodule_suffix='sl'
     ;;
-  cygwin* | mingw*)
+  cygwin* | mingw* | os2*)
     glib_gmodule_suffix='dll'
     ;;
   aix*)
@@ -1267,6 +1282,9 @@
   *-*-mingw*)
     GSPAWN=gspawn-win32.lo
     ;;
+  *-*-os2*)
+    GSPAWN=gspawn-os2.lo
+    ;;
   *)
     GSPAWN=gspawn.lo
     ;;    
@@ -1308,7 +1326,7 @@
 
 AC_MSG_CHECKING([whether to compile timeloop])
 case "$host" in
-  *-*-cygwin*|*-*-mingw*)
+  *-*-cygwin* | *-*-mingw* | *-*-os2*)
     enable_timeloop=no
     ;;
   *)
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/glib/gconvert.c glib-2.6.5.os2/glib/gconvert.c
--- glib-2.6.5/glib/gconvert.c	Wed Apr 27 09:08:00 2005
+++ glib-2.6.5.os2/glib/gconvert.c	Sun Jul 31 17:14:58 2005
@@ -1412,7 +1412,7 @@
   char *escaped_path;
   char *res;
 
-#ifdef G_OS_WIN32
+#if defined G_OS_WIN32 || defined __EMX__
   char *p, *backslash;
 
   /* Turn backslashes into forward slashes. That's what Netscape
@@ -1442,7 +1442,7 @@
 		     escaped_path,
 		     NULL);
 
-#ifdef G_OS_WIN32
+#if defined G_OS_WIN32 || defined __EMX__
   g_free ((char *) pathname);
 #endif
 
@@ -1675,7 +1675,7 @@
     }
 
   offs = 0;
-#ifdef G_OS_WIN32
+#if defined G_OS_WIN32 || defined __EMX__
   /* Drop localhost */
   if (hostname && *hostname != NULL &&
       g_ascii_strcasecmp (*hostname, "localhost") == 0)
@@ -1684,6 +1684,7 @@
       *hostname = NULL;
     }
 
+#ifndef __EMX__
   /* Turn slashes into backslashes, because that's the canonical spelling */
   p = filename;
   while ((slash = strchr (p, '/')) != NULL)
@@ -1691,6 +1692,7 @@
       *slash = '\\';
       p = slash + 1;
     }
+#endif
 
   /* Windows URIs with a drive letter can be like "file://host/c:/foo"
    * or "file://host/c|/foo" (some Netscape versions). In those cases, start
@@ -1777,7 +1779,7 @@
       return NULL;
     }
   
-#ifdef G_OS_WIN32
+#if defined G_OS_WIN32 || defined __EMX__
   /* Don't use localhost unnecessarily */
   if (hostname && g_ascii_strcasecmp (hostname, "localhost") == 0)
     hostname = NULL;
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/glib/gfileutils.c glib-2.6.5.os2/glib/gfileutils.c
--- glib-2.6.5/glib/gfileutils.c	Mon Mar 14 05:02:06 2005
+++ glib-2.6.5.os2/glib/gfileutils.c	Sun Jul 31 17:14:58 2005
@@ -224,6 +224,9 @@
     {
       struct stat s;
 
+#ifdef __EMX__
+#define lstat stat
+#endif
       if ((lstat (filename, &s) == 0) && S_ISLNK (s.st_mode))
         return TRUE;
     }
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/glib/giounix.c glib-2.6.5.os2/glib/giounix.c
--- glib-2.6.5/glib/giounix.c	Mon Mar 14 05:02:06 2005
+++ glib-2.6.5.os2/glib/giounix.c	Sun Jul 31 17:14:58 2005
@@ -42,6 +42,10 @@
 #include <errno.h>
 #include <string.h>
 #include <fcntl.h>
+#ifdef __EMX__
+#define INCL_DOSFILEMGR
+#include <os2.h>
+#endif
 
 #include "glib.h"
 #include "galias.h"
@@ -391,6 +395,10 @@
   GIOFlags flags = 0;
   glong fcntl_flags;
   GIOUnixChannel *unix_channel = (GIOUnixChannel *) channel;
+#ifdef __EMX__
+  int rc;
+  ULONG mode;
+#endif
 
   fcntl_flags = fcntl (unix_channel->fd, F_GETFL);
 
@@ -410,6 +418,7 @@
 #endif
     flags |= G_IO_FLAG_NONBLOCK;
 
+#ifndef __EMX__
   switch (fcntl_flags & (O_RDONLY | O_WRONLY | O_RDWR))
     {
       case O_RDONLY:
@@ -427,6 +436,27 @@
       default:
         g_assert_not_reached ();
     }
+#else	/* __EMX__ */
+  /* F_GETFL doesn't return access modes in EMX */
+  rc = DosQueryFHState(unix_channel->fd, &mode);
+  switch (mode & (OPEN_ACCESS_READONLY | OPEN_ACCESS_WRITEONLY | OPEN_ACCESS_READWRITE))
+    {
+      case OPEN_ACCESS_READONLY:
+        channel->is_readable = TRUE;
+        channel->is_writeable = FALSE;
+        break;
+      case OPEN_ACCESS_WRITEONLY:
+        channel->is_readable = FALSE;
+        channel->is_writeable = TRUE;
+        break;
+      case OPEN_ACCESS_READWRITE:
+        channel->is_readable = TRUE;
+        channel->is_writeable = TRUE;
+        break;
+      default:
+        g_assert_not_reached ();
+    }
+#endif	/* __EMX__ */
 
   return flags;
 }
@@ -528,6 +558,10 @@
     }
 
   channel = (GIOChannel *) g_new (GIOUnixChannel, 1);
+
+#ifdef __EMX__
+#define S_ISBLK(dummy) 0
+#endif
 
   channel->is_seekable = S_ISREG (buffer.st_mode) || S_ISCHR (buffer.st_mode)
                          || S_ISBLK (buffer.st_mode);
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/glib/glib-2.0.os2name glib-2.6.5.os2/glib/glib-2.0.os2name
--- glib-2.6.5/glib/glib-2.0.os2name	Thu Jan  1 00:00:00 1970
+++ glib-2.6.5.os2/glib/glib-2.0.os2name	Sun Jul 31 17:14:58 2005
@@ -0,0 +1 @@
+glib2
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/glib/gmain.c glib-2.6.5.os2/glib/gmain.c
--- glib-2.6.5/glib/gmain.c	Fri Apr  1 23:41:12 2005
+++ glib-2.6.5.os2/glib/gmain.c	Sun Jul 31 17:14:58 2005
@@ -3552,6 +3552,11 @@
        */
     }
 }
+
+#ifdef __EMX__
+/* doesn't have a meaning in EMX */
+#define SA_RESTART 0x10000000
+#endif
  
 static void
 g_child_watch_source_init_single (void)
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/glib/gspawn-os2.c glib-2.6.5.os2/glib/gspawn-os2.c
--- glib-2.6.5/glib/gspawn-os2.c	Thu Jan  1 00:00:00 1970
+++ glib-2.6.5.os2/glib/gspawn-os2.c	Sun Jul 31 17:14:58 2005
@@ -0,0 +1,1230 @@
+/* Copied and modified from: 
+ *
+ * gspawn.c - Process launching
+ *
+ *  Copyright 2000 Red Hat, Inc.
+ *  g_execvpe implementation based on GNU libc execvp:
+ *   Copyright 1991, 92, 95, 96, 97, 98, 99 Free Software Foundation, Inc.
+ *
+ * GLib is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * GLib 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with GLib; see the file COPYING.LIB.  If not, write
+ * to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ * Boston, MA 02111-1307, USA.
+ */
+
+#include "config.h"
+
+#include <sys/time.h>
+#include <sys/types.h>
+#include <sys/wait.h>
+#include <unistd.h>
+#include <errno.h>
+#include <fcntl.h>
+#include <signal.h>
+#include <string.h>
+
+#ifdef HAVE_SYS_SELECT_H
+#include <sys/select.h>
+#endif /* HAVE_SYS_SELECT_H */
+
+#include <stdlib.h>
+#include <process.h>
+
+#include "glib.h"
+#include "galias.h"
+
+#include "glibintl.h"
+
+static gint g_execute (const gchar  *file,
+                       gchar **argv,
+                       gchar **envp,
+                       gboolean search_path);
+
+static gboolean make_pipe            (gint                  p[2],
+                                      GError              **error);
+static gboolean fork_exec_with_pipes (gboolean              intermediate_child,
+                                      const gchar          *working_directory,
+                                      gchar               **argv,
+                                      gchar               **envp,
+                                      gboolean              close_descriptors,
+                                      gboolean              search_path,
+                                      gboolean              stdout_to_null,
+                                      gboolean              stderr_to_null,
+                                      gboolean              child_inherits_stdin,
+                                      gboolean              file_and_argv_zero,
+                                      GSpawnChildSetupFunc  child_setup,
+                                      gpointer              user_data,
+                                      GPid                 *child_pid,
+                                      gint                 *standard_input,
+                                      gint                 *standard_output,
+                                      gint                 *standard_error,
+                                      GError              **error);
+
+GQuark
+g_spawn_error_quark (void)
+{
+  static GQuark quark = 0;
+  if (quark == 0)
+    quark = g_quark_from_static_string ("g-exec-error-quark");
+  return quark;
+}
+
+/**
+ * g_spawn_async:
+ * @working_directory: child's current working directory, or %NULL to inherit parent's
+ * @argv: child's argument vector
+ * @envp: child's environment, or %NULL to inherit parent's
+ * @flags: flags from #GSpawnFlags
+ * @child_setup: function to run in the child just before exec()
+ * @user_data: user data for @child_setup
+ * @child_pid: return location for child process ID, or %NULL
+ * @error: return location for error
+ * 
+ * See g_spawn_async_with_pipes() for a full description; this function
+ * simply calls the g_spawn_async_with_pipes() without any pipes.
+ * 
+ * Return value: %TRUE on success, %FALSE if error is set
+ **/
+gboolean
+g_spawn_async (const gchar          *working_directory,
+               gchar               **argv,
+               gchar               **envp,
+               GSpawnFlags           flags,
+               GSpawnChildSetupFunc  child_setup,
+               gpointer              user_data,
+               GPid                 *child_pid,
+               GError              **error)
+{
+  g_return_val_if_fail (argv != NULL, FALSE);
+  
+  return g_spawn_async_with_pipes (working_directory,
+                                   argv, envp,
+                                   flags,
+                                   child_setup,
+                                   user_data,
+                                   child_pid,
+                                   NULL, NULL, NULL,
+                                   error);
+}
+
+/* Avoids a danger in threaded situations (calling close()
+ * on a file descriptor twice, and another thread has
+ * re-opened it since the first close)
+ */
+static gint
+close_and_invalidate (gint *fd)
+{
+  gint ret;
+
+  if (*fd < 0)
+    return -1;
+  else
+    {
+      ret = close (*fd);
+      *fd = -1;
+    }
+
+  return ret;
+}
+
+typedef enum
+{
+  READ_FAILED = 0, /* FALSE */
+  READ_OK,
+  READ_EOF
+} ReadResult;
+
+static ReadResult
+read_data (GString *str,
+           gint     fd,
+           GError **error)
+{
+  gssize bytes;        
+  gchar buf[4096];    
+
+ again:
+  
+  bytes = read (fd, buf, 4096);
+
+  if (bytes == 0)
+    return READ_EOF;
+  else if (bytes > 0)
+    {
+      g_string_append_len (str, buf, bytes);
+      return READ_OK;
+    }
+  else if (bytes < 0 && errno == EINTR)
+    goto again;
+  else if (bytes < 0)
+    {
+      g_set_error (error,
+                   G_SPAWN_ERROR,
+                   G_SPAWN_ERROR_READ,
+                   _("Failed to read data from child process (%s)"),
+                   g_strerror (errno));
+      
+      return READ_FAILED;
+    }
+  else
+    return READ_OK;
+}
+
+/**
+ * g_spawn_sync:
+ * @working_directory: child's current working directory, or %NULL to inherit parent's
+ * @argv: child's argument vector
+ * @envp: child's environment, or %NULL to inherit parent's
+ * @flags: flags from #GSpawnFlags
+ * @child_setup: function to run in the child just before exec()
+ * @user_data: user data for @child_setup
+ * @standard_output: return location for child output 
+ * @standard_error: return location for child error messages
+ * @exit_status: child exit status, as returned by waitpid()
+ * @error: return location for error
+ *
+ * Executes a child synchronously (waits for the child to exit before returning).
+ * All output from the child is stored in @standard_output and @standard_error,
+ * if those parameters are non-%NULL. If @exit_status is non-%NULL, the exit 
+ * status of the child is stored there as it would be returned by 
+ * waitpid(); standard UNIX macros such as WIFEXITED() and WEXITSTATUS() 
+ * must be used to evaluate the exit status. If an error occurs, no data is 
+ * returned in @standard_output, @standard_error, or @exit_status.
+ * 
+ * This function calls g_spawn_async_with_pipes() internally; see that function
+ * for full details on the other parameters.
+ * 
+ * Return value: %TRUE on success, %FALSE if an error was set.
+ **/
+gboolean
+g_spawn_sync (const gchar          *working_directory,
+              gchar               **argv,
+              gchar               **envp,
+              GSpawnFlags           flags,
+              GSpawnChildSetupFunc  child_setup,
+              gpointer              user_data,
+              gchar               **standard_output,
+              gchar               **standard_error,
+              gint                 *exit_status,
+              GError              **error)     
+{
+  gint outpipe = -1;
+  gint errpipe = -1;
+  GPid pid;
+  fd_set fds;
+  gint ret;
+  GString *outstr = NULL;
+  GString *errstr = NULL;
+  gboolean failed;
+  gint status;
+  
+  g_return_val_if_fail (argv != NULL, FALSE);
+  g_return_val_if_fail (!(flags & G_SPAWN_DO_NOT_REAP_CHILD), FALSE);
+  g_return_val_if_fail (standard_output == NULL ||
+                        !(flags & G_SPAWN_STDOUT_TO_DEV_NULL), FALSE);
+  g_return_val_if_fail (standard_error == NULL ||
+                        !(flags & G_SPAWN_STDERR_TO_DEV_NULL), FALSE);
+  
+  /* Just to ensure segfaults if callers try to use
+   * these when an error is reported.
+   */
+  if (standard_output)
+    *standard_output = NULL;
+
+  if (standard_error)
+    *standard_error = NULL;
+  
+  if (!fork_exec_with_pipes (FALSE,
+                             working_directory,
+                             argv,
+                             envp,
+                             !(flags & G_SPAWN_LEAVE_DESCRIPTORS_OPEN),
+                             (flags & G_SPAWN_SEARCH_PATH) != 0,
+                             (flags & G_SPAWN_STDOUT_TO_DEV_NULL) != 0,
+                             (flags & G_SPAWN_STDERR_TO_DEV_NULL) != 0,
+                             (flags & G_SPAWN_CHILD_INHERITS_STDIN) != 0,
+                             (flags & G_SPAWN_FILE_AND_ARGV_ZERO) != 0,
+                             child_setup,
+                             user_data,
+                             &pid,
+                             NULL,
+                             standard_output ? &outpipe : NULL,
+                             standard_error ? &errpipe : NULL,
+                             error))
+    return FALSE;
+
+  /* Read data from child. */
+  
+  failed = FALSE;
+
+  if (outpipe >= 0)
+    {
+      outstr = g_string_new (NULL);
+    }
+      
+  if (errpipe >= 0)
+    {
+      errstr = g_string_new (NULL);
+    }
+
+  /* Read data until we get EOF on both pipes. */
+  while (!failed &&
+         (outpipe >= 0 ||
+          errpipe >= 0))
+    {
+      ret = 0;
+          
+      FD_ZERO (&fds);
+      if (outpipe >= 0)
+        FD_SET (outpipe, &fds);
+      if (errpipe >= 0)
+        FD_SET (errpipe, &fds);
+          
+      ret = select (MAX (outpipe, errpipe) + 1,
+                    &fds,
+                    NULL, NULL,
+                    NULL /* no timeout */);
+
+      if (ret < 0 && errno != EINTR)
+        {
+          failed = TRUE;
+
+          g_set_error (error,
+                       G_SPAWN_ERROR,
+                       G_SPAWN_ERROR_READ,
+                       _("Unexpected error in select() reading data from a child process (%s)"),
+                       g_strerror (errno));
+              
+          break;
+        }
+
+      if (outpipe >= 0 && FD_ISSET (outpipe, &fds))
+        {
+          switch (read_data (outstr, outpipe, error))
+            {
+            case READ_FAILED:
+              failed = TRUE;
+              break;
+            case READ_EOF:
+              close_and_invalidate (&outpipe);
+              outpipe = -1;
+              break;
+            default:
+              break;
+            }
+
+          if (failed)
+            break;
+        }
+
+      if (errpipe >= 0 && FD_ISSET (errpipe, &fds))
+        {
+          switch (read_data (errstr, errpipe, error))
+            {
+            case READ_FAILED:
+              failed = TRUE;
+              break;
+            case READ_EOF:
+              close_and_invalidate (&errpipe);
+              errpipe = -1;
+              break;
+            default:
+              break;
+            }
+
+          if (failed)
+            break;
+        }
+    }
+
+  /* These should only be open still if we had an error.  */
+  
+  if (outpipe >= 0)
+    close_and_invalidate (&outpipe);
+  if (errpipe >= 0)
+    close_and_invalidate (&errpipe);
+  
+  /* Wait for child to exit, even if we have
+   * an error pending.
+   */
+ again:
+      
+  ret = waitpid (pid, &status, 0);
+
+  if (ret < 0)
+    {
+      if (errno == EINTR)
+        goto again;
+      else if (errno == ECHILD)
+        {
+          if (exit_status)
+            {
+              g_warning ("In call to g_spawn_sync(), exit status of a child process was requested but SIGCHLD action was set to SIG_IGN and ECHILD was received by waitpid(), so exit status can't be returned. This is a bug in the program calling g_spawn_sync(); either don't request the exit status, or don't set the SIGCHLD action.");
+            }
+          else
+            {
+              /* We don't need the exit status. */
+            }
+        }
+      else
+        {
+          if (!failed) /* avoid error pileups */
+            {
+              failed = TRUE;
+                  
+              g_set_error (error,
+                           G_SPAWN_ERROR,
+                           G_SPAWN_ERROR_READ,
+                           _("Unexpected error in waitpid() (%s)"),
+                           g_strerror (errno));
+            }
+        }
+    }
+  
+  if (failed)
+    {
+      if (outstr)
+        g_string_free (outstr, TRUE);
+      if (errstr)
+        g_string_free (errstr, TRUE);
+
+      return FALSE;
+    }
+  else
+    {
+      if (exit_status)
+        *exit_status = status;
+      
+      if (standard_output)        
+        *standard_output = g_string_free (outstr, FALSE);
+
+      if (standard_error)
+        *standard_error = g_string_free (errstr, FALSE);
+
+      return TRUE;
+    }
+}
+
+/**
+ * g_spawn_async_with_pipes:
+ * @working_directory: child's current working directory, or %NULL to inherit parent's
+ * @argv: child's argument vector
+ * @envp: child's environment, or %NULL to inherit parent's
+ * @flags: flags from #GSpawnFlags
+ * @child_setup: function to run in the child just before exec()
+ * @user_data: user data for @child_setup
+ * @child_pid: return location for child process ID, or %NULL
+ * @standard_input: return location for file descriptor to write to child's stdin, or %NULL
+ * @standard_output: return location for file descriptor to read child's stdout, or %NULL
+ * @standard_error: return location for file descriptor to read child's stderr, or %NULL
+ * @error: return location for error
+ *
+ * Executes a child program asynchronously (your program will not
+ * block waiting for the child to exit). The child program is
+ * specified by the only argument that must be provided, @argv. @argv
+ * should be a %NULL-terminated array of strings, to be passed as the
+ * argument vector for the child. The first string in @argv is of
+ * course the name of the program to execute. By default, the name of
+ * the program must be a full path; the <envar>PATH</envar> shell variable 
+ * will only be searched if you pass the %G_SPAWN_SEARCH_PATH flag.
+ *
+ * On Windows, the low-level child process creation API
+ * (CreateProcess())doesn't use argument vectors,
+ * but a command line. The C runtime library's
+ * <function>spawn*()</function> family of functions (which
+ * g_spawn_async_with_pipes() eventually calls) paste the argument
+ * vector elements into a command line, and the C runtime startup code
+ * does a corresponding reconstruction of an argument vector from the
+ * command line, to be passed to main(). Complications arise when you have
+ * argument vector elements that contain spaces of double quotes. The
+ * <function>spawn*()</function> functions don't do any quoting or
+ * escaping, but on the other hand the startup code does do unquoting
+ * and unescaping in order to enable receiving arguments with embedded
+ * spaces or double quotes. To work around this asymmetry,
+ * g_spawn_async_with_pipes() will do quoting and escaping on argument
+ * vector elements that need it before calling the C runtime
+ * spawn() function.
+ *
+ * @envp is a %NULL-terminated array of strings, where each string
+ * has the form <literal>KEY=VALUE</literal>. This will become
+ * the child's environment. If @envp is %NULL, the child inherits its
+ * parent's environment.
+ *
+ * @flags should be the bitwise OR of any flags you want to affect the
+ * function's behaviour. The %G_SPAWN_DO_NOT_REAP_CHILD means that 
+ * the child will not automatically be reaped; you must use a
+ * #GChildWatch source to be notified about the death of the child 
+ * process. Eventually you must call g_spawn_close_pid() on the
+ * @child_pid, in order to free resources which may be associated
+ * with the child process. (On Unix, using a #GChildWatch source is
+ * equivalent to calling waitpid() or handling the %SIGCHLD signal 
+ * manually. On Windows, calling g_spawn_close_pid() is equivalent
+ * to calling CloseHandle() on the process handle returned in 
+ * @child_pid).
+ *
+ * %G_SPAWN_LEAVE_DESCRIPTORS_OPEN means that the parent's open file
+ * descriptors will be inherited by the child; otherwise all
+ * descriptors except stdin/stdout/stderr will be closed before
+ * calling exec() in the child. %G_SPAWN_SEARCH_PATH 
+ * means that <literal>argv[0]</literal> need not be an absolute path, it
+ * will be looked for in the user's <envar>PATH</envar>. 
+ * %G_SPAWN_STDOUT_TO_DEV_NULL means that the child's standard output will 
+ * be discarded, instead of going to the same location as the parent's 
+ * standard output. If you use this flag, @standard_output must be %NULL.
+ * %G_SPAWN_STDERR_TO_DEV_NULL means that the child's standard error
+ * will be discarded, instead of going to the same location as the parent's
+ * standard error. If you use this flag, @standard_error must be %NULL.
+ * %G_SPAWN_CHILD_INHERITS_STDIN means that the child will inherit the parent's
+ * standard input (by default, the child's standard input is attached to
+ * /dev/null). If you use this flag, @standard_input must be %NULL.
+ * %G_SPAWN_FILE_AND_ARGV_ZERO means that the first element of @argv is
+ * the file to execute, while the remaining elements are the
+ * actual argument vector to pass to the file. Normally
+ * g_spawn_async_with_pipes() uses @argv[0] as the file to execute, and
+ * passes all of @argv to the child.
+ *
+ * @child_setup and @user_data are a function and user data. On POSIX
+ * platforms, the function is called in the child after GLib has
+ * performed all the setup it plans to perform (including creating
+ * pipes, closing file descriptors, etc.) but before calling
+ * exec(). That is, @child_setup is called just
+ * before calling exec() in the child. Obviously
+ * actions taken in this function will only affect the child, not the
+ * parent. On Windows, there is no separate fork() and exec()
+ * functionality. Child processes are created and run right away with
+ * one API call, CreateProcess(). @child_setup is
+ * called in the parent process just before creating the child
+ * process. You should carefully consider what you do in @child_setup
+ * if you intend your software to be portable to Windows.
+ *
+ * If non-%NULL, @child_pid will on Unix be filled with the child's
+ * process ID. You can use the process ID to send signals to the
+ * child, or to waitpid() if you specified the
+ * %G_SPAWN_DO_NOT_REAP_CHILD flag. On Windows, @child_pid will be
+ * filled with a handle to the child process only if you specified the
+ * %G_SPAWN_DO_NOT_REAP_CHILD flag. You can then access the child
+ * process using the Win32 API, for example wait for its termination
+ * with the <function>WaitFor*()</function> functions, or examine its
+ * exit code with GetExitCodeProcess(). You should close the handle 
+ * with CloseHandle() when you no longer need it.
+ *
+ * If non-%NULL, the @standard_input, @standard_output, @standard_error
+ * locations will be filled with file descriptors for writing to the child's
+ * standard input or reading from its standard output or standard error.
+ * The caller of g_spawn_async_with_pipes() must close these file descriptors
+ * when they are no longer in use. If these parameters are %NULL, the corresponding
+ * pipe won't be created.
+ *
+ * If @standard_input is NULL, the child's standard input is attached to /dev/null
+ * unless %G_SPAWN_CHILD_INHERITS_STDIN is set.
+ *
+ * If @standard_error is NULL, the child's standard error goes to the same location
+ * as the parent's standard error unless %G_SPAWN_STDERR_TO_DEV_NULL is set.
+ *
+ * If @standard_output is NULL, the child's standard output goes to the same location
+ * as the parent's standard output unless %G_SPAWN_STDOUT_TO_DEV_NULL is set.
+ *
+ * @error can be %NULL to ignore errors, or non-%NULL to report errors.
+ * If an error is set, the function returns %FALSE. Errors
+ * are reported even if they occur in the child (for example if the
+ * executable in <literal>argv[0]</literal> is not found). Typically
+ * the <literal>message</literal> field of returned errors should be displayed
+ * to users. Possible errors are those from the #G_SPAWN_ERROR domain.
+ *
+ * If an error occurs, @child_pid, @standard_input, @standard_output,
+ * and @standard_error will not be filled with valid values.
+ *
+ * If @child_pid is not %NULL and an error does not occur then the returned
+ * pid must be closed using g_spawn_close_pid().
+ * 
+ * Return value: %TRUE on success, %FALSE if an error was set
+ **/
+ 
+static void 
+Waitpid (GPid *pid)
+{
+  int stat_loc;
+   
+  waitpid (*pid, &stat_loc, 0);
+  /* Discard everything
+   */
+}
+ 
+gboolean
+g_spawn_async_with_pipes (const gchar          *working_directory,
+                          gchar               **argv,
+                          gchar               **envp,
+                          GSpawnFlags           flags,
+                          GSpawnChildSetupFunc  child_setup,
+                          gpointer              user_data,
+                          GPid                 *child_pid,
+                          gint                 *standard_input,
+                          gint                 *standard_output,
+                          gint                 *standard_error,
+                          GError              **error)
+{
+  gboolean result;
+  int tid;
+  
+  g_return_val_if_fail (argv != NULL, FALSE);
+  g_return_val_if_fail (standard_output == NULL ||
+                        !(flags & G_SPAWN_STDOUT_TO_DEV_NULL), FALSE);
+  g_return_val_if_fail (standard_error == NULL ||
+                        !(flags & G_SPAWN_STDERR_TO_DEV_NULL), FALSE);
+  /* can't inherit stdin if we have an input pipe. */
+  g_return_val_if_fail (standard_input == NULL ||
+                        !(flags & G_SPAWN_CHILD_INHERITS_STDIN), FALSE);
+  
+  result = fork_exec_with_pipes (!(flags & G_SPAWN_DO_NOT_REAP_CHILD),
+                               working_directory,
+                               argv,
+                               envp,
+                               !(flags & G_SPAWN_LEAVE_DESCRIPTORS_OPEN),
+                               (flags & G_SPAWN_SEARCH_PATH) != 0,
+                               (flags & G_SPAWN_STDOUT_TO_DEV_NULL) != 0,
+                               (flags & G_SPAWN_STDERR_TO_DEV_NULL) != 0,
+                               (flags & G_SPAWN_CHILD_INHERITS_STDIN) != 0,
+                               (flags & G_SPAWN_FILE_AND_ARGV_ZERO) != 0,
+                               child_setup,
+                               user_data,
+                               child_pid,
+                               standard_input,
+                               standard_output,
+                               standard_error,
+                               error);
+  /* start a thread with waitpid() so the return code does not fill up memory
+   */
+  tid = _beginthread (Waitpid, NULL, 0x2000, (void *) child_pid);
+   
+  return result;                               
+}
+
+/**
+ * g_spawn_command_line_sync:
+ * @command_line: a command line 
+ * @standard_output: return location for child output
+ * @standard_error: return location for child errors
+ * @exit_status: return location for child exit status
+ * @error: return location for errors
+ *
+ * A simple version of g_spawn_sync() with little-used parameters
+ * removed, taking a command line instead of an argument vector.  See
+ * g_spawn_sync() for full details. @command_line will be parsed by
+ * g_shell_parse_argv(). Unlike g_spawn_sync(), the %G_SPAWN_SEARCH_PATH flag
+ * is enabled. Note that %G_SPAWN_SEARCH_PATH can have security
+ * implications, so consider using g_spawn_sync() directly if
+ * appropriate. Possible errors are those from g_spawn_sync() and those
+ * from g_shell_parse_argv().
+ * 
+ * On Windows, please note the implications of g_shell_parse_argv()
+ * parsing @command_line. Space is a separator, and backslashes are
+ * special. Thus you cannot simply pass a @command_line containing
+ * canonical Windows paths, like "c:\\program files\\app\\app.exe", as
+ * the backslashes will be eaten, and the space will act as a
+ * separator. You need to enclose such paths with single quotes, like
+ * "'c:\\program files\\app\\app.exe' 'e:\\folder\\argument.txt'".
+ *
+ * Return value: %TRUE on success, %FALSE if an error was set
+ **/
+gboolean
+g_spawn_command_line_sync (const gchar  *command_line,
+                           gchar       **standard_output,
+                           gchar       **standard_error,
+                           gint         *exit_status,
+                           GError      **error)
+{
+  gboolean retval;
+  gchar **argv = NULL;
+
+  g_return_val_if_fail (command_line != NULL, FALSE);
+  
+  if (!g_shell_parse_argv (command_line,
+                           NULL, &argv,
+                           error))
+    return FALSE;
+  
+  retval = g_spawn_sync (NULL,
+                         argv,
+                         NULL,
+                         G_SPAWN_SEARCH_PATH,
+                         NULL,
+                         NULL,
+                         standard_output,
+                         standard_error,
+                         exit_status,
+                         error);
+  g_strfreev (argv);
+
+  return retval;
+}
+
+/**
+ * g_spawn_command_line_async:
+ * @command_line: a command line
+ * @error: return location for errors
+ * 
+ * A simple version of g_spawn_async() that parses a command line with
+ * g_shell_parse_argv() and passes it to g_spawn_async(). Runs a
+ * command line in the background. Unlike g_spawn_async(), the
+ * %G_SPAWN_SEARCH_PATH flag is enabled, other flags are not. Note
+ * that %G_SPAWN_SEARCH_PATH can have security implications, so
+ * consider using g_spawn_async() directly if appropriate. Possible
+ * errors are those from g_shell_parse_argv() and g_spawn_async().
+ * 
+ * The same concerns on Windows apply as for g_spawn_command_line_sync().
+ *
+ * Return value: %TRUE on success, %FALSE if error is set.
+ **/
+gboolean
+g_spawn_command_line_async (const gchar *command_line,
+                            GError     **error)
+{
+  gboolean retval;
+  gchar **argv = NULL;
+
+  g_return_val_if_fail (command_line != NULL, FALSE);
+
+  if (!g_shell_parse_argv (command_line,
+                           NULL, &argv,
+                           error))
+    return FALSE;
+  
+  retval = g_spawn_async (NULL,
+                          argv,
+                          NULL,
+                          G_SPAWN_SEARCH_PATH,
+                          NULL,
+                          NULL,
+                          NULL,
+                          error);
+  g_strfreev (argv);
+
+  return retval;
+}
+
+static gint
+exec_err_to_g_error (gint en)
+{
+  switch (en)
+    {
+#ifdef EACCES
+    case EACCES:
+      return G_SPAWN_ERROR_ACCES;
+      break;
+#endif
+
+#ifdef EPERM
+    case EPERM:
+      return G_SPAWN_ERROR_PERM;
+      break;
+#endif
+
+#ifdef E2BIG
+    case E2BIG:
+      return G_SPAWN_ERROR_2BIG;
+      break;
+#endif
+
+#ifdef ENOEXEC
+    case ENOEXEC:
+      return G_SPAWN_ERROR_NOEXEC;
+      break;
+#endif
+
+#ifdef ENAMETOOLONG
+    case ENAMETOOLONG:
+      return G_SPAWN_ERROR_NAMETOOLONG;
+      break;
+#endif
+
+#ifdef ENOENT
+    case ENOENT:
+      return G_SPAWN_ERROR_NOENT;
+      break;
+#endif
+
+#ifdef ENOMEM
+    case ENOMEM:
+      return G_SPAWN_ERROR_NOMEM;
+      break;
+#endif
+
+#ifdef ENOTDIR
+    case ENOTDIR:
+      return G_SPAWN_ERROR_NOTDIR;
+      break;
+#endif
+
+#ifdef ELOOP
+    case ELOOP:
+      return G_SPAWN_ERROR_LOOP;
+      break;
+#endif
+      
+#ifdef ETXTBUSY
+    case ETXTBUSY:
+      return G_SPAWN_ERROR_TXTBUSY;
+      break;
+#endif
+
+#ifdef EIO
+    case EIO:
+      return G_SPAWN_ERROR_IO;
+      break;
+#endif
+
+#ifdef ENFILE
+    case ENFILE:
+      return G_SPAWN_ERROR_NFILE;
+      break;
+#endif
+
+#ifdef EMFILE
+    case EMFILE:
+      return G_SPAWN_ERROR_MFILE;
+      break;
+#endif
+
+#ifdef EINVAL
+    case EINVAL:
+      return G_SPAWN_ERROR_INVAL;
+      break;
+#endif
+
+#ifdef EISDIR
+    case EISDIR:
+      return G_SPAWN_ERROR_ISDIR;
+      break;
+#endif
+
+#ifdef ELIBBAD
+    case ELIBBAD:
+      return G_SPAWN_ERROR_LIBBAD;
+      break;
+#endif
+      
+    default:
+      return G_SPAWN_ERROR_FAILED;
+      break;
+    }
+}
+
+static void
+set_cloexec (gint fd)
+{
+  fcntl (fd, F_SETFD, FD_CLOEXEC);
+}
+
+static gint
+sane_dup2 (gint fd1, gint fd2)
+{
+  gint ret;
+
+ retry:
+  ret = dup2 (fd1, fd2);
+  if (ret < 0 && errno == EINTR)
+    goto retry;
+
+  return ret;
+}
+
+enum
+{
+  CHILD_CHDIR_FAILED,
+  CHILD_EXEC_FAILED,
+  CHILD_DUP2_FAILED,
+  CHILD_FORK_FAILED
+};
+
+static gint
+do_exec (gint                  stdin_fd,
+         gint                  stdout_fd,
+         gint                  stderr_fd,
+         const gchar          *working_directory,
+         gchar               **argv,
+         gchar               **envp,
+         gboolean              close_descriptors,
+         gboolean              search_path,
+         gboolean              stdout_to_null,
+         gboolean              stderr_to_null,
+         gboolean              child_inherits_stdin,
+         gboolean              file_and_argv_zero,
+         GSpawnChildSetupFunc  child_setup,
+         gpointer              user_data,
+         GError                **error)
+{
+  gint stdin_sav = -1;
+  gint stdout_sav = -1;
+  gint stderr_sav = -1;
+  gint pid = -1;
+  char wd[1024];
+  
+  /* Save current working directory
+   */
+  if (working_directory && *working_directory)
+    _getcwd2 (wd,sizeof(wd)); 
+  
+  if (working_directory && *working_directory && _chdir2 (working_directory) < 0)
+    g_set_error (error,
+                 G_SPAWN_ERROR,
+                 G_SPAWN_ERROR_CHDIR,
+                 _("Failed to change to directory '%s' (%s)"),
+                 working_directory,
+                 g_strerror (errno));
+
+
+  /* Close all file descriptors but stdin stdout and stderr as
+   * soon as we exec. Note that this includes
+   * child_err_report_fd, which keeps the parent from blocking
+   * forever on the other end of that pipe.
+   */
+  
+  if (close_descriptors)
+    {
+      gint open_max;
+      gint i;
+      
+      open_max = /*sysconf (_SC_OPEN_MAX)*/256;
+      for (i = 3; i < open_max; i++)
+        set_cloexec (i);
+    }
+
+  /* Redirect pipes as required
+   * Save the handles before closing them!!!!
+   */
+
+  if (stdin_fd >= 0)
+    {
+      stdin_sav = dup (0);
+      /* dup2 can't actually fail here I don't think */
+          
+      if (sane_dup2 (stdin_fd, 0) < 0)
+        g_set_error (error,
+                     G_SPAWN_ERROR,
+                     G_SPAWN_ERROR_FAILED,
+                     _("Failed to redirect input or output of child process (%s)"),
+                     g_strerror (errno));
+
+      /* ignore this if it doesn't work */
+      close_and_invalidate (&stdin_fd);
+    }
+  else if (!child_inherits_stdin)
+    {
+      /* Keep process from blocking on a read of stdin */
+      gint read_null = open ("NUL", O_RDONLY);
+      stdin_sav = dup (0);
+      sane_dup2 (read_null, 0);
+      close_and_invalidate (&read_null);
+    }
+
+  if (stdout_fd >= 0)
+    {
+      stdout_sav = dup (1);
+      /* dup2 can't actually fail here I don't think */
+          
+      if (sane_dup2 (stdout_fd, 1) < 0)
+        g_set_error (error,
+                     G_SPAWN_ERROR,
+                     G_SPAWN_ERROR_FAILED,
+                     _("Failed to redirect input or ouput of child process (%s)"),
+                     g_strerror (errno));
+
+      /* ignore this if it doesn't work */
+      close_and_invalidate (&stdout_fd);
+    }
+  else if (stdout_to_null)
+    {
+      gint write_null = open ("NUL", O_WRONLY);
+      stdout_sav = dup (1);
+      sane_dup2 (write_null, 1);
+      close_and_invalidate (&write_null);
+    }
+
+  if (stderr_fd >= 0)
+    {
+      stderr_sav = dup (2);
+      /* dup2 can't actually fail here I don't think */
+          
+      if (sane_dup2 (stderr_fd, 2) < 0)
+        g_set_error (error,
+                     G_SPAWN_ERROR,
+                     G_SPAWN_ERROR_FAILED,
+                     _("Failed to redirect input or ouput of child process (%s)"),
+                     g_strerror (errno));
+
+      /* ignore this if it doesn't work */
+      close_and_invalidate (&stderr_fd);
+    }
+  else if (stderr_to_null)
+    {
+      gint write_null = open ("NUL", O_WRONLY);
+      stderr_sav = dup (2);
+      sane_dup2 (write_null, 2);
+      close_and_invalidate (&write_null);
+    }
+  
+  /* Call user function just before we exec */
+  if (child_setup)
+    {
+      (* child_setup) (user_data);
+    }
+
+  pid = g_execute (argv[0],
+             file_and_argv_zero ? argv + 1 : argv,
+             envp, search_path);
+
+  /* Restore working directory
+   */  
+  if (working_directory && *working_directory)
+    _chdir2 (wd);
+    
+  /* Restore the saved handles
+   */
+  if (stdin_sav > -1)
+    {
+      sane_dup2 (stdin_sav, 0);
+      close (stdin_sav);
+    }
+    
+  if (stdout_sav > -1)
+    {
+      sane_dup2 (stdout_sav, 1);
+      close (stdout_sav);
+    } 
+    
+  if (stderr_sav > -1)
+    {
+      sane_dup2 (stderr_sav, 2);
+      close (stderr_sav);
+    }
+    
+  return pid;
+
+}
+
+static gboolean
+fork_exec_with_pipes (gboolean              intermediate_child,
+                      const gchar          *working_directory,
+                      gchar               **argv,
+                      gchar               **envp,
+                      gboolean              close_descriptors,
+                      gboolean              search_path,
+                      gboolean              stdout_to_null,
+                      gboolean              stderr_to_null,
+                      gboolean              child_inherits_stdin,
+                      gboolean              file_and_argv_zero,
+                      GSpawnChildSetupFunc  child_setup,
+                      gpointer              user_data,
+                      GPid                 *child_pid,
+                      gint                 *standard_input,
+                      gint                 *standard_output,
+                      gint                 *standard_error,
+                      GError              **error)     
+{
+  GPid pid = -1;
+  gint stdin_pipe[2] = { -1, -1 };
+  gint stdout_pipe[2] = { -1, -1 };
+  gint stderr_pipe[2] = { -1, -1 };
+  
+  if (standard_input && !make_pipe (stdin_pipe, error))
+    goto cleanup_and_fail;
+  
+  if (standard_output && !make_pipe (stdout_pipe, error))
+    goto cleanup_and_fail;
+
+  if (standard_error && !make_pipe (stderr_pipe, error))
+    goto cleanup_and_fail;
+
+  /* Be sure we crash if the parent exits
+   * and we write to the err_report_pipe
+   */
+  signal (SIGPIPE, SIG_DFL);
+
+  /* Close the parent's end of the pipes;
+   * not needed in the close_descriptors case,
+   * though
+   */
+  set_cloexec (stdin_pipe[1]);
+  set_cloexec (stdout_pipe[0]);
+  set_cloexec (stderr_pipe[0]);
+      
+  /* Spawn the child
+   */
+  pid = do_exec (stdin_pipe[0],
+                stdout_pipe[1],
+                stderr_pipe[1],
+                working_directory,
+                argv,
+                envp,
+                close_descriptors,
+                search_path,
+                stdout_to_null,
+                stderr_to_null,
+                child_inherits_stdin,
+                file_and_argv_zero,
+                child_setup,
+                user_data,
+                error);
+
+  {
+
+   /* Close the uncared-about ends of the pipes */
+   close_and_invalidate (&stdin_pipe[0]);
+   close_and_invalidate (&stdout_pipe[1]);
+   close_and_invalidate (&stderr_pipe[1]);
+
+   /* Success against all odds! return the information */
+ 
+   if (child_pid)
+     *child_pid = pid;
+
+   if (standard_input)
+     *standard_input = stdin_pipe[1];
+   if (standard_output)
+     *standard_output = stdout_pipe[0];
+   if (standard_error)
+     *standard_error = stderr_pipe[0];
+   
+   return TRUE;
+ }
+
+ cleanup_and_fail:
+
+  /* There was an error from the Child, reap the child to avoid it being
+     a zombie.
+   */
+
+  if (pid > 0)
+  {
+    wait_failed:
+     if (waitpid (pid, NULL, 0) < 0)
+       {
+          if (errno == EINTR)
+            goto wait_failed;
+          else if (errno == ECHILD)
+            ; /* do nothing, child already reaped */
+          else
+            g_warning ("waitpid() should not fail in "
+                       "'fork_exec_with_pipes'");
+       }
+   }
+
+  close_and_invalidate (&stdin_pipe[0]);
+  close_and_invalidate (&stdin_pipe[1]);
+  close_and_invalidate (&stdout_pipe[0]);
+  close_and_invalidate (&stdout_pipe[1]);
+  close_and_invalidate (&stderr_pipe[0]);
+  close_and_invalidate (&stderr_pipe[1]);
+
+  return FALSE;
+}
+
+static gboolean
+make_pipe (gint     p[2],
+           GError **error)
+{
+  if (pipe (p) < 0)
+    {
+      g_set_error (error,
+                   G_SPAWN_ERROR,
+                   G_SPAWN_ERROR_FAILED,
+                   _("Failed to create pipe for communicating with child process (%s)"),
+                   g_strerror (errno));
+      return FALSE;
+    }
+  else
+    return TRUE;
+}
+
+/* Based on execvp from GNU C Library */
+
+static gint
+script_execute (const gchar *file,
+                gchar      **argv,
+                gchar      **envp,
+                gboolean     search_path)
+{
+  /* Count the arguments.  */
+  int argc = 0;
+  gint pid = -1;
+  
+  while (argv[argc])
+    ++argc;
+  
+  /* Construct an argument list for the shell.  */
+  {
+    gchar **new_argv;
+
+    new_argv = g_new0 (gchar*, argc + 2); /* /bin/sh and NULL */
+    
+    new_argv[0] = (char *) "sh.exe";
+    new_argv[1] = (char *) file;
+    while (argc > 0)
+      {
+	new_argv[argc + 1] = argv[argc];
+	--argc;
+      }
+
+    /* Execute the shell. */
+    if (envp)
+      pid = spawnve (P_NOWAIT, new_argv[0], new_argv, envp);
+    else
+      pid = spawnv (P_NOWAIT, new_argv[0], new_argv);
+    
+    g_free (new_argv);
+    
+    return pid;
+  }
+}
+
+static gint
+g_execute (const gchar *file,
+           gchar      **argv,
+           gchar      **envp,
+           gboolean     search_path)
+{
+  gint pid;
+  
+  if (*file == '\0')
+    {
+      /* We check the simple case first. */
+      errno = ENOENT;
+      return -1;
+    }
+
+  if (envp)
+    pid = spawnve (P_NOWAIT, file, argv, envp);
+  else
+    pid = spawnv (P_NOWAIT, file, argv);
+  
+  if (pid == -1)
+    pid = script_execute (file, argv, envp, FALSE);
+
+  return pid;
+}
+
+/**
+ * g_spawn_close_pid:
+ * @pid: The process identifier to close
+ *
+ * On some platforms, notably WIN32, the #GPid type represents a resource
+ * which must be closed to prevent resource leaking. g_spawn_close_pid()
+ * is provided for this purpose. It should be used on all platforms, even
+ * though it doesn't do anything under UNIX.
+ **/
+void
+g_spawn_close_pid (GPid pid)
+{
+}
+
+#define __G_SPAWN_C__
+#include "galiasdef.c"
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/glib/gutils.c glib-2.6.5.os2/glib/gutils.c
--- glib-2.6.5/glib/gutils.c	Wed Jun  8 21:57:14 2005
+++ glib-2.6.5.os2/glib/gutils.c	Sun Jul 31 17:14:58 2005
@@ -634,7 +634,7 @@
   if (G_IS_DIR_SEPARATOR (file_name[0]))
     return TRUE;
 
-#ifdef G_OS_WIN32
+#if defined G_OS_WIN32 || defined __EMX__
   /* Recognize drive letter on native Windows */
   if (g_ascii_isalpha (file_name[0]) && file_name[1] == ':' && G_IS_DIR_SEPARATOR (file_name[2]))
     return TRUE;
@@ -648,7 +648,7 @@
 {
   g_return_val_if_fail (file_name != NULL, NULL);
   
-#ifdef G_PLATFORM_WIN32
+#if defined G_PLATFORM_WIN32 || defined __EMX__
   /* Skip \\server\share or //server/share */
   if (G_IS_DIR_SEPARATOR (file_name[0]) &&
       G_IS_DIR_SEPARATOR (file_name[1]) &&
@@ -665,6 +665,13 @@
 	  p = q;
       }
 #endif
+#ifdef __EMX__
+      {
+	gchar *q = strchr (file_name + 2, '\\');
+	if (p == NULL || (q != NULL && q < p))
+	  p = q;
+      }
+#endif
       if (p &&
 	  p > file_name + 2 &&
 	  p[1])
@@ -691,7 +698,7 @@
       return (gchar *)file_name;
     }
 
-#ifdef G_OS_WIN32
+#if defined G_OS_WIN32 || defined __EMX__
   /* Skip X:\ */
   if (g_ascii_isalpha (file_name[0]) && file_name[1] == ':' && G_IS_DIR_SEPARATOR (file_name[2]))
     return (gchar *)file_name + 3;
@@ -716,9 +723,16 @@
 	base = q;
   }
 #endif
+#ifdef __EMX__
+  {
+    gchar *q = strrchr (file_name, '\\');
+    if (base == NULL || (q != NULL && q > base))
+	base = q;
+  }
+#endif
   if (!base)
     {
-#ifdef G_OS_WIN32
+#if defined G_OS_WIN32 || defined __EMX__
       if (g_ascii_isalpha (file_name[0]) && file_name[1] == ':')
 	{
 	  gchar drive_colon_dot[4];
@@ -737,7 +751,7 @@
   while (base > file_name && G_IS_DIR_SEPARATOR (*base))
     base--;
 
-#ifdef G_OS_WIN32
+#if defined G_OS_WIN32 || defined __EMX__
   /* base points to the char before the last slash.
    *
    * In case file_name is the root of a drive (X:\) or a child of the
@@ -835,6 +849,9 @@
   gchar *dir = NULL;
   static gulong max_len = 0;
 
+#ifdef __EMX__
+#define getcwd(a,b) _getcwd2(a,b)
+#endif
   if (max_len == 0) 
     max_len = (G_PATH_LENGTH == -1) ? 2048 : G_PATH_LENGTH;
   
@@ -2514,6 +2531,10 @@
 
 #endif /* G_OS_WIN32 */
 
+#ifdef __EMX__
+extern char *__XOS2RedirRoot (char *fname);
+#endif
+
 G_CONST_RETURN gchar *
 _glib_gettext (const gchar *str)
 {
@@ -2521,7 +2542,11 @@
 
   if (!_glib_gettext_initialized)
     {
+#ifndef __EMX__
       bindtextdomain(GETTEXT_PACKAGE, GLIB_LOCALE_DIR);
+#else
+      bindtextdomain(GETTEXT_PACKAGE, __XOS2RedirRoot (GLIB_LOCALE_DIR));
+#endif
 #    ifdef HAVE_BIND_TEXTDOMAIN_CODESET
       bind_textdomain_codeset (GETTEXT_PACKAGE, "UTF-8");
 #    endif
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/glib/gutils.h glib-2.6.5.os2/glib/gutils.h
--- glib-2.6.5/glib/gutils.h	Tue Apr 19 10:06:04 2005
+++ glib-2.6.5.os2/glib/gutils.h	Sun Jul 31 17:14:58 2005
@@ -44,8 +44,15 @@
 #define G_SEARCHPATH_SEPARATOR ';'
 #define G_SEARCHPATH_SEPARATOR_S ";"
 
-#else  /* !G_OS_WIN32 */
+#elif defined(__EMX__)  /* !G_OS_WIN32 */
 
+#define G_DIR_SEPARATOR '/'
+#define G_DIR_SEPARATOR_S "/"
+#define G_IS_DIR_SEPARATOR(c) ((c) == G_DIR_SEPARATOR || (c) == '\\')
+#define G_SEARCHPATH_SEPARATOR ';'
+#define G_SEARCHPATH_SEPARATOR_S ";"
+
+#else
 /* Unix */
 
 #define G_DIR_SEPARATOR '/'
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/glib/libcharset/localcharset.c glib-2.6.5.os2/glib/libcharset/localcharset.c
--- glib-2.6.5/glib/libcharset/localcharset.c	Sun Oct 24 03:37:42 2004
+++ glib-2.6.5.os2/glib/libcharset/localcharset.c	Thu Jul 21 19:51:50 2005
@@ -248,7 +248,7 @@
 const char *
 _g_locale_charset_raw (void)
 {
-  const char *codeset;
+  const char *codeset = NULL;
 
 #if !(defined WIN32 || defined OS2)
 
@@ -331,21 +331,21 @@
 	      buf [modifier - dot] = '\0';
 	      return buf;
 	    }
-	}
 
-      /* Resolve through the charset.alias file.  */
-      codeset = locale;
-    }
-  else
-    {
-      /* OS/2 has a function returning the locale's codepage as a number.  */
-      if (DosQueryCp (sizeof (cp), cp, &cplen))
-	codeset = "";
-      else
-	{
-	  sprintf (buf, "CP%u", cp[0]);
-	  codeset = buf;
+          /* Resolve through the charset.alias file.  */
+          codeset = locale;
 	}
+      else
+        {
+          /* OS/2 has a function returning the locale's codepage as a number.  */
+          if (DosQueryCp (sizeof (cp), cp, &cplen))
+	    codeset = "";
+          else
+	    {
+	      sprintf (buf, "CP%u", cp[0]);
+	      codeset = buf;
+	    }
+        }
     }
 
 #endif
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/glib/Makefile.am glib-2.6.5.os2/glib/Makefile.am
--- glib-2.6.5/glib/Makefile.am	Mon Mar 14 05:02:06 2005
+++ glib-2.6.5.os2/glib/Makefile.am	Sun Jul 31 17:14:58 2005
@@ -123,6 +123,7 @@
 	giowin32.c	\
 	gspawn.c	\
 	gspawn-win32.c	\
+	gspawn-os2.c	\
 	gwin32.c
 
 glibincludedir=$(includedir)/glib-2.0
@@ -225,9 +226,15 @@
 libglib_2_0_la_LIBADD = libcharset/libcharset.la $(printf_la) @GIO@ @GSPAWN@ @PLATFORMDEP@ @G_LIB_WIN32_RESOURCE@ @ICONV_LIBS@ @G_LIBS_EXTRA@ 
 libglib_2_0_la_DEPENDENCIES = libcharset/libcharset.la $(printf_la) @GIO@ @GSPAWN@ @PLATFORMDEP@ @G_LIB_WIN32_RESOURCE@ @GLIB_DEF@
 
+if !OS_OS2
 libglib_2_0_la_LDFLAGS = \
 	-version-info $(LT_CURRENT):$(LT_REVISION):$(LT_AGE) \
 	-export-dynamic $(no_undefined) $(export_symbols)
+else
+libglib_2_0_la_LDFLAGS = \
+	-version-info $(LT_CURRENT) $(LT_REVISION) $(LT_AGE) \
+	-export-dynamic $(no_undefined) $(export_symbols)
+endif
 
 if OS_WIN32
 bin_PROGRAMS = gspawn-win32-helper
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/gmodule/gmodule-2.0.os2name glib-2.6.5.os2/gmodule/gmodule-2.0.os2name
--- glib-2.6.5/gmodule/gmodule-2.0.os2name	Thu Jan  1 00:00:00 1970
+++ glib-2.6.5.os2/gmodule/gmodule-2.0.os2name	Thu Jul 21 19:51:52 2005
@@ -0,0 +1 @@
+gmodule2
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/gmodule/gmodule.c glib-2.6.5.os2/gmodule/gmodule.c
--- glib-2.6.5/gmodule/gmodule.c	Sun Jan  2 17:03:56 2005
+++ glib-2.6.5.os2/gmodule/gmodule.c	Thu Jul 21 19:51:52 2005
@@ -144,6 +144,9 @@
 
 /* --- include platform specifc code --- */
 #define	SUPPORT_OR_RETURN(rv)	{ g_module_set_error (NULL); }
+#ifdef __EMX__
+#include "gmodule-os2.c"
+#else
 #if	(G_MODULE_IMPL == G_MODULE_IMPL_DL)
 #include "gmodule-dl.c"
 #elif	(G_MODULE_IMPL == G_MODULE_IMPL_DLD)
@@ -188,6 +191,7 @@
   return NULL;
 }
 #endif	/* no implementation */
+#endif  /* !__EMX__ */
 
 /* --- functions --- */
 gboolean
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/gmodule/Makefile.am glib-2.6.5.os2/gmodule/Makefile.am
--- glib-2.6.5/gmodule/Makefile.am	Wed Mar  9 03:23:10 2005
+++ glib-2.6.5.os2/gmodule/Makefile.am	Thu Jul 21 19:51:52 2005
@@ -71,10 +71,17 @@
 endif
 
 libgmodule_2_0_la_SOURCES = gmodule.c
+if !OS_OS2
 libgmodule_2_0_la_LDFLAGS = \
 	$(G_MODULE_LDFLAGS) \
 	-version-info $(LT_CURRENT):$(LT_REVISION):$(LT_AGE) \
 	-export-dynamic $(no_undefined) $(export_symbols)
+else
+libgmodule_2_0_la_LDFLAGS = \
+	$(G_MODULE_LDFLAGS) \
+	-version-info $(LT_CURRENT) $(LT_REVISION) $(LT_AGE) \
+	-export-dynamic $(no_undefined) $(export_symbols)
+endif
 
 libgmodule_2_0_la_LIBADD = $(G_MODULE_WIN32_RESOURCE) $(G_MODULE_LIBS_EXTRA) $(G_MODULE_LIBS) $(libglib)
 
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/gobject/glib-genmarshal.c glib-2.6.5.os2/gobject/glib-genmarshal.c
--- glib-2.6.5/gobject/glib-genmarshal.c	Wed Jul 21 19:59:16 2004
+++ glib-2.6.5.os2/gobject/glib-genmarshal.c	Thu Jul 21 19:51:52 2005
@@ -613,7 +613,11 @@
   if (files)
     files = g_slist_reverse (files);
   else
+#ifndef __EMX__
     files = g_slist_prepend (files, "/dev/stdin");
+#else
+    files = g_slist_prepend (files, "con");
+#endif
 
   /* setup auxillary structs */
   scanner = g_scanner_new (&scanner_config_template);
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/gobject/gobject-2.0.os2name glib-2.6.5.os2/gobject/gobject-2.0.os2name
--- glib-2.6.5/gobject/gobject-2.0.os2name	Thu Jan  1 00:00:00 1970
+++ glib-2.6.5.os2/gobject/gobject-2.0.os2name	Thu Jul 21 19:51:52 2005
@@ -0,0 +1 @@
+gobject2
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/gobject/Makefile.am glib-2.6.5.os2/gobject/Makefile.am
--- glib-2.6.5/gobject/Makefile.am	Wed Apr  6 17:11:48 2005
+++ glib-2.6.5.os2/gobject/Makefile.am	Thu Jul 21 19:51:52 2005
@@ -77,9 +77,15 @@
 
 # libtool stuff: set version and export symbols for resolving
 libgobjectincludedir = $(includedir)/glib-2.0/gobject
+if !OS_OS2
 libgobject_2_0_la_LDFLAGS = \
   -version-info $(LT_CURRENT):$(LT_REVISION):$(LT_AGE)	\
   -export-dynamic $(no_undefined) $(export_symbols)
+else
+libgobject_2_0_la_LDFLAGS = \
+  -version-info $(LT_CURRENT) $(LT_REVISION) $(LT_AGE)	\
+  -export-dynamic $(no_undefined) $(export_symbols)
+endif
 
 libgobject_2_0_la_LIBADD = $(G_OBJECT_WIN32_RESOURCE) $(libglib)
 
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/gthread/gthread-2.0.os2name glib-2.6.5.os2/gthread/gthread-2.0.os2name
--- glib-2.6.5/gthread/gthread-2.0.os2name	Thu Jan  1 00:00:00 1970
+++ glib-2.6.5.os2/gthread/gthread-2.0.os2name	Thu Jul 21 19:51:52 2005
@@ -0,0 +1 @@
+gthread2
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/gthread/Makefile.am glib-2.6.5.os2/gthread/Makefile.am
--- glib-2.6.5/gthread/Makefile.am	Sat Mar  6 08:37:44 2004
+++ glib-2.6.5.os2/gthread/Makefile.am	Thu Jul 21 19:51:52 2005
@@ -55,9 +55,15 @@
 endif
 
 libgthread_2_0_la_SOURCES = gthread-impl.c
+if !OS_OS2
 libgthread_2_0_la_LDFLAGS = \
 	-version-info $(LT_CURRENT):$(LT_REVISION):$(LT_AGE) \
 	-export-dynamic $(no_undefined) $(export_symbols)
+else
+libgthread_2_0_la_LDFLAGS = \
+	-version-info $(LT_CURRENT) $(LT_REVISION) $(LT_AGE) \
+	-export-dynamic $(no_undefined) $(export_symbols)
+endif
 
 libgthread_2_0_la_LIBADD = $(G_THREAD_WIN32_RESOURCE) $(G_THREAD_LIBS_EXTRA) $(G_THREAD_LIBS_FOR_GTHREAD) $(libglib)
 
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/m4macros/glib-gettext.m4 glib-2.6.5.os2/m4macros/glib-gettext.m4
--- glib-2.6.5/m4macros/glib-gettext.m4	Fri Mar 11 19:01:04 2005
+++ glib-2.6.5.os2/m4macros/glib-gettext.m4	Thu Jul 21 19:51:52 2005
@@ -74,12 +74,14 @@
   IFS="${IFS= 	}"; ac_save_ifs="$IFS"; IFS="${IFS}:"
   for ac_dir in ifelse([$5], , $PATH, [$5]); do
     test -z "$ac_dir" && ac_dir=.
-    if test -f $ac_dir/$ac_word; then
-      if [$3]; then
-	ac_cv_path_$1="$ac_dir/$ac_word"
-	break
+    for ac_exec_ext in '' $ac_executable_extensions; do
+      if test -f $ac_dir/$ac_word$ac_exec_ext; then
+        if [$3]; then
+	  ac_cv_path_$1="$ac_dir/$ac_word$ac_exec_ext"
+	  break
+        fi
       fi
-    fi
+    done
   done
   IFS="$ac_save_ifs"
 dnl If no 4th arg is given, leave the cache variable unset,
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/setenv.cmd glib-2.6.5.os2/setenv.cmd
--- glib-2.6.5/setenv.cmd	Thu Jan  1 00:00:00 1970
+++ glib-2.6.5.os2/setenv.cmd	Thu Jul 21 20:37:12 2005
@@ -0,0 +1,12 @@
+setlocal
+call ..\setenv302.cmd
+path=e:\usr\bin;e:\perl\bin;e:\usr\X11R6\bin;%PATH%
+set PERLLIB_PREFIX=L:/Perl/lib;E:/Perl/lib
+set beginlibpath=e:\x11_latest\glib-2.6.5\glib\.libs;e:\x11_latest\glib-2.6.5\gmodule\.libs;e:\x11_latest\glib-2.6.5\gobject\.libs;e:\x11_latest\glib-2.6.5\gthread\.libs;%BEGINLIBPATH%e:\usr\X11R6\lib;
+set ETC=
+set C_INCLUDE_PATH=e:/usr/include;%C_INCLUDE_PATH%
+set LIBRARY_PATH=e:/usr/lib;%LIBRARY_PATH%
+set CONFIG_SHELL=bash.exe
+set EMXSHELL=bash.exe
+bash.exe
+endlocal
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/tests/dirname-test.c glib-2.6.5.os2/tests/dirname-test.c
--- glib-2.6.5/tests/dirname-test.c	Sun Mar 21 22:43:12 2004
+++ glib-2.6.5.os2/tests/dirname-test.c	Thu Jul 21 19:51:52 2005
@@ -73,7 +73,7 @@
     { "c///", "c" },
     { "/a/b", "/a" },
     { "/a/b/", "/a/b" },
-#ifdef G_OS_WIN32
+#if defined(G_OS_WIN32) || defined(__EMX__)
     { "\\", "\\" },
     { ".\\\\\\\\", "." },
     { ".\\/\\/", "." },
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/tests/iochannel-test.c glib-2.6.5.os2/tests/iochannel-test.c
--- glib-2.6.5/tests/iochannel-test.c	Wed Oct 16 00:39:16 2002
+++ glib-2.6.5.os2/tests/iochannel-test.c	Thu Jul 21 19:51:52 2005
@@ -22,7 +22,11 @@
     glong wlength = 0;
     gsize length_out;
     gboolean block;
+#ifndef __EMX__
     const gchar encoding[] = "EUC-JP";
+#else
+    const gchar encoding[] = "KOI8-R";
+#endif
     GIOStatus status;
     GIOFlags flags;
 
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/tests/libmoduletestplugin_a.c glib-2.6.5.os2/tests/libmoduletestplugin_a.c
--- glib-2.6.5/tests/libmoduletestplugin_a.c	Thu Jul  4 17:19:30 2002
+++ glib-2.6.5.os2/tests/libmoduletestplugin_a.c	Thu Jul 21 19:51:52 2005
@@ -30,7 +30,7 @@
 #include	<gmodule.h>
 #include	<stdlib.h>
 
-G_MODULE_EXPORT gchar* gplugin_a_state;
+G_MODULE_EXPORT gchar* gplugin_a_state = NULL;
 
 G_MODULE_EXPORT void
 gplugin_a_func (void)
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/tests/libmoduletestplugin_b.c glib-2.6.5.os2/tests/libmoduletestplugin_b.c
--- glib-2.6.5/tests/libmoduletestplugin_b.c	Thu Jul  4 17:19:30 2002
+++ glib-2.6.5.os2/tests/libmoduletestplugin_b.c	Thu Jul 21 19:51:52 2005
@@ -29,7 +29,7 @@
 
 #include        <gmodule.h>
 
-G_MODULE_EXPORT gchar* gplugin_b_state;
+G_MODULE_EXPORT gchar* gplugin_b_state = NULL;
 
 G_MODULE_EXPORT const gchar*
 g_module_check_init (GModule *module)
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/tests/Makefile.am glib-2.6.5.os2/tests/Makefile.am
--- glib-2.6.5/tests/Makefile.am	Tue Feb  8 16:15:16 2005
+++ glib-2.6.5.os2/tests/Makefile.am	Thu Jul 21 19:51:52 2005
@@ -9,6 +9,11 @@
 libgmodule = $(top_builddir)/gmodule/libgmodule-2.0.la
 libgobject = $(top_builddir)/gobject/libgobject-2.0.la
 
+if OS_OS2
+libadd_libgmodule = $(libgmodule)
+libadd_libglib = $(libglib)
+endif
+
 if PLATFORM_WIN32
 libadd_libgmodule = $(libgmodule)
 libadd_libglib = $(libglib)
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/tests/module-test.c glib-2.6.5.os2/tests/module-test.c
--- glib-2.6.5/tests/module-test.c	Fri Jan  9 15:40:30 2004
+++ glib-2.6.5.os2/tests/module-test.c	Thu Jul 21 19:51:52 2005
@@ -94,12 +94,14 @@
 
   /* module handles */
   
+#ifndef __EMX__
   module_self = g_module_open (NULL, G_MODULE_BIND_LAZY);
   if (!module_self)
     g_error ("error: %s", g_module_error ());
 
   if (!g_module_symbol (module_self, "g_module_close", (gpointer *) &f_self))
     g_error ("error: %s", g_module_error ());
+#endif
 
   module_a = g_module_open (plugin_a, G_MODULE_BIND_LAZY);
   if (!module_a)
@@ -139,9 +141,11 @@
   /* get and call globally clashing functions
    */
  
+#ifndef __EMX__
   if (!g_module_symbol (module_self, "g_clash_func", (gpointer *) &f_self))
     g_error ("error: %s", g_module_error ());
   test_states (NULL, NULL, NULL);
+#endif
 
   if (!g_module_symbol (module_a, "g_clash_func", (gpointer *) &f_a))
     g_error ("error: %s", g_module_error ());
@@ -151,8 +155,10 @@
     g_error ("error: %s", g_module_error ());
   test_states (NULL, NULL, NULL);
  
+#ifndef __EMX__
   f_self ();
   test_states ("global clash", NULL, NULL);
+#endif
   
   f_a ();
   test_states (NULL, "global clash", NULL);
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/tests/moduletestplugin_a.os2name glib-2.6.5.os2/tests/moduletestplugin_a.os2name
--- glib-2.6.5/tests/moduletestplugin_a.os2name	Thu Jan  1 00:00:00 1970
+++ glib-2.6.5.os2/tests/moduletestplugin_a.os2name	Thu Jul 21 19:51:52 2005
@@ -0,0 +1 @@
+mod_pl_a
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/tests/moduletestplugin_b.os2name glib-2.6.5.os2/tests/moduletestplugin_b.os2name
--- glib-2.6.5/tests/moduletestplugin_b.os2name	Thu Jan  1 00:00:00 1970
+++ glib-2.6.5.os2/tests/moduletestplugin_b.os2name	Thu Jul 21 19:51:52 2005
@@ -0,0 +1 @@
+mod_pl_b
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/tests/run-markup-tests.sh glib-2.6.5.os2/tests/run-markup-tests.sh
--- glib-2.6.5/tests/run-markup-tests.sh	Mon Jan 24 18:34:00 2005
+++ glib-2.6.5.os2/tests/run-markup-tests.sh	Thu Jul 21 19:51:52 2005
@@ -16,7 +16,8 @@
 error_out=/dev/null
 if [ "$1" = "-v" ]; then
   verbose=1
-  error_out=/dev/stderr
+#  error_out=/dev/stderr
+  error_out=con
 fi  
 for I in ${srcdir:-.}/markups/fail-*.gmarkup; do
   echo_v "Parsing $I, should fail"
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/tests/spawn-test.c glib-2.6.5.os2/tests/spawn-test.c
--- glib-2.6.5/tests/spawn-test.c	Sun Mar 20 21:06:48 2005
+++ glib-2.6.5.os2/tests/spawn-test.c	Thu Jul 21 20:47:50 2005
@@ -83,8 +83,12 @@
   else
     {
       g_assert (output != NULL);
-      
+
+#ifndef __EMX__
       if (strcmp (output, "hello\n") != 0)
+#else
+      if (strcmp (output, "hello\r\n") != 0)
+#endif
         {
           printf ("output was '%s', should have been 'hello'\n",
                   output);
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/tests/unicode-encoding.c glib-2.6.5.os2/tests/unicode-encoding.c
--- glib-2.6.5/tests/unicode-encoding.c	Wed Mar 31 04:19:10 2004
+++ glib-2.6.5.os2/tests/unicode-encoding.c	Thu Jul 21 19:51:52 2005
@@ -195,7 +195,7 @@
       gint n_chars;
       gchar *utf8_result;
 
-#ifdef G_PLATFORM_WIN32
+#if defined G_PLATFORM_WIN32 || defined __EMX__
 #define TARGET "UTF-16LE"
 #else
 #define TARGET "UTF-16"
diff -ruN -x configure -x ltmain.sh -x aclocal.m4 -x config.guess -x config.sub -x Makefile.in glib-2.6.5/tests/uri-test.c glib-2.6.5.os2/tests/uri-test.c
--- glib-2.6.5/tests/uri-test.c	Fri Oct 22 21:51:28 2004
+++ glib-2.6.5.os2/tests/uri-test.c	Thu Jul 21 19:51:52 2005
@@ -47,7 +47,7 @@
   { "/etc", NULL, "file:///etc"},
   { "/etc", "", "file:///etc"},
   { "/etc", "otherhost", "file://otherhost/etc"},
-#ifdef G_OS_WIN32
+#if defined G_OS_WIN32 || defined __EMX__
   { "/etc", "localhost", "file:///etc"},
   { "c:\\windows", NULL, "file:///c:/windows"},
   { "c:\\windows", "localhost", "file:///c:/windows"},
@@ -76,7 +76,7 @@
   { "/ABCDEFGHIJKLMNOPQRSTUVWXYZ", NULL, "file:///ABCDEFGHIJKLMNOPQRSTUVWXYZ"},
   { "/abcdefghijklmnopqrstuvwxyz", NULL, "file:///abcdefghijklmnopqrstuvwxyz"},
   { "/-_.!~*'()", NULL, "file:///-_.!~*'()"},
-#ifdef G_OS_WIN32
+#if defined G_OS_WIN32 || defined __EMX__
   /* As '\\' is a path separator on Win32, it gets turned into '/' in the URI */
   { "/\"#%<>[\\]^`{|}\x7F", NULL, "file:///%22%23%25%3C%3E%5B/%5D%5E%60%7B%7C%7D%7F"},
 #else
@@ -114,7 +114,7 @@
 from_uri_tests[] = {
   { "file:///etc", "/etc"},
   { "file:/etc", "/etc"},
-#ifdef G_OS_WIN32
+#if defined G_OS_WIN32 || defined __EMX__
   /* On Win32 we don't return "localhost" hostames, just in case
    * it isn't recognized anyway.
    */
@@ -139,7 +139,7 @@
   { "http://www.yahoo.com/", NULL, NULL, G_CONVERT_ERROR_BAD_URI},
   { "file:////etc", "//etc"},
   { "file://///etc", "///etc"},
-#ifdef G_OS_WIN32
+#if defined G_OS_WIN32 || defined __EMX__
   /* URIs with backslashes come from some nonstandard application, but accept them anyhow */
   { "file:///c:\\foo", "c:\\foo"},
   { "file:///c:/foo\\bar", "c:\\foo\\bar"},
@@ -269,7 +269,7 @@
 	}
       else
 	{
-#ifdef G_OS_WIN32
+#if defined G_OS_WIN32
 	  gchar *slash, *p;
 
 	  p = from_uri_tests[i].expected_filename = g_strdup (from_uri_tests[i].expected_filename);
@@ -362,7 +362,7 @@
 	{
 	  g_print ("roundtrip test %d failed, hostname modified: "
 		     " expected \"%s\", but got \"%s\"\n",
-		   i, to_uri_tests[i].hostname, hostname);
+		   i, to_uri_tests[i].hostname ? to_uri_tests[i].hostname : "", hostname ? hostname : "");
 	  any_failed = TRUE;
 	}
 
