[git] GPG-ERROR - branch, master, updated. libgpg-error-1.27-234-g513415c

by Werner Koch cvs at cvs.gnupg.org
Tue Nov 28 16:48:23 CET 2017


This is an automated email from the git hooks/post-receive script. It was
generated because a ref change was pushed to the repository containing
the project "Error codes used by GnuPG et al.".

The branch, master has been updated
       via  513415c71781ab400ebb01f6b4cf2984ec6b1757 (commit)
       via  930d27ba6b1205395add0c79139e62355a1d5b62 (commit)
       via  4a2538e69dd35377bce0fb584f72322c69a111b3 (commit)
       via  241e9a73891fcd12f124aab1a299c2cf4f8eebc4 (commit)
       via  b67daca506991507cea9d383df7faf95117e58a6 (commit)
      from  97b0881216af24f2a46c11650e23691cff9cb12a (commit)

Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.

- Log -----------------------------------------------------------------
commit 513415c71781ab400ebb01f6b4cf2984ec6b1757
Author: Werner Koch <wk at gnupg.org>
Date:   Tue Nov 28 16:36:12 2017 +0100

    core: Change new functions to return gpg_err_code_t.
    
    * src/gpg-error.h.in (gpgrt_sentenv, gpgrt_mkdir, gpgrt_chdir): Change
    return type to gpg_err_code_t.
    * src/sysutils.c (_gpgrt_setenv): Implement that.
    (_gpgrt_mkdir): Ditto.
    (_gpgrt_chdir): Ditto.
    * gpgscm/ffi.c (do_setenv, do_mkdir): Adjust for this change.
    --
    
    The functions are already a bit different and thus it is useful to let
    them return a gpg-error style error code and don't let the user
    implement that for each call.
    
    Signed-off-by: Werner Koch <wk at gnupg.org>

diff --git a/gpgscm/ffi.c b/gpgscm/ffi.c
index 51de63f..2f3e2f7 100644
--- a/gpgscm/ffi.c
+++ b/gpgscm/ffi.c
@@ -243,6 +243,7 @@ static pointer
 do_setenv (scheme *sc, pointer args)
 {
   FFI_PROLOG ();
+  gpg_err_code_t ec;
   char *name;
   char *value;
   int overwrite;
@@ -250,8 +251,8 @@ do_setenv (scheme *sc, pointer args)
   FFI_ARG_OR_RETURN (sc, char *, value, string, args);
   FFI_ARG_OR_RETURN (sc, int, overwrite, bool, args);
   FFI_ARGS_DONE_OR_RETURN (sc, args);
-  if (gpgrt_setenv (name, value, overwrite))
-    FFI_RETURN_ERR (sc, gpg_error_from_syserror ());
+  if ((ec = gpgrt_setenv (name, value, overwrite)))
+    FFI_RETURN_ERR (sc, ec);
   FFI_RETURN (sc);
 }
 
@@ -490,13 +491,15 @@ static pointer
 do_mkdir (scheme *sc, pointer args)
 {
   FFI_PROLOG ();
+  gpg_err_code_t ec;
   char *name;
   char *mode;
   FFI_ARG_OR_RETURN (sc, char *, name, string, args);
   FFI_ARG_OR_RETURN (sc, char *, mode, string, args);
   FFI_ARGS_DONE_OR_RETURN (sc, args);
-  if (gpgrt_mkdir (name, mode) == -1)
-    FFI_RETURN_ERR (sc, gpg_error_from_syserror ());
+  ec = gpgrt_mkdir (name, mode);
+  if (ec)
+    FFI_RETURN_ERR (sc, ec);
   FFI_RETURN (sc);
 }
 
diff --git a/src/gpg-error.h.in b/src/gpg-error.h.in
index dffde2e..20d196a 100644
--- a/src/gpg-error.h.in
+++ b/src/gpg-error.h.in
@@ -453,14 +453,15 @@ void gpgrt_free (void *a);
 char *gpgrt_getenv (const char *name);
 
 /* A setenv and a unsetenv replacement.*/
-int gpgrt_setenv (const char *name, const char *value, int overwrite);
+gpg_err_code_t gpgrt_setenv (const char *name,
+                             const char *value, int overwrite);
 #define gpgrt_unsetenv(n) gpgrt_setenv ((n), NULL, 1)
 
 /* A wrapper around mkdir using a string for the mode.  */
-int gpgrt_mkdir (const char *name, const char *modestr);
+gpg_err_code_t gpgrt_mkdir (const char *name, const char *modestr);
 
 /* A simple wrapper around chdir.  */
-int gpgrt_chdir (const char *name);
+gpg_err_code_t gpgrt_chdir (const char *name);
 
 /* Return the current WD as a malloced string.  */
 char *gpgrt_getcwd (void);
diff --git a/src/gpgrt-int.h b/src/gpgrt-int.h
index b2f87b9..dc1305e 100644
--- a/src/gpgrt-int.h
+++ b/src/gpgrt-int.h
@@ -564,13 +564,14 @@ char *_gpgrt_getenv (const char *name);
 
 /* A setenv variant which can be used for unsetenv by setting VALUE to
  * NULL and OVERRIDE to true.  */
-int _gpgrt_setenv (const char *name, const char *value, int overwrite);
+gpg_err_code_t _gpgrt_setenv (const char *name,
+                              const char *value, int overwrite);
 
 /* A wrapper around mkdir using a string for the mode (permissions).  */
-int _gpgrt_mkdir (const char *name, const char *modestr);
+gpg_err_code_t _gpgrt_mkdir (const char *name, const char *modestr);
 
 /* A simple wrapper around chdir.  */
-int _gpgrt_chdir (const char *name);
+gpg_err_code_t _gpgrt_chdir (const char *name);
 
 /* Return the current WD as a malloced string.  */
 char *_gpgrt_getcwd (void);
diff --git a/src/sysutils.c b/src/sysutils.c
index 70c2dc3..1f2c293 100644
--- a/src/sysutils.c
+++ b/src/sysutils.c
@@ -118,14 +118,11 @@ _gpgrt_getenv (const char *name)
 /* Wrapper around setenv so that we can have the same function in
  * Windows and Unix.  In contrast to the standard setenv passing a
  * VALUE as NULL and setting OVERWRITE will remove the envvar.  */
-int
+gpg_err_code_t
 _gpgrt_setenv (const char *name, const char *value, int overwrite)
 {
   if (!name || !*name || strchr (name, '='))
-    {
-      _gpg_err_set_errno (EINVAL);
-      return -1;
-    }
+    return GPG_ERR_EINVAL;
 
 #ifdef HAVE_W32_SYSTEM
   /* Windows maintains (at least) two sets of environment variables.
@@ -143,34 +140,30 @@ _gpgrt_setenv (const char *name, const char *value, int overwrite)
     if (!value && overwrite)
       {
         if (!SetEnvironmentVariable (name, NULL))
-          {
-            _gpg_err_set_errno (EINVAL);
-            return -1;
-          }
+          return GPG_ERR_EINVAL;
         if (getenv (name))
           {
             /* Ugly: Leaking memory.  */
             buf = _gpgrt_strdup (name);
             if (!buf)
-              return -1;
-            return putenv (buf);
+              return _gpg_err_code_from_syserror ();
+            if (putenv (buf))
+              return _gpg_err_code_from_syserror ();
           }
         return 0;
       }
 
     exists = GetEnvironmentVariable (name, tmpbuf, sizeof tmpbuf);
     if ((! exists || overwrite) && !SetEnvironmentVariable (name, value))
-      {
-        _gpg_err_set_errno (EINVAL); /* (Might also be ENOMEM.) */
-        return -1;
-      }
+      return GPG_ERR_EINVAL; /* (Might also be ENOMEM.) */
     if (overwrite || !getenv (name))
       {
         /* Ugly: Leaking memory.  */
         buf = _gpgrt_strconcat (name, "=", value, NULL);
         if (!buf)
-          return -1;
-        return putenv (buf);
+          return _gpg_err_code_from_syserror ();
+        if (putenv (buf))
+          return _gpg_err_code_from_syserror ();
       }
     return 0;
   }
@@ -181,9 +174,17 @@ _gpgrt_setenv (const char *name, const char *value, int overwrite)
 
   {
     if (!value && overwrite)
-      return unsetenv (name);
+      {
+        if (unsetenv (name))
+          return _gpg_err_code_from_syserror ();
+      }
     else
-      return setenv (name, value, overwrite);
+      {
+        if (setenv (name, value, overwrite))
+          return _gpg_err_code_from_syserror ();
+      }
+
+    return 0;
   }
 
 # else /*!HAVE_SETENV*/
