* gcrypt.h (GCRYCTL_DISABLE_INTERNAL_LOCKING): New.
authorWerner Koch <wk@gnupg.org>
Thu, 2 May 2002 14:07:31 +0000 (14:07 +0000)
committerWerner Koch <wk@gnupg.org>
Thu, 2 May 2002 14:07:31 +0000 (14:07 +0000)
* global.c (gcry_control): Implement it.
(_gcry_no_internal_locking): New.
* mutex.h: Prefixed all fucntions with _gcry_.  Bypass all
functions when desired.

* gcrypt.h (GCRYCTL_DISABLE_SECMEM): New.
* global.c (gcry_control,gcry_malloc_secure,gcry_is_secure):
Implement it here.
* secmem.c (_gcry_private_is_secure): Return false if the pool is
not initialized.

* gcrypt.h (GCRYCTL_INITIALIZATION_FINISHED): New.

* gcrypt.h (gcry_cipher_algos): Replaced RINDAEL by AES and change
the macros to expand from rijdael to aes.

* stdmem.c (_gcry_private_malloc): Return NULL for 0 byte allocation.
(_gcry_private_malloc_secure): Ditto.

* g10lib.h:  Copied the JNLIB_GCC macros from ../jnlib/mischelp.h
and removed the inclusion of that file.

src/ChangeLog
src/Makefile.am
src/g10lib.h
src/gcrypt.h
src/global.c
src/mutex.h [new file with mode: 0644]
src/secmem.c
src/stdmem.c

index 59d46aa..38fb9a7 100644 (file)
@@ -1,3 +1,37 @@
+2002-05-02  Werner Koch  <wk@gnupg.org>
+
+       * gcrypt.h (GCRYCTL_DISABLE_INTERNAL_LOCKING): New.
+       * global.c (gcry_control): Implement it.
+       (_gcry_no_internal_locking): New.
+       * mutex.h: Prefixed all fucntions with _gcry_.  Bypass all
+       functions when desired.
+
+       * gcrypt.h (GCRYCTL_DISABLE_SECMEM): New.
+       * global.c (gcry_control,gcry_malloc_secure,gcry_is_secure):
+       Implement it here.
+       * secmem.c (_gcry_private_is_secure): Return false if the pool is
+       not initialized.
+
+       * gcrypt.h (GCRYCTL_INITIALIZATION_FINISHED): New.
+
+       * gcrypt.h (gcry_cipher_algos): Replaced RINDAEL by AES and change
+       the macros to expand from rijdael to aes.
+
+       * stdmem.c (_gcry_private_malloc): Return NULL for 0 byte allocation.
+       (_gcry_private_malloc_secure): Ditto.
+
+       * g10lib.h:  Copied the JNLIB_GCC macros from ../jnlib/mischelp.h
+       and removed the inclusion of that file.
+
+2002-04-15  Werner Koch  <wk@gnupg.org>
+
+       * global.c (gcry_strdup): New.
+
+2002-03-18  Werner Koch  <wk@gnupg.org>
+
+       * mutex.h: New file with a portable thread mutex implementation
+       written by Marcus Brinkmann.  Taken from GPGME.
+
 2002-02-18  Werner Koch  <wk@gnupg.org>
 
        * sexp.c (gcry_sexp_sscan): Don't initialize the dummy
index 38cd218..71b82d1 100644 (file)
@@ -49,7 +49,8 @@ libgcrypt_la_SOURCES =         g10lib.h \
                         stdmem.h \
                         secmem.c \
                         secmem.h \
-                        mpi.h
+                        mpi.h \
+                        mutex.h 
 
 libgcrypt_la_DEPENDENCIES = libgcrypt.sym \
                            ../cipher/libcipher.la ../mpi/libmpi.la
