summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorWerner Koch <wk@gnupg.org>2002-05-16 17:11:21 +0000
committerWerner Koch <wk@gnupg.org>2002-05-16 17:11:21 +0000
commit848c32beeb723d8e06499ec119222dae77a3cd8e (patch)
tree1c29feda82dc9927881d6706e8f9338c77e86b2d
parent9e93c817955b8e876227df3c1ae0285f911c138a (diff)
downloadlibgcrypt-848c32beeb723d8e06499ec119222dae77a3cd8e.tar.gz
* tsexp.c (back_and_forth): Very minimal test of the new functions.
* missing-string.c: New. * gcrypt.h: Add new error codes GCRYERR_SEXP_ and typedefs GcryMPI, GcrySexp, GcryCipherHd, GcryMDHd as aliases for the old ones using an underscore. * global.c (gcry_strerror): Add strings fro the new error codes. * sexp.c (gcry_sexp_canon_len): Use a macro to convert from new to old error codes. (gcry_sexp_create,gcry_sexp_new): New.
-rw-r--r--src/ChangeLog13
-rw-r--r--src/Makefile.am3
-rw-r--r--src/g10lib.h21
-rw-r--r--src/gcrypt.h49
-rw-r--r--src/global.c13
-rw-r--r--src/missing-string.c209
-rw-r--r--src/sexp.c111
-rw-r--r--tests/ChangeLog4
-rw-r--r--tests/tsexp.c63
9 files changed, 450 insertions, 36 deletions
diff --git a/src/ChangeLog b/src/ChangeLog
index b012286f..e1419dbd 100644
--- a/src/ChangeLog
+++ b/src/ChangeLog
@@ -1,3 +1,16 @@
+2002-05-16 Werner Koch <wk@gnupg.org>
+
+ * missing-string.c: New.
+
+ * gcrypt.h: Add new error codes GCRYERR_SEXP_ and typedefs
+ GcryMPI, GcrySexp, GcryCipherHd, GcryMDHd as aliases for the old
+ ones using an underscore.
+
+ * global.c (gcry_strerror): Add strings fro the new error codes.
+ * sexp.c (gcry_sexp_canon_len): Use a macro to convert from new to
+ old error codes.
+ (gcry_sexp_create,gcry_sexp_new): New.
+
2002-05-15 Werner Koch <wk@gnupg.org>
* mutex.h (DEFINE_LOCAL_MUTEX): Macro to define a mutex and
diff --git a/src/Makefile.am b/src/Makefile.am
index 71b82d1e..447da749 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -50,7 +50,8 @@ libgcrypt_la_SOURCES = g10lib.h \
secmem.c \
secmem.h \
mpi.h \
- mutex.h
+ mutex.h \
+ missing-string.c
libgcrypt_la_DEPENDENCIES = libgcrypt.sym \
../cipher/libcipher.la ../mpi/libmpi.la
diff --git a/src/g10lib.h b/src/g10lib.h
index 125c7826..bfbe7f80 100644
--- a/src/g10lib.h
+++ b/src/g10lib.h
@@ -128,16 +128,22 @@ MPI _gcry_generate_elg_prime( int mode, unsigned pbits, unsigned qbits,
-/* replacements of missing functions */
-#ifndef HAVE_MEMICMP
-int memicmp( const char *a, const char *b, size_t n );
-#endif
+/* replacements of missing functions (missing-string.c)*/
#ifndef HAVE_STPCPY
-char *stpcpy(char *a,const char *b);
+char *stpcpy (char *a, const char *b);
+#endif
+#ifndef HAVE_STRSEP
+char *strsep (char **stringp, const char *delim);
#endif
#ifndef HAVE_STRLWR
-char *strlwr(char *a);
+char *strlwr (char *a);
#endif
+#ifndef HAVE_STRCASECMP
+int strcasecmp (const char *a, const char *b);
+#endif
+
+
+/* macros used to rename missing functions */
#ifndef HAVE_STRTOUL
#define strtoul(a,b,c) ((unsigned long)strtol((a),(b),(c)))
#endif
@@ -154,6 +160,7 @@ char *strlwr(char *a);
#define raise(a) kill(getpid(), (a))
#endif
+
/* some handy macros */
#ifndef STR
#define STR(v) #v
@@ -164,3 +171,5 @@ char *strlwr(char *a);
#endif /* G10LIB_H */
+
+
diff --git a/src/gcrypt.h b/src/gcrypt.h
index c0b979ff..aa382a38 100644
--- a/src/gcrypt.h
+++ b/src/gcrypt.h
@@ -52,6 +52,7 @@ extern "C" {
struct gcry_mpi;
typedef struct gcry_mpi *GCRY_MPI;
+typedef struct gcry_mpi *GcryMPI;
/*******************************************
* *
@@ -90,7 +91,23 @@ enum {
GCRYERR_NO_OBJ = 68, /* Missing item in an object */
GCRYERR_NOT_IMPL = 69, /* Not implemented */
GCRYERR_CONFLICT = 70,
- GCRYERR_INV_CIPHER_MODE = 71
+ GCRYERR_INV_CIPHER_MODE = 71,
+
+ /* error codes pertaining to S-expressions */
+ GCRYERR_SEXP_INV_LEN_SPEC = 201,
+ GCRYERR_SEXP_STRING_TOO_LONG = 202,
+ GCRYERR_SEXP_UNMATCHED_PAREN = 203,
+ GCRYERR_SEXP_NOT_CANONICAL = 204,
+ GCRYERR_SEXP_BAD_CHARACTER = 205,
+ GCRYERR_SEXP_BAD_QUOTATION = 206,/* or invalid hex or octal value */
+ GCRYERR_SEXP_ZERO_PREFIX = 207,/* first character of a length is 0 */
+ GCRYERR_SEXP_NESTED_DH = 208,/* nested display hints */
+ GCRYERR_SEXP_UNMATCHED_DH = 209,/* unmatched display hint */
+ GCRYERR_SEXP_UNEXPECTED_PUNC = 210,/* unexpected reserved punctuation */
+ GCRYERR_SEXP_BAD_HEX_CHAR = 211,
+ GCRYERR_SEXP_ODD_HEX_NUMBERS = 212,
+ GCRYERR_SEXP_BAD_OCT_CHAR = 213
+
};
const char *gcry_check_version( const char *req_version );
@@ -151,6 +168,7 @@ enum gcry_random_level {
struct gcry_sexp;
typedef struct gcry_sexp *GCRY_SEXP;
+typedef struct gcry_sexp *GcrySexp; /* this type looks more pretty */
enum gcry_sexp_format {
GCRYSEXP_FMT_DEFAULT = 0,
@@ -159,20 +177,29 @@ enum gcry_sexp_format {
GCRYSEXP_FMT_ADVANCED = 3
};
-void gcry_sexp_release( GCRY_SEXP sexp );
+int gcry_sexp_new (GCRY_SEXP *retsexp, const void *buffer, size_t length,
+ int autodetect);
+int gcry_sexp_create (GCRY_SEXP *retsexp, void *buffer, size_t length,
+ int autodetect, void (*freefnc)(void*) );
+int gcry_sexp_sscan (GCRY_SEXP *retsexp, size_t *erroff,
+ const char *buffer, size_t length );
+int gcry_sexp_build (GCRY_SEXP *retsexp, size_t *erroff,
+ const char *format, ... );
+void gcry_sexp_release (GCRY_SEXP sexp);
+
+size_t gcry_sexp_canon_len (const unsigned char *buffer, size_t length,
+ size_t *erroff, int *errcode);
+
+size_t gcry_sexp_sprint (GCRY_SEXP sexp, int mode, char *buffer,
+ size_t maxlength );
+
void gcry_sexp_dump( const GCRY_SEXP a );
GCRY_SEXP gcry_sexp_cons( const GCRY_SEXP a, const GCRY_SEXP b );
GCRY_SEXP gcry_sexp_alist( const GCRY_SEXP *array );
GCRY_SEXP gcry_sexp_vlist( const GCRY_SEXP a, ... );
GCRY_SEXP gcry_sexp_append( const GCRY_SEXP a, const GCRY_SEXP n );
GCRY_SEXP gcry_sexp_prepend( const GCRY_SEXP a, const GCRY_SEXP n );
-int gcry_sexp_sscan( GCRY_SEXP *retsexp, size_t *erroff,
- const char *buffer, size_t length );
-int gcry_sexp_build( GCRY_SEXP *retsexp, size_t *erroff,
- const char *format, ... );
-size_t gcry_sexp_sprint( GCRY_SEXP sexp, int mode, char *buffer,
- size_t maxlength );
-GCRY_SEXP gcry_sexp_find_token( GCRY_SEXP list,
+GCRY_SEXP gcry_sexp_find_token( GCRY_SEXP list,
const char *tok, size_t toklen );
int gcry_sexp_length( const GCRY_SEXP list );
GCRY_SEXP gcry_sexp_nth( const GCRY_SEXP list, int number );
@@ -183,8 +210,6 @@ const char *gcry_sexp_nth_data( const GCRY_SEXP list, int number,
size_t *datalen );
GCRY_MPI gcry_sexp_nth_mpi( GCRY_SEXP list, int number, int mpifmt );
-size_t gcry_sexp_canon_len (const unsigned char *buffer, size_t length,
- size_t *erroff, int *errcode);
/*******************************************
@@ -305,6 +330,7 @@ int gcry_mpi_get_flag( GCRY_MPI a, enum gcry_mpi_flag flag );
struct gcry_cipher_handle;
typedef struct gcry_cipher_handle *GCRY_CIPHER_HD;
+typedef struct gcry_cipher_handle *GcryCipherHd;
enum gcry_cipher_algos {
GCRY_CIPHER_NONE = 0,
@@ -436,6 +462,7 @@ struct gcry_md_handle {
byte buf[1];
};
typedef struct gcry_md_handle *GCRY_MD_HD;
+typedef struct gcry_md_handle *GcryMDHd;
GCRY_MD_HD gcry_md_open( int algo, unsigned flags );
diff --git a/src/global.c b/src/global.c
index 7d922b70..192cf503 100644
--- a/src/global.c
+++ b/src/global.c
@@ -280,6 +280,19 @@ gcry_strerror( int ec )
X(CONFLICT, N_("conflict"))
X(INV_CIPHER_MODE,N_("invalid cipher mode"))
+ X(SEXP_INV_LEN_SPEC ,N_("invalid length specification"))
+ X(SEXP_STRING_TOO_LONG,N_("string too long"))
+ X(SEXP_UNMATCHED_PAREN,N_("unmatched parenthesis"))
+ X(SEXP_NOT_CANONICAL ,N_("not a canonical S-expression"))
+ X(SEXP_BAD_CHARACTER ,N_("bad character"))
+ X(SEXP_BAD_QUOTATION ,N_("invalid hex/octal value or bad quotation"))
+ X(SEXP_ZERO_PREFIX ,N_("a length may not begin with zero"))
+ X(SEXP_NESTED_DH ,N_("nested display hints"))
+ X(SEXP_UNMATCHED_DH ,N_("unmatched display hint close"))
+ X(SEXP_UNEXPECTED_PUNC,N_("unexpected reserved punctuation"))
+ X(SEXP_BAD_HEX_CHAR, N_("invalid hex character"))
+ X(SEXP_ODD_HEX_NUMBERS,N_("odd number of hex characters"))
+ X(SEXP_BAD_OCT_CHAR, N_("invalid octal character"))
default:
sprintf( buf, "ec=%d", ec );
diff --git a/src/missing-string.c b/src/missing-string.c
new file mode 100644
index 00000000..f9c5df1a
--- /dev/null
+++ b/src/missing-string.c
@@ -0,0 +1,209 @@
+/* missing-string.c - missing string utilities
+ * Copyright (C) 1994, 1998, 1999, 2000, 2001 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 Lesser General Public License as
+ * published by the Free Software Foundation; either version 2.1 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 Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser 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
+ */
+
+#include <config.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "g10lib.h"
+
+
+#ifndef HAVE_STPCPY
+char *
+stpcpy(char *a,const char *b)
+{
+ while( *b )
+ *a++ = *b++;
+ *a = 0;
+
+ return (char*)a;
+}
+#endif
+
+
+#ifndef HAVE_STRSEP
+/* code taken from glibc-2.2.1/sysdeps/generic/strsep.c */
+char *
+strsep (char **stringp, const char *delim)
+{
+ char *begin, *end;
+
+ begin = *stringp;
+ if (begin == NULL)
+ return NULL;
+
+ /* A frequent case is when the delimiter string contains only one
+ character. Here we don't need to call the expensive `strpbrk'
+ function and instead work using `strchr'. */
+ if (delim[0] == '\0' || delim[1] == '\0')
+ {
+ char ch = delim[0];
+
+ if (ch == '\0')
+ end = NULL;
+ else
+ {
+ if (*begin == ch)
+ end = begin;
+ else if (*begin == '\0')
+ end = NULL;
+ else
+ end = strchr (begin + 1, ch);
+ }
+ }
+ else
+ /* Find the end of the token. */
+ end = strpbrk (begin, delim);
+
+ if (end)
+ {
+ /* Terminate the token and set *STRINGP past NUL character. */
+ *end++ = '\0';
+ *stringp = end;
+ }
+ else
+ /* No more delimiters; this is the last token. */
+ *stringp = NULL;
+
+ return begin;
+}
+#endif /*HAVE_STRSEP*/
+
+
+#ifndef HAVE_STRLWR
+char *
+strlwr(char *s)
+{
+ char *p;
+ for(p=s; *p; p++ )
+ *p = tolower(*p);
+ return s;
+}
+#endif
+
+#ifndef HAVE_STRCASECMP
+int
+strcasecmp( const char *a, const char *b )
+{
+ for( ; *a && *b; a++, b++ ) {
+ if( *a != *b && toupper(*a) != toupper(*b) )
+ break;
+ }
+ return *(const byte*)a - *(const byte*)b;
+}
+#endif
+
+
+#ifdef __MINGW32__
+/*
+ * Like vsprintf but provides a pointer to malloc'd storage, which
+ * must be freed by the caller (m_free). Taken from libiberty as
+ * found in gcc-2.95.2 and a little bit modernized.
+ * FIXME: Write a new CRT for W32.
+ */
+int
+vasprintf ( char **result, const char *format, va_list args)
+{
+ const char *p = format;
+ /* Add one to make sure that it is never zero, which might cause malloc
+ to return NULL. */
+ int total_width = strlen (format) + 1;
+ va_list ap;
+
+ /* this is not really portable but works under Windows */
+ memcpy ( &ap, &args, sizeof (va_list));
+
+ while (*p != '\0')
+ {
+ if (*p++ == '%')
+ {
+ while (strchr ("-+ #0", *p))
+ ++p;
+ if (*p == '*')
+ {
+ ++p;
+ total_width += abs (va_arg (ap, int));
+ }
+ else
+ {
+ char *endp;
+ total_width += strtoul (p, &endp, 10);
+ p = endp;
+ }
+ if (*p == '.')
+ {
+ ++p;
+ if (*p == '*')
+ {
+ ++p;
+ total_width += abs (va_arg (ap, int));
+ }
+ else
+ {
+ char *endp;
+ total_width += strtoul (p, &endp, 10);
+ p = endp;
+ }
+ }
+ while (strchr ("hlL", *p))
+ ++p;
+ /* Should be big enough for any format specifier except %s
+ and floats. */
+ total_width += 30;
+ switch (*p)
+ {
+ case 'd':
+ case 'i':
+ case 'o':
+ case 'u':
+ case 'x':
+ case 'X':
+ case 'c':
+ (void) va_arg (ap, int);
+ break;
+ case 'f':
+ case 'e':
+ case 'E':
+ case 'g':
+ case 'G':
+ (void) va_arg (ap, double);
+ /* Since an ieee double can have an exponent of 307, we'll
+ make the buffer wide enough to cover the gross case. */
+ total_width += 307;
+
+ case 's':
+ total_width += strlen (va_arg (ap, char *));
+ break;
+ case 'p':
+ case 'n':
+ (void) va_arg (ap, char *);
+ break;
+ }
+ }
+ }
+ *result = m_alloc (total_width);
+ if (*result != NULL)
+ return vsprintf (*result, format, args);
+ else
+ return 0;
+}
+
+#endif /*__MINGW32__*/
+
diff --git a/src/sexp.c b/src/sexp.c
index c1bf804e..aea3a5fa 100644
--- a/src/sexp.c
+++ b/src/sexp.c
@@ -59,6 +59,13 @@ struct gcry_sexp {
#define TOKEN_SPECIALS "-./_:*+="
+#define OLDPARSECODE(a) (-((GCRYERR_SEXP_ ## a)-GCRYERR_SEXP_INV_LEN_SPEC+1))
+
+
+static int
+sexp_sscan( GCRY_SEXP *retsexp, size_t *erroff ,
+ const char *buffer, size_t length, va_list arg_ptr, int argflag);
+
#if 0
static void
@@ -174,6 +181,73 @@ normalize ( GCRY_SEXP list )
return list;
}
+/* Create a new S-expression object by reading LENGTH bytes from
+ BUFFER, assuming it is canonilized encoded or autodetected encoding
+ when AUTODETECT is set to 1. With FREEFNC not NULL, ownership of
+ the buffer is transferred to tyhe newle created object. FREEFNC
+ should be the freefnc used to release BUFFER; there is no guarantee
+ at which point this function is called; most likey you want to use
+ free() or gcry_free().
+
+ Passing LENGTH and AUTODETECT as 0 is allowed to indicate that
+ BUFFER points to a valid canonical encoded S-expression. A LENGTH
+ of 0 and AUTODETECT 1 indicates that buffer points to a
+ null-terminated string.
+
+ This function returns 0 and and the pointer to the new object in
+ RETSEXP or an error code in which case RETSEXP is set to NULL. */
+int
+gcry_sexp_create (GCRY_SEXP *retsexp, void *buffer, size_t length,
+ int autodetect, void (*freefnc)(void*) )
+{
+ int errcode;
+ GCRY_SEXP se;
+ volatile va_list dummy_arg_ptr;
+
+ if (!retsexp)
+ return GCRYERR_INV_ARG;
+ *retsexp = NULL;
+ if (autodetect < 0 || autodetect > 1 || !buffer)
+ return GCRYERR_INV_ARG;
+
+ if (!length && !autodetect)
+ { /* What a brave caller to assume that there is really a canonical
+ encoded S-expression in buffer */
+ length = gcry_sexp_canon_len (buffer, 0, NULL, &errcode);
+ if (!length)
+ return 200 - errcode;
+ }
+ else if (!length && autodetect)
+ { /* buffer is a string */
+ length = strlen ((char *)buffer);
+ }
+
+ errcode = sexp_sscan (&se, NULL, buffer, length, dummy_arg_ptr, 0);
+ if (errcode)
+ return 200 - errcode;
+
+ *retsexp = se;
+ if (freefnc)
+ {
+ /* For now we release the buffer immediately. As soon as we
+ have changed the internal represenation of S-expression to
+ the canoncial format - which has the advantage of faster
+ parsing - we will use this function as a closure in our
+ GCRYSEXP object and use the BUFFER directly */
+ freefnc (buffer);
+ }
+ return 0;
+}
+
+/* Same as gcry_sexp_create but don't transfer ownership */
+int
+gcry_sexp_new (GCRY_SEXP *retsexp, const void *buffer, size_t length,
+ int autodetect)
+{
+ return gcry_sexp_create (retsexp, (void *)buffer, length, autodetect, NULL);
+}
+
+
/****************
* Release resource of the given SEXP object.
*/
@@ -890,7 +964,7 @@ sexp_sscan( GCRY_SEXP *retsexp, size_t *erroff ,
else if( *p == '#' ) {
if( (hexcount & 1) ) {
*erroff = p - buffer;
- return -12; /* odd number of hex digits */
+ return OLDPARSECODE (ODD_HEX_NUMBERS);
}
datalen = hexcount/2;
@@ -907,7 +981,7 @@ sexp_sscan( GCRY_SEXP *retsexp, size_t *erroff ,
}
else if( !isspace( *p ) ) {
*erroff = p - buffer;
- return -11; /* invalid hex character */
+ return OLDPARSECODE (BAD_HEX_CHAR);
}
}
else if( base64 ) {
@@ -1394,7 +1468,7 @@ gcry_sexp_sprint( const GCRY_SEXP list, int mode,
return the actual length this S-expression uses. For a valid S-Exp
it should never return 0. If LENGTH is not zero, the maximum
length to scan is given - this can be used for syntax checks of
- data passed from outside. erroce and erroff may both be passed as
+ data passed from outside. errorcode and erroff may both be passed as
NULL
Errorcodes (for historic reasons they are all negative):
@@ -1407,7 +1481,10 @@ gcry_sexp_sprint( const GCRY_SEXP list, int mode,
-7 := a length may not begin with zero
-8 := nested display hints
-9 := unmatched display hint close
- -10 := unexpected reserved punctuation
+ -10 := unexpected reserved punctuation
+
+ Use this formula to convert the errorcodes:
+ gcryerr = 200 - errcode;
*/
size_t
gcry_sexp_canon_len (const unsigned char *buffer, size_t length,
@@ -1432,7 +1509,7 @@ gcry_sexp_canon_len (const unsigned char *buffer, size_t length,
return 0;
if (*buffer != '(')
{
- *errcode = -4; /* not a canonical S-expression */
+ *errcode = OLDPARSECODE (NOT_CANONICAL);
return 0;
}
@@ -1441,7 +1518,7 @@ gcry_sexp_canon_len (const unsigned char *buffer, size_t length,
if (length && count >= length)
{
*erroff = count;
- *errcode = -2; /* string too long */
+ *errcode = OLDPARSECODE (STRING_TOO_LONG);
return 0;
}
@@ -1452,7 +1529,7 @@ gcry_sexp_canon_len (const unsigned char *buffer, size_t length,
if (length && (count+datalen) >= length)
{
*erroff = count;
- *errcode = -2; /* string too long */
+ *errcode = OLDPARSECODE (STRING_TOO_LONG);
return 0;
}
count += datalen;
@@ -1464,7 +1541,7 @@ gcry_sexp_canon_len (const unsigned char *buffer, size_t length,
else
{
*erroff = count;
- *errcode = -1;
+ *errcode = OLDPARSECODE (INV_LEN_SPEC);
return 0;
}
}
@@ -1473,7 +1550,7 @@ gcry_sexp_canon_len (const unsigned char *buffer, size_t length,
if (disphint)
{
*erroff = count;
- *errcode = -9; /* open display hint */
+ *errcode = OLDPARSECODE (UNMATCHED_DH);
return 0;
}
level++;
@@ -1483,13 +1560,13 @@ gcry_sexp_canon_len (const unsigned char *buffer, size_t length,
if (!level)
{
*erroff = count;
- *errcode = -3; /* unmatched parenthesis */
+ *errcode = OLDPARSECODE (UNMATCHED_PAREN);
return 0;
}
if (disphint)
{
*erroff = count;
- *errcode = -9; /* open display hint */
+ *errcode = OLDPARSECODE (UNMATCHED_DH);
return 0;
}
if (!--level)
@@ -1500,7 +1577,7 @@ gcry_sexp_canon_len (const unsigned char *buffer, size_t length,
if (disphint)
{
*erroff = count;
- *errcode = -8; /* nested display hints */
+ *errcode = OLDPARSECODE (NESTED_DH);
return 0;
}
disphint = p;
@@ -1510,7 +1587,7 @@ gcry_sexp_canon_len (const unsigned char *buffer, size_t length,
if( !disphint )
{
*erroff = count;
- *errcode = -9; /* unmatched display hint close */
+ *errcode = OLDPARSECODE (UNMATCHED_DH);
return 0;
}
disphint = NULL;
@@ -1520,7 +1597,7 @@ gcry_sexp_canon_len (const unsigned char *buffer, size_t length,
if (*p == '0')
{
*erroff = count;
- *errcode = -7; /* a length may not begin with zero */
+ *errcode = OLDPARSECODE (ZERO_PREFIX);
return 0;
}
datalen = atoi_1 (p);
@@ -1528,16 +1605,14 @@ gcry_sexp_canon_len (const unsigned char *buffer, size_t length,
else if (*p == '&' || *p == '\\')
{
*erroff = count;
- *errcode = -10; /* unexpected reserved punctuation */
+ *errcode = OLDPARSECODE (UNEXPECTED_PUNC);
return 0;
}
else
{
*erroff = count;
- *errcode = -5; /* bad character */
+ *errcode = OLDPARSECODE (BAD_CHARACTER);
return 0;
}
}
}
-
-
diff --git a/tests/ChangeLog b/tests/ChangeLog
index ca1b5ef1..e0c73312 100644
--- a/tests/ChangeLog
+++ b/tests/ChangeLog
@@ -1,3 +1,7 @@
+2002-05-16 Werner Koch <wk@gnupg.org>
+
+ * tsexp.c (back_and_forth): Very minimal test of the new functions.
+
2002-05-14 Werner Koch <wk@gnupg.org>
Changed license of all files to the LGPL.
diff --git a/tests/tsexp.c b/tests/tsexp.c
index 2615f424..dd852f96 100644
--- a/tests/tsexp.c
+++ b/tests/tsexp.c
@@ -213,6 +213,64 @@ canon_len (void)
}
+static void
+back_and_forth_one (int testno, const char *buffer, size_t length)
+{
+ int rc;
+ GcrySexp se, se1;
+ size_t n, n1;
+ char *p1;
+
+ rc = gcry_sexp_new (&se, buffer, length, 1);
+ if (rc)
+ {
+ fail ("baf %d: gcry_sexp_new failed: %s\n", testno, gcry_strerror (rc));
+ return;
+ }
+ n1 = gcry_sexp_sprint (se, GCRYSEXP_FMT_CANON, NULL, 0);
+ if (!n1)
+ {
+ fail ("baf %d: get required length for canon failed\n", testno);
+ return;
+ }
+ p1 = gcry_xmalloc (n1);
+ n = gcry_sexp_sprint (se, GCRYSEXP_FMT_CANON, p1, n1);
+ if (n1 != n+1) /* sprints adds an extra 0 but dies not return it */
+ {
+ fail ("baf %d: length mismatch for canon\n", testno);
+ return;
+ }
+ rc = gcry_sexp_create (&se1, p1, n, 0, gcry_free);
+ if (rc)
+ {
+ fail ("baf %d: gcry_sexp_create failed: %s\n",
+ testno, gcry_strerror (rc));
+ return;
+ }
+ gcry_sexp_release (se1);
+
+ /* FIXME: we need a lot more tests */
+
+ gcry_sexp_release (se);
+}
+
+
+
+static void
+back_and_forth (void)
+{
+ static struct { char *buf; int len; } tests[] = {
+ { "(7:g34:fgh1::2:())", 0 },
+ { "(7:g34:fgh1::2:())", 18 },
+ { NULL, 0 }
+ };
+ int idx;
+
+ for (idx=0; tests[idx].buf; idx++)
+ back_and_forth_one (idx, tests[idx].buf, tests[idx].len);
+}
+
+
int
main (int argc, char **argv)
{
@@ -221,8 +279,13 @@ main (int argc, char **argv)
basic ();
canon_len ();
+ back_and_forth ();
return error_count? 1:0;
}
+
+
+
+