@@ -200,16 +201,18 @@ _gpgrt_setenv (const char *name, const char *value, int overwrite)
           {
             buf = _gpgrt_strdup (name);
             if (!buf)
+              return _gpg_err_code_from_syserror ();
+            if (putenv (buf))
               return -1;
-            return putenv (buf);
           }
       }
     else if (overwrite || !getenv (name))
       {
         buf = _gpgrt_strconcat (name, "=", value, NULL);
         if (!buf)
-          return -1;
-        return putenv (buf);
+          return _gpg_err_code_from_syserror ();
+        if (putenv (buf))
+          return _gpg_err_code_from_syserror ();
       }
 
     return 0;
@@ -264,7 +267,7 @@ modestr_to_mode (const char *modestr)
  * the second for the group and the third for all others.  If the
  * string is shorter than above the missing mode characters are meant
  * to be not set.  */
-int
+gpg_err_code_t
 _gpgrt_mkdir (const char *name, const char *modestr)
 {
 #ifdef HAVE_W32CE_SYSTEM
@@ -273,11 +276,11 @@ _gpgrt_mkdir (const char *name, const char *modestr)
 
   wname = utf8_to_wchar (name);
   if (!wname)
-    return -1;
+    return _gpg_err_code_from_syserror ();
   if (!CreateDirectoryW (wname, NULL))
     {
       xfree (wname);
-      return -1;  /* ERRNO is automagically provided by gpg-error.h.  */
+      return _gpg_err_code_from_syserror ();
     }
   xfree (wname);
   return 0;
@@ -286,19 +289,25 @@ _gpgrt_mkdir (const char *name, const char *modestr)
   /* Note: In the case of W32 we better use CreateDirectory and try to
      set appropriate permissions.  However using mkdir is easier
      because this sets ERRNO.  */
-  return mkdir (name);
+  if (mkdir (name))
+    return _gpg_err_code_from_syserror ();
+  return 0;
 #else
-  return mkdir (name, modestr_to_mode (modestr));
+  if (mkdir (name, modestr_to_mode (modestr)))
+    return _gpg_err_code_from_syserror ();
+  return 0;
 #endif
 }
 
 
 /* A simple wrapper around chdir.  NAME is expected to be utf8
  * encoded.  */
-int
+gpg_err_code_t
 _gpgrt_chdir (const char *name)
 {
-  return chdir (name);
+  if (chdir (name))
+    return _gpg_err_code_from_syserror ();
+  return 0;
 }
 
 
diff --git a/src/visibility.c b/src/visibility.c
index c0cab3d..0f6d159 100644
--- a/src/visibility.c
+++ b/src/visibility.c
@@ -763,25 +763,26 @@ gpgrt_getenv (const char *name)
   return _gpgrt_getenv (name);
 }
 
-int
+gpg_err_code_t
 gpgrt_setenv (const char *name, const char *value, int overwrite)
 {
   return _gpgrt_setenv (name, value, overwrite);
 }
 
-int
+gpg_err_code_t
 gpgrt_mkdir (const char *name, const char *modestr)
 {
   return _gpgrt_mkdir (name, modestr);
 }
 
-int
+gpg_err_code_t
 gpgrt_chdir (const char *name)
 {
   return _gpgrt_chdir (name);
 }
 
-char *gpgrt_getcwd (void)
+char *
+gpgrt_getcwd (void)
 {
   return _gpgrt_getcwd ();
 }

commit 930d27ba6b1205395add0c79139e62355a1d5b62
Author: Werner Koch <wk at gnupg.org>
Date:   Tue Nov 28 16:17:23 2017 +0100

    gpgscm: Some adjustments for use in gpgrt.
    
    * gpgscm/Makefile.am: Remove cruft leftover from GnuPG.  Link to the
    just build libgpg-error.
    * gpgscm/private.h: Include gpgrt.h and provide i18n macros.
    (xfree, xtrymalloc, xtrycalloc, xtryrealloc): New macros.
    (xmalloc, xstrdup): New inline functions.
    * gpgscm/main.c: Remove inclusion of gcrypt.h and gpg-error.h.  Remove
    all other gnupg specific headers.
    (opts, parse_arguments): Temporary comment out.
    (main): Adjust for use with gpgrt.  Temporary comment out some stuff.
    * gpgscm/ffi-private.h: Include local gpgrt.h instead of gpg-error.h.
    * gpgscm/ffi.h: Ditto.
    * gpgscm/ffi.c: Remove gpg-error.h and headers from GnuPG.
    (do_getenv): Use gpgrt_getenv.
    (do_setenv): Use gpgrt_setenv.
    (do_mkdtemp): Temporary return an error.
    (unlink_recursively): Use gpgrt_bsprintf.
    (do_getcwd): Use gpgrt_getcwd.
    (do_mkdir): Use gpgrt_mkdir.
    (do_get_isotime): Temporary return an error.
    (do_get_time): Directly use time().
    --
    
    Note that this does not yet compile because the spawn functions from
    GnuPG are missing.  There are two other problems as well:
    
     - We don't have GnuPG's isotime fucntions.  We need to see whether we
       want to support them in gpgrt.  That might be useful in libksba.
    
     - gpgrt_mkdtemp does not work.  We do not want to link to Libgcrypt,
       which is the way mkdtemp was written for GnuPG.  We should get a
       more straight implementation.
    
    Signed-off-by: Werner Koch <wk at gnupg.org>

diff --git a/gpgscm/Makefile.am b/gpgscm/Makefile.am
index 59e1924..43741f2 100644
--- a/gpgscm/Makefile.am
+++ b/gpgscm/Makefile.am
@@ -31,9 +31,6 @@ EXTRA_DIST = \
 	gnupg.scm \
 	time.scm
 
-AM_CPPFLAGS = -I$(top_srcdir)/common
-include $(top_srcdir)/am/cmacros.am
-
 AM_CFLAGS =
 
 CLEANFILES =
@@ -41,23 +38,17 @@ CLEANFILES =
 bin_PROGRAMS = gpgscm
 noinst_PROGRAMS = t-child
 
-common_libs = ../$(libcommon)
-commonpth_libs = ../$(libcommonpth)
-
-gpgscm_CFLAGS = -imacros scheme-config.h \
-	$(LIBGCRYPT_CFLAGS) $(LIBASSUAN_CFLAGS) $(GPG_ERROR_CFLAGS)
+gpgscm_CFLAGS = -imacros scheme-config.h
 gpgscm_SOURCES = main.c private.h ffi.c ffi.h ffi-private.h \
 	scheme-config.h scheme.c scheme.h scheme-private.h \
 	opdefines.h small-integers.h
-gpgscm_LDADD = $(LDADD) $(common_libs) \
-	$(NETLIBS) $(LIBICONV) $(LIBREADLINE) $(LIBINTL) \
-	$(LIBGCRYPT_LIBS) $(GPG_ERROR_LIBS)
+gpgscm_LDADD = $(LDADD) $(LIBREADLINE) ../src/libgpg-error.la $(LTLIBINTL)
 
 t_child_SOURCES = t-child.c
 
 # Make sure that all libs are build before we use them.  This is
-# important for things like make -j2.
-$(PROGRAMS): $(common_libs)
+# important for parallel builds (i.e. make -j2).
+$(PROGRAMS): ../src/libgpg-error.la
 
 check-local: gpgscm$(EXEEXT) t-child$(EXEEXT)
 	EXEEXT=$(EXEEXT) GPGSCM_PATH=$(srcdir) \
diff --git a/gpgscm/ffi-private.h b/gpgscm/ffi-private.h
index 5d82127..42627ea 100644
--- a/gpgscm/ffi-private.h
+++ b/gpgscm/ffi-private.h
@@ -20,7 +20,7 @@
 #ifndef GPGSCM_FFI_PRIVATE_H
 #define GPGSCM_FFI_PRIVATE_H
 
-#include <gpg-error.h>
+#include "../src/gpgrt.h"
 #include "scheme.h"
 #include "scheme-private.h"
 
diff --git a/gpgscm/ffi.c b/gpgscm/ffi.c
index 5c8ff45..51de63f 100644
--- a/gpgscm/ffi.c
+++ b/gpgscm/ffi.c
@@ -24,7 +24,6 @@
 #include <dirent.h>
 #include <errno.h>
 #include <fcntl.h>
-#include <gpg-error.h>
 #include <limits.h>
 #include <stdarg.h>
 #include <stdlib.h>
@@ -40,9 +39,9 @@
 #include <readline/history.h>
 #endif
 
-#include "../../common/util.h"
-#include "../../common/exechelp.h"
-#include "../../common/sysutils.h"
+/* #include "../../common/util.h" */
+/* #include "../../common/exechelp.h" */
+/* #include "../../common/sysutils.h" */
 
 #include "private.h"
 #include "ffi.h"