index 71aaf82..70d61e4 100644 (file)
@@ -1,5 +1,5 @@
 /* g10lib.h -  internal defintions for libgcrypt
- *     Copyright (C) 1998, 1999, 2000, 2001 Free Software Foundation, Inc.
+ * Copyright (C) 1998, 1999, 2000, 2001, 2002 Free Software Foundation, Inc.
  *
  * This header is to be used inside of libgcrypt in place of gcrypt.h.
  * This way we can better distinguish between internal and external
 
 #include <gcrypt.h>
 #include "types.h"
-#include "../jnlib/mischelp.h"
+
+#if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 5 )
+# define JNLIB_GCC_M_FUNCTION 1
+# define JNLIB_GCC_A_NR             __attribute__ ((noreturn))
+# define JNLIB_GCC_A_PRINTF( f, a )  __attribute__ ((format (printf,f,a)))
+# define JNLIB_GCC_A_NR_PRINTF( f, a ) \
+                           __attribute__ ((noreturn, format (printf,f,a)))
+#else
+# define JNLIB_GCC_A_NR
+# define JNLIB_GCC_A_PRINTF( f, a )
+# define JNLIB_GCC_A_NR_PRINTF( f, a )
+#endif
 
 #ifdef G10_I18N_H
   #error i18n should not be included here
index 27116a5..299fa6a 100644 (file)
@@ -132,7 +132,10 @@ enum gcry_ctl_cmds {
     GCRYCTL_START_DUMP         = 32,
     GCRYCTL_STOP_DUMP          = 33,
     GCRYCTL_GET_ALGO_USAGE      = 34,
-    GCRYCTL_IS_ALGO_ENABLED     = 35
+    GCRYCTL_IS_ALGO_ENABLED     = 35,
+    GCRYCTL_DISABLE_INTERNAL_LOCKING = 36,
+    GCRYCTL_DISABLE_SECMEM      = 37,
+    GCRYCTL_INITIALIZATION_FINISHED = 38
 };
 
 int gcry_control( enum gcry_ctl_cmds, ... );
@@ -309,18 +312,19 @@ enum gcry_cipher_algos {
     GCRY_CIPHER_BLOWFISH    = 4,
     GCRY_CIPHER_SAFER_SK128 = 5,
     GCRY_CIPHER_DES_SK     = 6,
-    GCRY_CIPHER_RIJNDAEL    = 7,
-    GCRY_CIPHER_RIJNDAEL192 = 8,
-    GCRY_CIPHER_RIJNDAEL256 = 9,
+    GCRY_CIPHER_AES         = 7,
+    GCRY_CIPHER_AES192      = 8,
+    GCRY_CIPHER_AES256      = 9,
     GCRY_CIPHER_TWOFISH     = 10,
     /* other cipher numbers are above 300 for OpenPGP reasons. */
     GCRY_CIPHER_ARCFOUR     = 301
 };
 