@@ -236,7 +235,7 @@ do_getenv (scheme *sc, pointer args)
   char *value;
   FFI_ARG_OR_RETURN (sc, char *, name, string, args);
   FFI_ARGS_DONE_OR_RETURN (sc, args);
-  value = getenv (name);
+  value = gpgrt_getenv (name);
   FFI_RETURN_STRING (sc, value ? value : "");
 }
 
@@ -251,7 +250,7 @@ do_setenv (scheme *sc, pointer args)
   FFI_ARG_OR_RETURN (sc, char *, value, string, args);
   FFI_ARG_OR_RETURN (sc, int, overwrite, bool, args);
   FFI_ARGS_DONE_OR_RETURN (sc, args);
-  if (gnupg_setenv (name, value, overwrite))
+  if (gpgrt_setenv (name, value, overwrite))
     FFI_RETURN_ERR (sc, gpg_error_from_syserror ());
   FFI_RETURN (sc);
 }
@@ -376,7 +375,7 @@ do_mkdtemp (scheme *sc, pointer args)
     FFI_RETURN_ERR (sc, EINVAL);
   strncpy (buffer, template, sizeof buffer);
 
-  name = gnupg_mkdtemp (buffer);
+  name = NULL; /*gnupg_mkdtemp (buffer);*/
   if (name == NULL)
     FFI_RETURN_ERR (sc, gpg_error_from_syserror ());
   FFI_RETURN_STRING (sc, name);
@@ -420,8 +419,8 @@ unlink_recursively (const char *name)
               || strcmp (dent->d_name, "..") == 0)
             continue;
 
-          child = xtryasprintf ("%s/%s", name, dent->d_name);
-          if (child == NULL)
+          child = gpgrt_bsprintf ("%s/%s", name, dent->d_name);
+          if (!child)
             {
               err = gpg_error_from_syserror ();
               goto leave;
@@ -479,7 +478,7 @@ do_getcwd (scheme *sc, pointer args)
   pointer result;
   char *cwd;
   FFI_ARGS_DONE_OR_RETURN (sc, args);
-  cwd = gnupg_getcwd ();
+  cwd = gpgrt_getcwd ();
   if (cwd == NULL)
     FFI_RETURN_ERR (sc, gpg_error_from_syserror ());
   result = sc->vptr->mk_string (sc, cwd);
@@ -496,7 +495,7 @@ do_mkdir (scheme *sc, pointer args)
   FFI_ARG_OR_RETURN (sc, char *, name, string, args);
   FFI_ARG_OR_RETURN (sc, char *, mode, string, args);
   FFI_ARGS_DONE_OR_RETURN (sc, args);
-  if (gnupg_mkdir (name, mode) == -1)
+  if (gpgrt_mkdir (name, mode) == -1)
     FFI_RETURN_ERR (sc, gpg_error_from_syserror ());
   FFI_RETURN (sc);
 }
@@ -517,9 +516,10 @@ static pointer
 do_get_isotime (scheme *sc, pointer args)
 {
   FFI_PROLOG ();
-  gnupg_isotime_t timebuf;
+  /* gnupg_isotime_t timebuf; */
+  char timebuf[15];
   FFI_ARGS_DONE_OR_RETURN (sc, args);
-  gnupg_get_isotime (timebuf);
+  *timebuf = 0; /*gnupg_get_isotime (timebuf);*/
   FFI_RETURN_STRING (sc, timebuf);
 }
 
@@ -527,8 +527,12 @@ static pointer
 do_get_time (scheme *sc, pointer args)
 {
   FFI_PROLOG ();
+  time_t current;
   FFI_ARGS_DONE_OR_RETURN (sc, args);
-  FFI_RETURN_INT (sc, gnupg_get_time ());
+  current = time (NULL);
+  if (current == (time_t)(-1))
+    gpgrt_log_fatal ("time() failed\n");
+  FFI_RETURN_INT (sc, current);
 }
 
 static pointer
diff --git a/gpgscm/ffi.h b/gpgscm/ffi.h
index a7986e6..3ddf68b 100644
--- a/gpgscm/ffi.h
+++ b/gpgscm/ffi.h
@@ -20,7 +20,7 @@
 #ifndef GPGSCM_FFI_H
 #define GPGSCM_FFI_H
 
-#include <gpg-error.h>
+#include "../src/gpgrt.h"
 #include "scheme.h"
 
 gpg_error_t ffi_init (scheme *sc, const char *argv0, const char *scriptname,
diff --git a/gpgscm/main.c b/gpgscm/main.c
index a4963e2..22c7c98 100644
--- a/gpgscm/main.c
+++ b/gpgscm/main.c
@@ -23,8 +23,6 @@
 #include <ctype.h>
 #include <errno.h>
 #include <fcntl.h>
-#include <gcrypt.h>
-#include <gpg-error.h>
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
@@ -36,17 +34,12 @@
 #include <sys/mman.h>
 #endif
 
+
 #include "private.h"
 #include "scheme.h"
 #include "scheme-private.h"
 #include "ffi.h"
-#include "../common/i18n.h"
-#include "../../common/argparse.h"
-#include "../../common/init.h"
-#include "../../common/logging.h"
-#include "../../common/strlist.h"
-#include "../../common/sysutils.h"
-#include "../../common/util.h"
+
 
 /* The TinyScheme banner.  Unfortunately, it isn't in the header
    file.  */
@@ -64,35 +57,35 @@ enum cmd_and_opt_values
   };
 
 /* The list of commands and options. */
-static ARGPARSE_OPTS opts[] =
-  {
-    ARGPARSE_s_n (oVerbose, "verbose", N_("verbose")),
-    ARGPARSE_end (),
-  };
+/* static ARGPARSE_OPTS opts[] = */
+/*   { */
+/*     ARGPARSE_s_n (oVerbose, "verbose", N_("verbose")), */
+/*     ARGPARSE_end (), */
+/*   }; */
 
 char *scmpath = "";
 size_t scmpath_len = 0;
 
 /* Command line parsing.  */
-static void
-parse_arguments (ARGPARSE_ARGS *pargs, ARGPARSE_OPTS *popts)
-{
-  int no_more_options = 0;
-
-  while (!no_more_options && optfile_parse (NULL, NULL, NULL, pargs, popts))
-    {
-      switch (pargs->r_opt)
-        {
-        case oVerbose:
-          verbose++;
-          break;
-
-        default:
-	  pargs->err = 2;
-	  break;
-	}
-    }
-}
+/* static void */
+/* parse_arguments (ARGPARSE_ARGS *pargs, ARGPARSE_OPTS *popts) */
+/* { */
+  /* int no_more_options = 0; */
+
+  /* while (!no_more_options && optfile_parse (NULL, NULL, NULL, pargs, popts)) */
+  /*   { */
+  /*     switch (pargs->r_opt) */
+  /*       { */
+  /*       case oVerbose: */
+  /*         verbose++; */
+  /*         break; */
+
+  /*       default: */
+  /*         pargs->err = 2; */
+  /*         break; */
+  /*       } */
+  /*   } */
+/* } */
 
 /* Print usage information and provide strings for help. */
 static const char *
@@ -102,19 +95,18 @@ my_strusage( int level )
 
   switch (level)
     {
-    case 11: p = "gpgscm (@GNUPG@)";
+    case 11: p = "gpgscm";
       break;
     case 13: p = VERSION; break;
-    case 17: p = PRINTABLE_OS_NAME; break;
-    case 19: p = _("Please report bugs to <@EMAIL@>.\n"); break;
+    case 19: p = "Please report bugs to <@EMAIL@>.\n"; break;
 
     case 1:
     case 40:
-      p = _("Usage: gpgscm [options] [file] (-h for help)");
+      p = "Usage: gpgscm [options] [file] (-h for help)";
       break;
     case 41:
-      p = _("Syntax: gpgscm [options] [file]\n"
-            "Execute the given Scheme program, or spawn interactive shell.\n");
+      p = "Syntax: gpgscm [options] [file]\n"
+          "Execute the given Scheme program, or spawn interactive shell.\n";
       break;
 
     default: p = NULL; break;
@@ -251,7 +243,7 @@ main (int argc, char **argv)
   int retcode;
   gpg_error_t err;
   char *argv0;
-  ARGPARSE_ARGS pargs;
+  /* ARGPARSE_ARGS pargs; */
   scheme *sc;
   char *p;
 #if _WIN32
@@ -264,6 +256,13 @@ main (int argc, char **argv)
   /* Save argv[0] so that we can re-exec.  */
   argv0 = argv[0];
 
+  if (!gpgrt_check_version (PACKAGE_VERSION))
+    {
+      fprintf (stderr, _("%s is too old (need %s, have %s)\n"), "libgpg-error",
+               PACKAGE_VERSION, gpgrt_check_version (NULL));
+      exit (2);
+    }
+
   /* Parse path.  */
   if (getenv ("GPGSCM_PATH"))
     scmpath = getenv ("GPGSCM_PATH");
@@ -278,33 +277,28 @@ main (int argc, char **argv)
     if (*p == pathsep)
       *p = 0, scmpath_len++;
 
-  set_strusage (my_strusage);
-  log_set_prefix ("gpgscm", GPGRT_LOG_WITH_PREFIX);
+  /* set_strusage (my_strusage); */
+  gpgrt_log_set_prefix ("gpgscm", GPGRT_LOG_WITH_PREFIX);
 
   /* Make sure that our subsystems are ready.  */
-  i18n_init ();
-  init_common_subsystems (&argc, &argv);
-
-  if (!gcry_check_version (NEED_LIBGCRYPT_VERSION))
-    {
-      fputs ("libgcrypt version mismatch\n", stderr);
-      exit (2);
-    }
+  /* i18n_init (); */
+  /* init_common_subsystems (&argc, &argv); */
 
   /* Parse the command line. */
-  pargs.argc  = &argc;
-  pargs.argv  = &argv;
-  pargs.flags = 0;
-  parse_arguments (&pargs, opts);
+  /* pargs.argc  = &argc; */
+  /* pargs.argv  = &argv; */
+  /* pargs.flags = 0; */
+  /* parse_arguments (&pargs, opts); */
 
-  if (log_get_errorcount (0))
+  if (gpgrt_get_errorcount (0))
     exit (2);
 
-  sc = scheme_init_new_custom_alloc (gcry_malloc, gcry_free);
-  if (! sc) {
-    fprintf (stderr, "Could not initialize TinyScheme!\n");
-    return 2;
-  }
+  sc = scheme_init_new_custom_alloc (gpgrt_malloc, gpgrt_free);
+  if (!sc)
+    {
+      fprintf (stderr, "Could not initialize TinyScheme!\n");
+      return 2;
+    }
   scheme_set_input_port_file (sc, stdin);
   scheme_set_output_port_file (sc, stderr);
 
@@ -347,7 +341,7 @@ main (int argc, char **argv)
     {
       err = load (sc, script, 1, 1);
       if (err)
-        log_fatal ("%s: %s", script, gpg_strerror (err));
+        gpgrt_log_fatal ("%s: %s", script, gpg_strerror (err));
     }
 
   retcode = sc->retcode;
diff --git a/gpgscm/private.h b/gpgscm/private.h
index 5685314..93547ce 100644
--- a/gpgscm/private.h
+++ b/gpgscm/private.h
@@ -20,6 +20,54 @@
 #ifndef GPGSCM_PRIVATE_H
 #define GPGSCM_PRIVATE_H
 
+
+#include "../src/gpgrt.h"
+
+/*
+ * Internal i18n macros.
+ */
+#ifdef ENABLE_NLS
+# ifdef HAVE_W32_SYSTEM
+#  include "gettext.h"
+# else
+#  include <libintl.h>
+# endif
+# define _(a) gettext (a)
+# ifdef gettext_noop
+#  define N_(a) gettext_noop (a)
+# else
+#  define N_(a) (a)
+# endif
+#else  /*!ENABLE_NLS*/
+# define _(a) (a)
+# define N_(a) (a)
+#endif /*!ENABLE_NLS */
+
+#define xfree(a)         gpgrt_free ((a))
+#define xtrymalloc(a)    gpgrt_malloc ((a))
+#define xtrycalloc(a,b)  gpgrt_calloc ((a),(b))
+#define xtryrealloc(a,b) gpgrt_realloc ((a),(b))
+
+
+static GPGRT_INLINE void *
+xmalloc (size_t n)
+{
+  void *p = gpgrt_malloc (n);
+  if (!p)
+    log_fatal ("malloc failed: %s\n", strerror (errno));
+  return p;
+}
+
+static GPGRT_INLINE char *
+xstrdup (const char *s)
+{
+  char *p = gpgrt_malloc (strlen (s) + 1);
+  strcpy (p, s);
+  return p;
+}
+
+
 extern int verbose;
 
+
 #endif /* GPGSCM_PRIVATE_H */

commit 4a2538e69dd35377bce0fb584f72322c69a111b3
Author: Werner Koch <wk at gnupg.org>
Date:   Tue Nov 28 15:39:56 2017 +0100

    core: New API functions gpgrt_mkdir, gpgrt_chdir, gpgrt_getcwd.
    
    * src/gpg-error.h.in (gpgrt_mkdir, gpgrt_chdir, gpgrt_getcwd): New.
    * src/visibility.c, src/visibility.h: Add wrappers.
    * src/gpg-error.vers, src/gpg-error.def.in: Add them.
    * src/sysutils.c (modestr_to_mode): New.
    (_gpgrt_mkdir, _gpgrt_chdir, _gpgrt_getcwd): New.
    * m4/gnupg-misc.m4: New.
    * m4/Makefile.am (EXTRA_DIST): Add new M4 file.
    * configure.ac: Call new GNUPG_FUNC_MKDIR_TAKES_ONE_ARG.
    (AC_CHECK_FUNCS): Add stat.
    --
    
    The code has been taken from GnuPG.  _gpgrt_mkdir was originally
    written by me as gnupg_mkdir and here relicensed to LGPLv2.1+.
    _gpgrt_getcwd was originally written by in 2007 and also here
    relicensed to LGPLv2.1.  The new M4 macro was also written by me for
    use in in GnuPG; it has been taken from GnUPG's acinclude.m4, moved to
    its own file here, and relicensed to FSFULLR.
    
    Signed-off-by: Werner Koch <wk at gnupg.org>

diff --git a/configure.ac b/configure.ac
index 68dbc55..0d2f4b5 100644
--- a/configure.ac
+++ b/configure.ac
@@ -177,7 +177,7 @@ AC_MSG_WARN([[Without strerror_r, gpg_strerror_r might not be thread-safe]]))
      ;;
 esac
 
-AC_CHECK_FUNCS([flockfile vasprintf mmap rand strlwr stpcpy setenv])
+AC_CHECK_FUNCS([flockfile vasprintf mmap rand strlwr stpcpy setenv stat])
 
 
 #
@@ -203,6 +203,9 @@ AC_CHECK_SIZEOF(time_t,,[[
 #endif
 ]])
 
+GNUPG_FUNC_MKDIR_TAKES_ONE_ARG
+
+
 # Find a 64 bit integer type to be used instead of off_t.  We prefer
 # the standard integer types over int64_t and finally try long long.
 if test "$ac_cv_sizeof_int" = "8"; then
@@ -223,7 +226,6 @@ AC_DEFINE_UNQUOTED(REPLACEMENT_FOR_OFF_T, "$replacement_for_off_t",
                    [Used by mkheader to insert the replacement type.])
 
 
-
 #
 # Setup gcc specific options
 #
diff --git a/m4/Makefile.am b/m4/Makefile.am
index f92d115..b7b1963 100644
--- a/m4/Makefile.am
+++ b/m4/Makefile.am
@@ -1,3 +1,3 @@
 EXTRA_DIST = inttypes-h.m4 lock.m4 visibility.m4 glibc2.m4 intmax.m4 longdouble.m4 longlong.m4 printf-posix.m4 signed.m4 size_max.m4 wchar_t.m4 wint_t.m4 xsize.m4 ac_prog_cc_for_build.m4 nls.m4 po.m4  codeset.m4 gettext.m4 glibc21.m4 iconv.m4 intdiv0.m4 inttypes.m4 inttypes_h.m4 inttypes-pri.m4 isc-posix.m4 lcmessage.m4 lib-ld.m4 lib-link.m4 lib-prefix.m4 progtest.m4 stdint_h.m4 uintmax_t.m4 ulonglong.m4
 