-#define GCRY_CIPHER_AES    GCRY_CIPHER_RIJNDAEL
-#define GCRY_CIPHER_AES128 GCRY_CIPHER_RIJNDAEL
-#define GCRY_CIPHER_AES192 GCRY_CIPHER_RIJNDAEL192
-#define GCRY_CIPHER_AES256 GCRY_CIPHER_RIJNDAEL256
+#define GCRY_CIPHER_AES128      GCRY_CIPHER_AES    
+#define GCRY_CIPHER_RIJNDAEL    GCRY_CIPHER_AES    
+#define GCRY_CIPHER_RIJNDAEL128 GCRY_CIPHER_AES128 
+#define GCRY_CIPHER_RIJNDAEL192 GCRY_CIPHER_AES192 
+#define GCRY_CIPHER_RIJNDAEL256 GCRY_CIPHER_AES256 
 
 enum gcry_cipher_modes {
     GCRY_CIPHER_MODE_NONE   = 0,
@@ -337,7 +341,7 @@ enum gcry_cipher_flags {
 };
 
 
-GCRY_CIPHER_HD gcry_cipher_open( int algo, int mode, unsigned flags);
+GCRY_CIPHER_HD gcry_cipher_open( int algo, int mode, unsigned int flags);
 void gcry_cipher_close( GCRY_CIPHER_HD h );
 int  gcry_cipher_ctl( GCRY_CIPHER_HD h, int cmd, void *buffer, size_t buflen);
 int gcry_cipher_info( GCRY_CIPHER_HD h, int what, void *buffer, size_t *nbytes);
@@ -521,6 +525,7 @@ void *gcry_calloc( size_t n, size_t m );
 void *gcry_malloc_secure( size_t n );
 void *gcry_calloc_secure( size_t n, size_t m );
 void *gcry_realloc( void *a, size_t n );
+char *gcry_strdup( const char *string );
 void *gcry_xmalloc( size_t n );
 void *gcry_xcalloc( size_t n, size_t m );
 void *gcry_xmalloc_secure( size_t n );
index f78b6f7..b4c78b6 100644 (file)
@@ -31,6 +31,7 @@
 #include "stdmem.h" /* our own memory allocator */
 #include "secmem.h" /* our own secmem allocator */
 
+
 /****************
  * flag bits: 0 : general cipher debug
  *           1 : general MPI debug
@@ -45,6 +46,8 @@ static void *(*realloc_func)(void *p, size_t n) = NULL;
 static void (*free_func)(void*) = NULL;
 static int (*outofcore_handler)( void*, size_t, unsigned int ) = NULL;
 static void *outofcore_handler_value = NULL;
+static int no_internal_locking = 0;
+static int no_secure_memory = 0;
 
 static const char*
 parse_version_number( const char *s, int *number )
@@ -151,6 +154,10 @@ gcry_control( enum gcry_ctl_cmds cmd, ... )
        _gcry_secmem_init( 0 );
        break;
 
+      case GCRYCTL_DISABLE_SECMEM:
+        no_secure_memory = 1;
+        break;    
+
       case GCRYCTL_INIT_SECMEM:
        _gcry_secmem_init( va_arg( arg_ptr, unsigned int ) );
        break;
@@ -187,6 +194,19 @@ gcry_control( enum gcry_ctl_cmds cmd, ... )
        debug_flags &= ~va_arg( arg_ptr, unsigned int );
        break;
 
+      case GCRYCTL_DISABLE_INTERNAL_LOCKING:
+        no_internal_locking = 1;
+        break;
+
+      case GCRYCTL_INITIALIZATION_FINISHED:
+        /* This is a hook which should be used by an application after
+           all intialization has been done and right before any
+           threads are started.  It is not really needed but the only
+           way to be really sure that all initialization for
+           thread-safety has been done. */
+        /* fixme: we should initialize the various mutexs here */
+        break;
+
       default:
        va_end(arg_ptr);
        return GCRYERR_INV_OP;
@@ -261,8 +281,7 @@ _gcry_set_lasterr( int ec )
 
 
 /****************
- * NOTE: All 5 functions should be set.
- */
+ * NOTE: All 5 functions should be set.  */
 void
 gcry_set_allocation_handler( void *(*new_alloc_func)(size_t n),
                             void *(*new_alloc_secure_func)(size_t n),
@@ -314,17 +333,21 @@ gcry_malloc( size_t n )
 void *
 gcry_malloc_secure( size_t n )
 {
-    if( alloc_secure_func )
-       return alloc_secure_func( n ) ;
-    return _gcry_private_malloc_secure( n );
+  if (no_secure_memory)
+    return gcry_malloc (n);
+  if (alloc_secure_func)
+    return alloc_secure_func (n) ;
+  return _gcry_private_malloc_secure (n);
 }
 
 int
 gcry_is_secure( const void *a )
 {
-    if( is_secure_func )
-       return is_secure_func( a ) ;
-    return _gcry_private_is_secure( a );
+  if (no_secure_memory)
+    return 0;
+  if (is_secure_func)
+    return is_secure_func (a) ;
+  return _gcry_private_is_secure (a);
 }
 
 void
@@ -380,6 +403,15 @@ gcry_calloc_secure( size_t n, size_t m )
 }
 
 
+char *
+gcry_strdup( const char *string )
+{
+    void *p = gcry_malloc( strlen(string)+1 );
+    strcpy( p, string );
+    return p;
+}
+
+
 void *
 gcry_xmalloc( size_t n )
 {
@@ -454,4 +486,9 @@ _gcry_get_debug_flag( unsigned int mask )
     return debug_flags & mask;
 }
 
+int 
+_gcry_no_internal_locking (void)
+{
+  return no_internal_locking;
+}
 
diff --git a/src/mutex.h b/src/mutex.h
new file mode 100644 (file)
index 0000000..547d311
--- /dev/null
@@ -0,0 +1,143 @@
+/* mutex.h -  Portable mutual exclusion, independent from any thread library.
+ *      Copyright (C) 2002 g10 Code GmbH
+ *     Copyright (C) 2002 Free Software Foundation, Inc.
+ *
+ * This file is part of Libgcrypt.
+ *
+ * Libgcrypt is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * Libgcrypt is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
+ */
+
+#ifndef MUTEX_H
+#define MUTEX_H
+
+/* Define MUTEX_FAKE before including the file to get stubs that don't
+   provide any locking at all.  Define MUTEX_PTHREAD if you can link
+   against the posix thread library.  */
+
+#if defined(MUTEX_FAKE)
+
+typedef char mutex_t;
+#define mutex_init(x) (0)
+#define mutex_destroy(x)
+#define mutex_lock(x) (0)
+#define mutex_unlock(x) (0)
+
+#elif defined(MUTEX_PTHREAD)
+
+#include <pthread.h>
+
+#define mutex_t pthread_mutex_t
+#define mutex_init(x) pthread_mutex_init (&(x), 0)
+#define mutex_destroy(x) pthread_mutex_destroy(&(x))
+#define mutex_lock(x) pthread_mutex_lock (&(x))
+#define mutex_unlock(x) pthread_mutex_unlock (&(x))
+
+#else
+
+int _gcry_no_internal_locking (void);
+
+#include <errno.h>
+#include <fcntl.h>
+#include <unistd.h>
+
+/* The type of a mutex.  */
+typedef int mutex_t[2];
+
+inline static int
+set_close_on_exec (int fd)
+{
+  int flags = fcntl (fd, F_GETFD, 0);
+  if (flags == -1)
+    return errno;
+  flags |= FD_CLOEXEC;
+  if (fcntl (fd, F_SETFD, flags) == -1)
+    return errno;
+  return 0;
+}
+
+/* Initialize the mutex variable MUTEX.  */
+inline int
+_gcry_mutex_init (mutex_t mutex)
+{
+  ssize_t amount;
+  int err = 0;
+
+  if  (_gcry_no_internal_locking())
+    return 0;
+  if (pipe (mutex))
+    return errno;
+
+  err = set_close_on_exec (mutex[0]);
+  if (!err)
+    err = set_close_on_exec (mutex[1]);
+  if (!err)
+    while ((amount = write (mutex[1], " ", 1)) < 0 && errno == EINTR)
+      ;
+  if (!err && amount != 1)
+    err = errno;
+
+  if (err)
+    {
+      close (mutex[0]);
+      close (mutex[1]);
+    }
+  return err;
+}
+
+/* Destroy the mutex variable MUTEX.  */
+inline void
+_gcry_mutex_destroy (mutex_t mutex)
+{
+  if  (_gcry_no_internal_locking ())
+    return;
+  close (mutex[0]);
+  close (mutex[1]);
+}
+
+/* Take the mutex variable MUTEX.  */
+inline int
+_gcry_mutex_lock (mutex_t mutex)
+{
+  char data;
+  int amount;
+  if  (_gcry_no_internal_locking ())
+    return 0;
+
+  while ((amount = read (mutex[0], &data, 1)) < 0 && errno == EINTR)
+    ;
+  return (amount != 1) ? errno : 0;
+}
+
+/* Release the mutex variable MUTEX.  */
+inline int
+_gcry_mutex_unlock (mutex_t mutex)
+{
+  int amount;
+  if  (_gcry_no_internal_locking ())
+    return 0;
+  while ((amount = write (mutex[1], " ", 1)) < 0 && errno == EINTR)
+    ;
+  return (amount != 1) ? errno : 0;
+}
+
+#define mutex_init(x)    _gcry_mutex_init (x)
+#define mutex_destroy(x) _gcry_mutex_destroy(x)
+#define mutex_lock(x)    _gcry_mutex_lock (x)
+#define mutex_unlock(x)  _gcry_mutex_unlock (x)
+
+
+#endif /* MUTEX_FAKE */
+#endif /* MUTEX_H */
+
index 4ef44e5..63ba67e 100644 (file)
@@ -382,7 +382,9 @@ _gcry_secmem_free( void *a )
 int
 _gcry_private_is_secure( const void *p )
 {
-    return p >= pool && p < (void*)((char*)pool+poolsize);
+  if (!pool_okay)
+    return 0;
+  return p >= pool && p < (void*)((char*)pool+poolsize);
 }
 
 
index 1cfe62f..1b22994 100644 (file)
@@ -1,5 +1,5 @@
 /* stdmem.c  - private memory allocator
- *     Copyright (C) 1998, 2000 Free Software Foundation, Inc.
+ *     Copyright (C) 1998, 2000, 2002 Free Software Foundation, Inc.
  *
  * This file is part of Libgcrypt.
  *
@@ -59,6 +59,9 @@ _gcry_private_enable_m_guard(void)
 void *
 _gcry_private_malloc( size_t n)
 {
+    if(!n) 
+      return NULL; /* allocating 0 bytes is undefined - better return
+                      an error */
     if( use_m_guard ) {
        char *p;
 
@@ -83,6 +86,9 @@ _gcry_private_malloc( size_t n)
 void *
 _gcry_private_malloc_secure( size_t n)
 {
+    if(!n) 
+      return NULL; /* allocating 0 bytes is undefined - better return
+                      an error */
     if( use_m_guard ) {
        char *p;