-EXTRA_DIST += autobuild.m4 estream.m4 readline.m4
+EXTRA_DIST += autobuild.m4 estream.m4 readline.m4 gnupg-misc.m4
diff --git a/m4/gnupg-misc.m4 b/m4/gnupg-misc.m4
new file mode 100644
index 0000000..12f86d8
--- /dev/null
+++ b/m4/gnupg-misc.m4
@@ -0,0 +1,35 @@
+dnl gnupg-misc.m4 - Autoconf macros originally from GnuPG
+dnl Copyright (C) 2017 g10 Code GmbH
+dnl
+dnl This file is free software; as a special exception the author gives
+dnl unlimited permission to copy and/or distribute it, with or without
+dnl modifications, as long as this notice is preserved.
+dnl
+dnl This file is distributed in the hope that it will be useful, but
+dnl WITHOUT ANY WARRANTY, to the extent permitted by law; without even the
+dnl implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
+dnl SPDX-License-Identifier: FSFULLR
+
+
+dnl Define MKDIR_TAKES_ONE_ARG if mkdir accepts only one argument instead
+dnl of the usual 2.
+AC_DEFUN([GNUPG_FUNC_MKDIR_TAKES_ONE_ARG],
+[AC_CHECK_HEADERS(sys/stat.h unistd.h direct.h)
+AC_CACHE_CHECK([if mkdir takes one argument], gnupg_cv_mkdir_takes_one_arg,
+[AC_TRY_COMPILE([
+#include <sys/types.h>
+#ifdef HAVE_SYS_STAT_H
+# include <sys/stat.h>
+#endif
+#ifdef HAVE_UNISTD_H
+# include <unistd.h>
+#endif
+#ifdef HAVE_DIRECT_H
+# include <direct.h>
+#endif], [mkdir ("foo", 0);],
+        gnupg_cv_mkdir_takes_one_arg=no, gnupg_cv_mkdir_takes_one_arg=yes)])
+if test $gnupg_cv_mkdir_takes_one_arg = yes ; then
+  AC_DEFINE(MKDIR_TAKES_ONE_ARG,1,
+            [Defined if mkdir() does not take permission flags])
+fi
+])
diff --git a/src/gpg-error.def.in b/src/gpg-error.def.in
index 6c40571..64c75dc 100644
--- a/src/gpg-error.def.in
+++ b/src/gpg-error.def.in
@@ -189,11 +189,13 @@ EXPORTS
  gpgrt_strdup                 @144
  gpgrt_strconcat              @145
 
- gpgrt_getenv                 @146
- gpgrt_setenv                 @147
+ gpgrt_w32_reg_query_string   @146
+
+ gpgrt_getenv                 @147
+ gpgrt_setenv                 @148
+ gpgrt_mkdir                  @149
+ gpgrt_chdir                  @150
+ gpgrt_getcwd                 @151
 
-#ifdef HAVE_W32_SYSTEM
- gpgrt_w32_reg_query_string   @148
-#endif
 
 ;; end of file with public symbols for Windows.
diff --git a/src/gpg-error.h.in b/src/gpg-error.h.in
index 3d9c914..dffde2e 100644
--- a/src/gpg-error.h.in
+++ b/src/gpg-error.h.in
@@ -456,6 +456,15 @@ char *gpgrt_getenv (const char *name);
 int gpgrt_setenv (const char *name, const char *value, int overwrite);
 #define gpgrt_unsetenv(n) gpgrt_setenv ((n), NULL, 1)
 
+/* A wrapper around mkdir using a string for the mode.  */
+int gpgrt_mkdir (const char *name, const char *modestr);
+
+/* A simple wrapper around chdir.  */
+int gpgrt_chdir (const char *name);
+
+/* Return the current WD as a malloced string.  */
+char *gpgrt_getcwd (void);
+
 
 
 

diff --git a/src/gpg-error.vers b/src/gpg-error.vers
index 661222c..92184f3 100644
--- a/src/gpg-error.vers
+++ b/src/gpg-error.vers
@@ -165,6 +165,9 @@ GPG_ERROR_1.0 {
 
     gpgrt_getenv;
     gpgrt_setenv;
+    gpgrt_mkdir;
+    gpgrt_chdir;
+    gpgrt_getcwd;
 
   local:
     *;
diff --git a/src/gpgrt-int.h b/src/gpgrt-int.h
index c65f630..b2f87b9 100644
--- a/src/gpgrt-int.h
+++ b/src/gpgrt-int.h
@@ -566,7 +566,14 @@ char *_gpgrt_getenv (const char *name);
  * NULL and OVERRIDE to true.  */
 int _gpgrt_setenv (const char *name, const char *value, int overwrite);
 
+/* A wrapper around mkdir using a string for the mode (permissions).  */
+int _gpgrt_mkdir (const char *name, const char *modestr);
 
+/* A simple wrapper around chdir.  */
+int _gpgrt_chdir (const char *name);
+
+/* Return the current WD as a malloced string.  */
+char *_gpgrt_getcwd (void);
 
 

 /*
diff --git a/src/sysutils.c b/src/sysutils.c
index 2dda4cd..70c2dc3 100644
--- a/src/sysutils.c
+++ b/src/sysutils.c
@@ -27,6 +27,11 @@
 #ifdef HAVE_W32_SYSTEM
 # include <windows.h>
 #endif
+#ifdef HAVE_STAT
+# include <sys/stat.h>
+#endif
+#include <sys/types.h>
+#include <fcntl.h>
 
 #include "gpgrt-int.h"
 
@@ -212,3 +217,114 @@ _gpgrt_setenv (const char *name, const char *value, int overwrite)
 # endif /*!HAVE_SETENV*/
 #endif /*!HAVE_W32_SYSTEM*/
 }
+
+
+#ifndef HAVE_W32_SYSTEM
+static mode_t
+modestr_to_mode (const char *modestr)
+{
+  mode_t mode = 0;
+
+  if (modestr && *modestr)
+    {
+      modestr++;
+      if (*modestr && *modestr++ == 'r')
+        mode |= S_IRUSR;
+      if (*modestr && *modestr++ == 'w')
+        mode |= S_IWUSR;
+      if (*modestr && *modestr++ == 'x')
+        mode |= S_IXUSR;
+      if (*modestr && *modestr++ == 'r')
+        mode |= S_IRGRP;
+      if (*modestr && *modestr++ == 'w')
+        mode |= S_IWGRP;
+      if (*modestr && *modestr++ == 'x')
+        mode |= S_IXGRP;
+      if (*modestr && *modestr++ == 'r')
+        mode |= S_IROTH;
+      if (*modestr && *modestr++ == 'w')
+        mode |= S_IWOTH;
+      if (*modestr && *modestr++ == 'x')
+        mode |= S_IXOTH;
+    }
+
+  return mode;
+}
+#endif
+
+
+/* A wrapper around mkdir which takes a string for the mode argument.
+ * This makes it easier to handle the mode argument which is not
+ * defined on all systems.  The format of the modestring is
+ *
+ *    "-rwxrwxrwx"
+ *
+ * '-' is a don't care or not set.  'r', 'w', 'x' are read allowed,
+ * write allowed, execution allowed with the first group for the user,
+ * the second for the group and the third for all others.  If the
+ * string is shorter than above the missing mode characters are meant
+ * to be not set.  */
+int
+_gpgrt_mkdir (const char *name, const char *modestr)
+{
+#ifdef HAVE_W32CE_SYSTEM
+  wchar_t *wname;
+  (void)modestr;
+
+  wname = utf8_to_wchar (name);
+  if (!wname)
+    return -1;
+  if (!CreateDirectoryW (wname, NULL))
+    {
+      xfree (wname);
+      return -1;  /* ERRNO is automagically provided by gpg-error.h.  */
+    }
+  xfree (wname);
+  return 0;
+#elif MKDIR_TAKES_ONE_ARG
+  (void)modestr;
+  /* Note: In the case of W32 we better use CreateDirectory and try to
+     set appropriate permissions.  However using mkdir is easier
+     because this sets ERRNO.  */
+  return mkdir (name);
+#else
+  return mkdir (name, modestr_to_mode (modestr));
+#endif
+}
+
+
+/* A simple wrapper around chdir.  NAME is expected to be utf8
+ * encoded.  */
+int
+_gpgrt_chdir (const char *name)
+{
+  return chdir (name);
+}
+
+
+/* Return the current working directory as a malloced string.  Return
+ * NULL and sets ERRNO on error.  */
+char *
+_gpgrt_getcwd (void)
+{
+  char *buffer;
+  size_t size = 100;
+
+  for (;;)
+    {
+      buffer = xtrymalloc (size+1);
+      if (!buffer)
+        return NULL;
+#ifdef HAVE_W32CE_SYSTEM
+      strcpy (buffer, "/");  /* Always "/".  */
+      return buffer;
+#else
+      if (getcwd (buffer, size) == buffer)
+        return buffer;
+      xfree (buffer);
+      if (errno != ERANGE)
+        return NULL;
+      size *= 2;
+#endif
+    }
+}
diff --git a/src/visibility.c b/src/visibility.c
index 45ac644..c0cab3d 100644
--- a/src/visibility.c
+++ b/src/visibility.c
@@ -504,66 +504,6 @@ gpgrt_read_line (estream_t stream,
                            max_length);
 }
 
-void *
-gpgrt_realloc (void *a, size_t n)
-{
-  return _gpgrt_realloc (a, n);
-}
-
-void *
-gpgrt_malloc (size_t n)
-{
-  return _gpgrt_malloc (n);
-}
-
-void *
-gpgrt_calloc (size_t n, size_t m)
-{
-  return _gpgrt_calloc (n, m);
-}
-
-char *
-gpgrt_strdup (const char *string)
-{
-  return _gpgrt_strdup (string);
-}
-
-char *
-gpgrt_strconcat (const char *s1, ...)
-{
-  va_list arg_ptr;
-  char *result;
-
-  if (!s1)
-    result = _gpgrt_strdup ("");
-  else
-    {
-      va_start (arg_ptr, s1);
-      result = _gpgrt_strconcat_core (s1, arg_ptr);
-      va_end (arg_ptr);
-    }
-  return result;
-}
-
-void
-gpgrt_free (void *a)
-{
-  if (a)
-    _gpgrt_free (a);
-}
-
-char *
-gpgrt_getenv (const char *name)
-{
-  return _gpgrt_getenv (name);
-}
-
-int
-gpgrt_setenv (const char *name, const char *value, int overwrite)
-{
-  return _gpgrt_setenv (name, value, overwrite);
-}
-
 int
 gpgrt_vfprintf (estream_t _GPGRT__RESTRICT stream,
                 const char *_GPGRT__RESTRICT format,
@@ -769,6 +709,85 @@ gpgrt_vsnprintf (char *buf, size_t bufsize,
 
 
 

+void *
+gpgrt_realloc (void *a, size_t n)
+{
+  return _gpgrt_realloc (a, n);
+}
+
+void *
+gpgrt_malloc (size_t n)
+{
+  return _gpgrt_malloc (n);
+}
+
+void *
+gpgrt_calloc (size_t n, size_t m)
+{
+  return _gpgrt_calloc (n, m);
+}
+
+char *
+gpgrt_strdup (const char *string)
+{
+  return _gpgrt_strdup (string);
+}
+
+char *
+gpgrt_strconcat (const char *s1, ...)
+{
+  va_list arg_ptr;
+  char *result;
+
+  if (!s1)
+    result = _gpgrt_strdup ("");
+  else
+    {
+      va_start (arg_ptr, s1);
+      result = _gpgrt_strconcat_core (s1, arg_ptr);
+      va_end (arg_ptr);
+    }
+  return result;
+}
+
+void
+gpgrt_free (void *a)
+{
+  if (a)
+    _gpgrt_free (a);
+}
+
+char *
+gpgrt_getenv (const char *name)
+{
+  return _gpgrt_getenv (name);
+}
+
+int
+gpgrt_setenv (const char *name, const char *value, int overwrite)
+{
+  return _gpgrt_setenv (name, value, overwrite);
+}
+
+int
+gpgrt_mkdir (const char *name, const char *modestr)
+{
+  return _gpgrt_mkdir (name, modestr);
+}
+
+int
+gpgrt_chdir (const char *name)
+{
+  return _gpgrt_chdir (name);
+}
+
+char *gpgrt_getcwd (void)
+{
+  return _gpgrt_getcwd ();
+}
+
+
+

 gpgrt_b64state_t
 gpgrt_b64dec_start (const char *title)
 {
@@ -990,6 +1009,8 @@ _gpgrt_log_assert (const char *expr, const char *file,
 
 
 
+
+
 

 /* For consistency reasons we use function wrappers also for Windows
  * specific function despite that they are technically not needed.  */
diff --git a/src/visibility.h b/src/visibility.h
index 3c2d6be..3209c23 100644
--- a/src/visibility.h
+++ b/src/visibility.h
@@ -118,14 +118,6 @@ MARK_VISIBLE (gpgrt_fputs)
 MARK_VISIBLE (gpgrt_fputs_unlocked)
 MARK_VISIBLE (gpgrt_getline)
 MARK_VISIBLE (gpgrt_read_line)
-MARK_VISIBLE (gpgrt_realloc)
-MARK_VISIBLE (gpgrt_malloc)
-MARK_VISIBLE (gpgrt_calloc)
-MARK_VISIBLE (gpgrt_strdup)
-MARK_VISIBLE (gpgrt_strconcat)
-MARK_VISIBLE (gpgrt_free)
-MARK_VISIBLE (gpgrt_getenv)
-MARK_VISIBLE (gpgrt_setenv)
 MARK_VISIBLE (gpgrt_fprintf)
 MARK_VISIBLE (gpgrt_fprintf_unlocked)
 MARK_VISIBLE (gpgrt_printf)
@@ -149,10 +141,23 @@ MARK_VISIBLE (gpgrt_bsprintf)
 MARK_VISIBLE (gpgrt_vbsprintf)
 MARK_VISIBLE (gpgrt_snprintf)
 MARK_VISIBLE (gpgrt_vsnprintf)
+
 MARK_VISIBLE (gpgrt_set_syscall_clamp)
 MARK_VISIBLE (gpgrt_get_syscall_clamp)
 MARK_VISIBLE (gpgrt_set_alloc_func)
 
+MARK_VISIBLE (gpgrt_realloc)
+MARK_VISIBLE (gpgrt_malloc)
+MARK_VISIBLE (gpgrt_calloc)
+MARK_VISIBLE (gpgrt_strdup)
+MARK_VISIBLE (gpgrt_strconcat)
+MARK_VISIBLE (gpgrt_free)
+MARK_VISIBLE (gpgrt_getenv)
+MARK_VISIBLE (gpgrt_setenv)
+MARK_VISIBLE (gpgrt_mkdir)
+MARK_VISIBLE (gpgrt_chdir)
+MARK_VISIBLE (gpgrt_getcwd)
+
 MARK_VISIBLE (gpgrt_b64dec_start)
 MARK_VISIBLE (gpgrt_b64dec_proc)
 MARK_VISIBLE (gpgrt_b64dec_finish)
@@ -264,14 +269,6 @@ MARK_VISIBLE (_gpgrt_log_assert)
 #define gpgrt_fputs_unlocked        _gpgrt_USE_UNDERSCORED_FUNCTION
 #define gpgrt_getline               _gpgrt_USE_UNDERSCORED_FUNCTION
 #define gpgrt_read_line             _gpgrt_USE_UNDERSCORED_FUNCTION
-#define gpgrt_realloc               _gpgrt_USE_UNDERSCORED_FUNCTION
-#define gpgrt_malloc                _gpgrt_USE_UNDERSCORED_FUNCTION
-#define gpgrt_calloc                _gpgrt_USE_UNDERSCORED_FUNCTION
-#define gpgrt_strdup                _gpgrt_USE_UNDERSCORED_FUNCTION
-#define gpgrt_strconcat             _gpgrt_USE_UNDERSCORED_FUNCTION
-#define gpgrt_free                  _gpgrt_USE_UNDERSCORED_FUNCTION
-#define gpgrt_getenv                _gpgrt_USE_UNDERSCORED_FUNCTION
-#define gpgrt_setenv                _gpgrt_USE_UNDERSCORED_FUNCTION
 #define gpgrt_fprintf               _gpgrt_USE_UNDERSCORED_FUNCTION
 #define gpgrt_fprintf_unlocked      _gpgrt_USE_UNDERSCORED_FUNCTION
 #define gpgrt_printf                _gpgrt_USE_UNDERSCORED_FUNCTION
@@ -296,6 +293,18 @@ MARK_VISIBLE (_gpgrt_log_assert)
 #define gpgrt_snprintf              _gpgrt_USE_UNDERSCORED_FUNCTION
 #define gpgrt_vsnprintf             _gpgrt_USE_UNDERSCORED_FUNCTION
 
+#define gpgrt_realloc               _gpgrt_USE_UNDERSCORED_FUNCTION
+#define gpgrt_malloc                _gpgrt_USE_UNDERSCORED_FUNCTION
+#define gpgrt_calloc                _gpgrt_USE_UNDERSCORED_FUNCTION
+#define gpgrt_strdup                _gpgrt_USE_UNDERSCORED_FUNCTION
+#define gpgrt_strconcat             _gpgrt_USE_UNDERSCORED_FUNCTION
+#define gpgrt_free                  _gpgrt_USE_UNDERSCORED_FUNCTION
+#define gpgrt_getenv                _gpgrt_USE_UNDERSCORED_FUNCTION
+#define gpgrt_setenv                _gpgrt_USE_UNDERSCORED_FUNCTION
+#define gpgrt_mkdir                 _gpgrt_USE_UNDERSCORED_FUNCTION
+#define gpgrt_chdir                 _gpgrt_USE_UNDERSCORED_FUNCTION
+#define gpgrt_getcwd                _gpgrt_USE_UNDERSCORED_FUNCTION
+
 #define gpgrt_set_syscall_clamp     _gpgrt_USE_UNDERSCORED_FUNCTION
 #define gpgrt_get_syscall_clamp     _gpgrt_USE_UNDERSCORED_FUNCTION
 #define gpgrt_set_alloc_func        _gpgrt_USE_UNDERSCORED_FUNCTION

commit 241e9a73891fcd12f124aab1a299c2cf4f8eebc4
Author: Werner Koch <wk at gnupg.org>
Date:   Tue Nov 28 12:54:13 2017 +0100

    core: Prepare to build with gpgscm.
    
    * configure.ac: New option --enable-gpgscm.  Create gpgscm/Makefile.
    (GPGRT_ENABLE_LOG_MACROS): Define.
    * Makefile.am (SUBDIRS): Add gpgscm
    * src/logging.c (_gpgrt_logv_clock): Do not use the log_debug macro.
    --
    
    Note that gpscm does not yet build.
    
    Signed-off-by: Werner Koch <wk at gnupg.org>

diff --git a/Makefile.am b/Makefile.am
index f5d0b81..856f44c 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -27,12 +27,19 @@ EXTRA_DIST = autogen.sh autogen.rc libgpg-error.spec.in 		\
 	     po/ChangeLog-2011 m4/ChangeLog-2011 contrib/ChangeLog-2011 \
              build-aux/git-log-footer  build-aux/git-log-fix
 
+
 if LANGUAGES_SOME
 lang_subdirs = lang
 else
 lang_subdirs =
 endif
 
+if BUILD_GPGSCM
+doc = gpgscm
+else
+doc =
+endif
+
 if BUILD_DOC
 doc = doc
 else
@@ -45,7 +52,7 @@ else
 tests =
 endif
 
-SUBDIRS = m4 src $(doc) $(tests) po $(lang_subdirs)
+SUBDIRS = m4 src $(gpgscm) $(doc) $(tests) po $(lang_subdirs)
 
 
 dist-hook: gen-ChangeLog
diff --git a/configure.ac b/configure.ac
index 9f3ea82..68dbc55 100644
--- a/configure.ac
+++ b/configure.ac
@@ -154,6 +154,7 @@ AH_BOTTOM([
 #define GPG_ERR_ENABLE_GETTEXT_MACROS 1
 #define GPG_ERR_ENABLE_ERRNO_MACROS 1
 #define GPGRT_ENABLE_ES_MACROS 1
+#define GPGRT_ENABLE_LOG_MACROS 1
 ])
 
 
@@ -531,6 +532,19 @@ if test "$enable_log_clock" = yes ; then
   AC_DEFINE(ENABLE_LOG_CLOCK,1,[Defined to use log_clock timestamps])
 fi
 
+#
+# For now we do not build gpgscm by default.
+# Eventually we will reverse the meaning of that option.
+#
+build_gpgscm=no
+AC_MSG_CHECKING([whether to build gpgscm])
+AC_ARG_ENABLE(gpgscm,
+              AC_HELP_STRING([--enable-gpgscm],
+                             [build the gpgscm tool]),
+              build_gpgscm=$enableval, build_gpgscm=no)
+AC_MSG_RESULT($build_gpgscm)
+AM_CONDITIONAL([BUILD_GPGSCM], [test "x$build_gpgscm" != xno])
+
 
 #
 # Add -Werror to CFLAGS.  This hack can be used to avoid problems with
@@ -597,7 +611,7 @@ AM_CONDITIONAL([BUILD_TESTS], [test "x$build_tests" != xno])
 #
 AC_CONFIG_FILES([Makefile])
 AC_CONFIG_FILES([doc/Makefile po/Makefile.in m4/Makefile])
-AC_CONFIG_FILES([src/Makefile tests/Makefile])
+AC_CONFIG_FILES([src/Makefile gpgscm/Makefile tests/Makefile])
 AC_CONFIG_FILES([lang/Makefile lang/cl/Makefile lang/cl/gpg-error.asd])
 AC_CONFIG_FILES([src/versioninfo.rc src/gpg-error.w32-manifest])
 AC_CONFIG_FILES([src/gpg-error-config], [chmod +x src/gpg-error-config])
diff --git a/src/logging.c b/src/logging.c
index 13873eb..70c13ba 100644
--- a/src/logging.c
+++ b/src/logging.c
@@ -1165,7 +1165,7 @@ _gpgrt_logv_clock (const char *fmt, va_list arg_ptr)
 
   if (clock_gettime (CLOCK_REALTIME, &tv))
     {
-      log_debug ("error getting the realtime clock value\n");
+      _gpgrt_log_debug ("error getting the realtime clock value\n");
       return;
     }
   now = tv.tv_sec * 1000000000ull;

commit b67daca506991507cea9d383df7faf95117e58a6
Author: Werner Koch <wk at gnupg.org>
Date:   Tue Nov 28 12:34:12 2017 +0100

    core: New API functions gpgrt_getenv and gpgrt_setenv.
    
    * src/gpg-error.h.in (gpgrt_getenv, gpgrt_setenv): New.
    (gpgrt_unsetenv): New macro.
    * src/gpg-error.vers, src/gpg-error.def.in: Add them.
    * src/visibility.c (gpgrt_getenv, gpgrt_setenv): New.
    * src/visibility.h: Add them.
    * src/sysutils.c: Include string.h and on Windows windows.h.
    (_gpgrt_getenv): New.
    (_gpgrt_setenv): New.
    --
    
    These functions are wrappers to cope with Windows problems.  The code
    is similar to what we have in GnuPG but not identical.
    
    Requires better testing.
    
    Signed-off-by: Werner Koch <wk at gnupg.org>

diff --git a/src/gpg-error.def.in b/src/gpg-error.def.in
index 5c7835f..6c40571 100644
--- a/src/gpg-error.def.in
+++ b/src/gpg-error.def.in
@@ -189,6 +189,9 @@ EXPORTS
  gpgrt_strdup                 @144
  gpgrt_strconcat              @145
 
+ gpgrt_getenv                 @146
+ gpgrt_setenv                 @147
+
 #ifdef HAVE_W32_SYSTEM
  gpgrt_w32_reg_query_string   @148
 #endif
diff --git a/src/gpg-error.h.in b/src/gpg-error.h.in
index 35027d6..3d9c914 100644
--- a/src/gpg-error.h.in
+++ b/src/gpg-error.h.in
@@ -445,6 +445,19 @@ char *gpgrt_strconcat (const char *s1, ...) GPGRT_ATTR_SENTINEL(0);
 void gpgrt_free (void *a);
 
 
+/*
+ * System specific function wrappers.
+ */
+
+/* A getenv replacement which mallocs the returned string.  */
+char *gpgrt_getenv (const char *name);
+
+/* A setenv and a unsetenv replacement.*/
+int gpgrt_setenv (const char *name, const char *value, int overwrite);
+#define gpgrt_unsetenv(n) gpgrt_setenv ((n), NULL, 1)
+
+
+
 

 /*
  * Lock functions.
diff --git a/src/gpg-error.vers b/src/gpg-error.vers
index 074981b..661222c 100644
--- a/src/gpg-error.vers
+++ b/src/gpg-error.vers
@@ -163,6 +163,9 @@ GPG_ERROR_1.0 {
     gpgrt_strdup;
     gpgrt_strconcat;
 
+    gpgrt_getenv;
+    gpgrt_setenv;
+
   local:
     *;
 };
diff --git a/src/gpgrt-int.h b/src/gpgrt-int.h
index c0e83b1..c65f630 100644
--- a/src/gpgrt-int.h
+++ b/src/gpgrt-int.h
@@ -559,6 +559,14 @@ int _gpgrt_logv_internal (int level, int ignore_arg_ptr,
 /* Return true if FD is valid.  */
 int _gpgrt_fd_valid_p (int fd);
 
+/* A getenv variant which returns a malloced copy.  */
+char *_gpgrt_getenv (const char *name);
+
+/* A setenv variant which can be used for unsetenv by setting VALUE to
+ * NULL and OVERRIDE to true.  */
+int _gpgrt_setenv (const char *name, const char *value, int overwrite);
+
+
 
 

 /*
diff --git a/src/sysutils.c b/src/sysutils.c
index 1933506..2dda4cd 100644
--- a/src/sysutils.c
+++ b/src/sysutils.c
@@ -21,7 +21,12 @@
 #include <config.h>
 #include <stdlib.h>
 #include <stdint.h>
+#include <string.h>
 #include <unistd.h>
+#include <errno.h>
+#ifdef HAVE_W32_SYSTEM
+# include <windows.h>
+#endif
 
 #include "gpgrt-int.h"
 
@@ -37,3 +42,173 @@ _gpgrt_fd_valid_p (int fd)
   close (d);
   return 1;
 }
+
+
+/* Our variant of getenv.  The returned string must be freed.  If the
+ * environment variable does not exists NULL is retruned and ERRNO set
+ * to 0.  */
+char *
+_gpgrt_getenv (const char *name)
+{
+  if (!name || !*name || strchr (name, '='))
+    {
+      _gpg_err_set_errno (EINVAL);
+      return NULL;
+    }
+
+#ifdef HAVE_W32_SYSTEM
+  {
+    int len, size;
+    char *result;
+
+    len = GetEnvironmentVariable (name, NULL, 0);
+    if (!len && GetLastError () == ERROR_ENVVAR_NOT_FOUND)
+      {
+        _gpg_err_set_errno (0);
+        return NULL;
+      }
+  again:
+    size = len;
+    result = _gpgrt_malloc (size);
+    if (!result)
+      return NULL;
+    len = GetEnvironmentVariable (name, result, size);
+    if (len >= size)
+      {
+        /* Changed in the meantime - retry.  */
+        _gpgrt_free (result);
+        goto again;
+      }
+    if (!len && GetLastError () == ERROR_ENVVAR_NOT_FOUND)
+      {
+        /* Deleted in the meantime.  */
+        _gpgrt_free (result);
+        _gpg_err_set_errno (0);
+        return NULL;
+      }
+    if (!len)
+      {
+        /* Other error.  FIXME: We need mapping fucntion. */
+        _gpgrt_free (result);
+        _gpg_err_set_errno (EIO);
+        return NULL;
+      }
+
+    return result;
+  }
+#else /*!HAVE_W32_SYSTEM*/
+  {
+    const char *s = getenv (name);
+    if (!s)
+      {
+        _gpg_err_set_errno (0);
+        return NULL;
+      }
+    return _gpgrt_strdup (s);
+  }
+#endif /*!HAVE_W32_SYSTEM*/
+}
+
+
+/* Wrapper around setenv so that we can have the same function in
+ * Windows and Unix.  In contrast to the standard setenv passing a
+ * VALUE as NULL and setting OVERWRITE will remove the envvar.  */
+int
+_gpgrt_setenv (const char *name, const char *value, int overwrite)
+{
+  if (!name || !*name || strchr (name, '='))
+    {
+      _gpg_err_set_errno (EINVAL);
+      return -1;
+    }
+
+#ifdef HAVE_W32_SYSTEM
+  /* Windows maintains (at least) two sets of environment variables.
+   * One set can be accessed by GetEnvironmentVariable and
+   * SetEnvironmentVariable.  This set is inherited by the children.
+   * The other set is maintained in the C runtime, and is accessed
+   * using getenv and putenv.  We try to keep them in sync by
+   * modifying both sets.  Note that gpgrt_getenv ignores the libc
+   * values - however, too much existing code still uses getenv.  */
+  {
+    int exists;
+    char tmpbuf[10];
+    char *buf;
+
+    if (!value && overwrite)
+      {
+        if (!SetEnvironmentVariable (name, NULL))
+          {
+            _gpg_err_set_errno (EINVAL);
+            return -1;
+          }
+        if (getenv (name))
+          {
+            /* Ugly: Leaking memory.  */
+            buf = _gpgrt_strdup (name);
+            if (!buf)
+              return -1;
+            return putenv (buf);
+          }
+        return 0;
+      }
+
+    exists = GetEnvironmentVariable (name, tmpbuf, sizeof tmpbuf);
+    if ((! exists || overwrite) && !SetEnvironmentVariable (name, value))
+      {
+        _gpg_err_set_errno (EINVAL); /* (Might also be ENOMEM.) */
+        return -1;
+      }
+    if (overwrite || !getenv (name))
+      {
+        /* Ugly: Leaking memory.  */
+        buf = _gpgrt_strconcat (name, "=", value, NULL);
+        if (!buf)
+          return -1;
+        return putenv (buf);
+      }
+    return 0;
+  }
+
+#else /*!HAVE_W32_SYSTEM*/
+
+# ifdef HAVE_SETENV
+
+  {
+    if (!value && overwrite)
+      return unsetenv (name);
+    else
+      return setenv (name, value, overwrite);
+  }
+
+# else /*!HAVE_SETENV*/
+
+# if __GNUC__
+#   warning no setenv - using putenv but leaking memory.
+# endif
+  {
+    char *buf;
+
+    if (!value && overwrite)
+      {
+        if (getenv (name))
+          {
+            buf = _gpgrt_strdup (name);
+            if (!buf)
+              return -1;
+            return putenv (buf);
+          }
+      }
+    else if (overwrite || !getenv (name))
+      {
+        buf = _gpgrt_strconcat (name, "=", value, NULL);
+        if (!buf)
+          return -1;
+        return putenv (buf);
+      }
+
+    return 0;
+  }
+# endif /*!HAVE_SETENV*/
+#endif /*!HAVE_W32_SYSTEM*/
+}
diff --git a/src/visibility.c b/src/visibility.c
index 01ed2ce..45ac644 100644
--- a/src/visibility.c
+++ b/src/visibility.c
@@ -552,6 +552,18 @@ gpgrt_free (void *a)
     _gpgrt_free (a);
 }
 
+char *
+gpgrt_getenv (const char *name)
+{
+  return _gpgrt_getenv (name);
+}
+
+int
+gpgrt_setenv (const char *name, const char *value, int overwrite)
+{
+  return _gpgrt_setenv (name, value, overwrite);
+}
+
 int
 gpgrt_vfprintf (estream_t _GPGRT__RESTRICT stream,
                 const char *_GPGRT__RESTRICT format,
diff --git a/src/visibility.h b/src/visibility.h
index 416f266..3c2d6be 100644
--- a/src/visibility.h
+++ b/src/visibility.h
@@ -124,6 +124,8 @@ MARK_VISIBLE (gpgrt_calloc)
 MARK_VISIBLE (gpgrt_strdup)
 MARK_VISIBLE (gpgrt_strconcat)
 MARK_VISIBLE (gpgrt_free)
+MARK_VISIBLE (gpgrt_getenv)
+MARK_VISIBLE (gpgrt_setenv)
 MARK_VISIBLE (gpgrt_fprintf)
 MARK_VISIBLE (gpgrt_fprintf_unlocked)
 MARK_VISIBLE (gpgrt_printf)
@@ -268,6 +270,8 @@ MARK_VISIBLE (_gpgrt_log_assert)
 #define gpgrt_strdup                _gpgrt_USE_UNDERSCORED_FUNCTION
 #define gpgrt_strconcat             _gpgrt_USE_UNDERSCORED_FUNCTION
 #define gpgrt_free                  _gpgrt_USE_UNDERSCORED_FUNCTION
+#define gpgrt_getenv                _gpgrt_USE_UNDERSCORED_FUNCTION
+#define gpgrt_setenv                _gpgrt_USE_UNDERSCORED_FUNCTION
 #define gpgrt_fprintf               _gpgrt_USE_UNDERSCORED_FUNCTION
 #define gpgrt_fprintf_unlocked      _gpgrt_USE_UNDERSCORED_FUNCTION
 #define gpgrt_printf                _gpgrt_USE_UNDERSCORED_FUNCTION

-----------------------------------------------------------------------

Summary of changes:
 Makefile.am          |   9 +-
 configure.ac         |  22 +++-
 gpgscm/Makefile.am   |  17 +--
 gpgscm/ffi-private.h |   2 +-
 gpgscm/ffi.c         |  39 ++++---
 gpgscm/ffi.h         |   2 +-
 gpgscm/main.c        | 116 ++++++++++----------
 gpgscm/private.h     |  48 +++++++++
 m4/Makefile.am       |   2 +-
 m4/gnupg-misc.m4     |  35 ++++++
 src/gpg-error.def.in |  11 +-
 src/gpg-error.h.in   |  23 ++++
 src/gpg-error.vers   |   6 ++
 src/gpgrt-int.h      |  16 +++
 src/logging.c        |   2 +-
 src/sysutils.c       | 300 +++++++++++++++++++++++++++++++++++++++++++++++++++
 src/visibility.c     | 130 +++++++++++++---------
 src/visibility.h     |  37 ++++---
 18 files changed, 656 insertions(+), 161 deletions(-)
 create mode 100644 m4/gnupg-misc.m4


hooks/post-receive
-- 
Error codes used by GnuPG et al.
http://git.gnupg.org




More information about the Gnupg-commits mailing list