[or-cvs] Introduce a few unit tests (from older code), refactor comp...

Nick Mathewson nickm at seul.org
Tue Apr 15 19:10:20 UTC 2003


Update of /home/or/cvsroot/src/or
In directory moria.mit.edu:/tmp/cvs-serv17073/src/or

Modified Files:
	buffers.c connection.c or.h test.c 
Log Message:
Introduce a few unit tests (from older code), refactor compression setup/teardown

Index: buffers.c
===================================================================
RCS file: /home/or/cvsroot/src/or/buffers.c,v
retrieving revision 1.18
retrieving revision 1.19
diff -u -d -r1.18 -r1.19
--- buffers.c	7 Apr 2003 02:12:02 -0000	1.18
+++ buffers.c	15 Apr 2003 19:10:18 -0000	1.19
@@ -136,7 +136,57 @@
 
 }
 
-#ifdef USE_ZLIB
+z_stream *zstream_new(int compression)
+{
+  z_stream* stream;
+  stream = malloc(sizeof(z_stream));
+  if (!stream)
+    return NULL;
+  memset(stream, 0, sizeof(z_stream));
+  if (compression) {
+    if (deflateInit(stream, Z_DEFAULT_COMPRESSION) != Z_OK) {
+      log(LOG_ERR, "Error initializing zlib: %s", stream->msg);
+      free(stream);
+      return NULL;
+    }
+  } else {
+    if (inflateInit(stream) != Z_OK) {
+      log(LOG_ERR, "Error initializing zlib: %s", stream->msg);
+      free(stream);
+      return NULL;
+    }
+  }
+  return stream;
+}
+
+z_compression *compression_new()
+{
+  return (z_compression *) zstream_new(1);
+}
+
+z_decompression *decompression_new()
+{
+  return (z_compression *) zstream_new(0);
+}
+
+void compression_free(z_stream *stream)
+{
+  int r;
+  r = deflateEnd(stream);
+  if (r != Z_OK)
+    log(LOG_ERR, "while closing zlib: %d (%s)", r, stream->msg);
+  free(stream);
+}
+
+void decompression_free(z_stream *stream)
+{
+  int r;
+  r = inflateEnd(stream);
+  if (r != Z_OK)
+    log(LOG_ERR, "while closing zlib: %d (%s)", r, stream->msg);
+  free(stream);
+}
+
 int compress_from_buf(char *string, int string_len, 
                       char **buf_in, int *buflen_in, int *buf_datalen_in,
                       z_stream *zstream, int flush) {
@@ -209,13 +259,16 @@
       return -1;
     }
 }
-#endif
 
 int fetch_from_buf(char *string, int string_len,
                    char **buf, int *buflen, int *buf_datalen) {
 
   /* if there are string_len bytes in buf, write them onto string,
-   * then memmove buf back (that is, remove them from buf) */
+   * then memmove buf back (that is, remove them from buf).
+   *
+   * If there are not enough bytes on the buffer to fill string, return -1.
+   *
+   * Return the number of bytes still on the buffer. */
 
   assert(string && buf && *buf && buflen && buf_datalen);
 

Index: connection.c
===================================================================
RCS file: /home/or/cvsroot/src/or/connection.c,v
retrieving revision 1.52
retrieving revision 1.53
diff -u -d -r1.52 -r1.53
--- connection.c	11 Apr 2003 22:11:11 -0000	1.52
+++ connection.c	15 Apr 2003 19:10:18 -0000	1.53
@@ -130,20 +130,10 @@
   if (type == CONN_TYPE_AP || type == CONN_TYPE_EXIT)  {
     if (buf_new(&conn->z_outbuf, &conn->z_outbuflen, &conn->z_outbuf_datalen) < 0)
       return NULL;
-    if (! (conn->compression = malloc(sizeof(z_stream))))
-      return NULL;
-    if (! (conn->decompression = malloc(sizeof(z_stream))))
-      return NULL;
-    memset(conn->compression, 0, sizeof(z_stream));
-    memset(conn->decompression, 0, sizeof(z_stream));
-    if (deflateInit(conn->compression, Z_DEFAULT_COMPRESSION) != Z_OK) {
-      log(LOG_ERR, "Error initializing zlib: %s", conn->compression->msg);
+    if (! (conn->compression = compression_new()))
       return NULL;
-    }
-    if (inflateInit(conn->decompression) != Z_OK) {
-      log(LOG_ERR, "Error initializing zlib: %s", conn->decompression->msg);
+    if (! (conn->decompression = decompression_new()))
       return NULL;
-    }
   } else {
     conn->compression = conn->decompression = NULL;
   }
@@ -181,14 +171,8 @@
   }
 #ifdef USE_ZLIB
   if (conn->compression) {
-    if (inflateEnd(conn->decompression) != Z_OK)
-      log(LOG_ERR,"connection_free(): while closing zlib: %s",
-          conn->decompression->msg);
-    if (deflateEnd(conn->compression) != Z_OK)
-      log(LOG_ERR,"connection_free(): while closing zlib: %s",
-          conn->compression->msg);
-    free(conn->compression);
-    free(conn->decompression);
+    decompression_free(conn->decompression);
+    compression_free(conn->compression);
     buf_free(conn->z_outbuf);
   }
 #endif

Index: or.h
===================================================================
RCS file: /home/or/cvsroot/src/or/or.h,v
retrieving revision 1.61
retrieving revision 1.62
diff -u -d -r1.61 -r1.62
--- or.h	11 Apr 2003 22:28:51 -0000	1.61
+++ or.h	15 Apr 2003 19:10:18 -0000	1.62
@@ -36,11 +36,11 @@
 #include <errno.h>
 #include <assert.h>
 #include <time.h>
-#ifdef USE_ZLIB
+
 #define free_func zlib_free_func
 #include <zlib.h>
 #undef free_func
-#endif
+
 
 #include "../common/crypto.h"
 #include "../common/log.h"
@@ -174,6 +174,9 @@
 /* legal characters in a filename */
 #define CONFIG_LEGAL_FILENAME_CHARACTERS "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789.-_/"
 
+typedef z_stream z_compression;
+typedef z_stream z_decompression;
+
 struct config_line {
   char *key;
   char *value;
@@ -446,10 +449,14 @@
    * then memmove buf back (that is, remove them from buf)
    */
 
-#ifdef USE_ZLIB
+z_compression* compression_new();
+z_decompression* decompression_new();
+void compression_free(z_compression *);
+void decompression_free(z_decompression *);
+
 int compress_from_buf(char *string, int string_len, 
 		      char **buf_in, int *buflen_in, int *buf_datalen_in,
-		      z_stream *zstream, int flush);
+		      z_compression *compression, int flush);
   /* read and compress as many characters as possible from buf, writing up to
    * string_len of them onto string, then memmove buf back.  Return number of
    * characters written.
@@ -457,10 +464,9 @@
 
 int decompress_buf_to_buf(char **buf_in, int *buflen_in, int *buf_datalen_in,
 			  char **buf_out, int *buflen_out, int *buf_datalen_out,
-			  z_stream *zstream, int flush);
+			  z_decompression *decompression, int flush);
   /* XXX document this NM
    */
-#endif
 
 int find_on_inbuf(char *string, int string_len,
                   char *buf, int buf_datalen);

Index: test.c
===================================================================
RCS file: /home/or/cvsroot/src/or/test.c,v
retrieving revision 1.2
retrieving revision 1.3
diff -u -d -r1.2 -r1.3
--- test.c	7 Apr 2003 13:25:44 -0000	1.2
+++ test.c	15 Apr 2003 19:10:18 -0000	1.3
@@ -2,28 +2,211 @@
 /* See LICENSE for licensing information */
 /* $Id$ */
 
+#include <stdio.h>
+#include <fcntl.h>
+
 #include "or.h"
 #include "../common/test.h"
 
 void
+setup_directory() {
+  char buf[256];
+  sprintf(buf, "/tmp/tor_test");
+  if (mkdir(buf, 0700) && errno != EEXIST)
+    fprintf(stderr, "Can't create directory %s", buf);
+}
+
+void
 test_buffers() {
+  char str[256];
+  char str2[256];
+
   char *buf;
   int buflen, buf_datalen;
 
-  if (buf_new(&buf, &buflen, &buf_datalen)) {
+  char *buf2;
+  int buf2len, buf2_datalen;
+
+  int s, i, j, eof;
+  z_compression *comp;
+  z_decompression *decomp;
+
+  /****
+   * buf_new
+   ****/
+  if (buf_new(&buf, &buflen, &buf_datalen))
     test_fail();
+
+  test_eq(buflen, MAX_BUF_SIZE);
+  test_eq(buf_datalen, 0);
+
+  /****
+   * read_to_buf
+   ****/
+  s = open("/tmp/tor_test/data", O_WRONLY|O_CREAT|O_TRUNC, 0600);
+  for (j=0;j<256;++j) {
+    str[j] = (char)j;
   }
+  write(s, str, 256);
+  close(s);
+  
+  s = open("/tmp/tor_test/data", O_RDONLY, 0);
+  eof = 0;
+  i = read_to_buf(s, 10, &buf, &buflen, &buf_datalen, &eof);
+  test_eq(buflen, MAX_BUF_SIZE);
+  test_eq(buf_datalen, 10);
+  test_eq(eof, 0);
+  test_eq(i, 10);
+  test_memeq(str, buf, 10);
 
+  /* Test reading 0 bytes. */
+  i = read_to_buf(s, 0, &buf, &buflen, &buf_datalen, &eof);
+  test_eq(buflen, MAX_BUF_SIZE);
+  test_eq(buf_datalen, 10);
+  test_eq(eof, 0);
+  test_eq(i, 0);
+
+  /* Now test when buffer is filled exactly. */
+  buflen = 16;
+  i = read_to_buf(s, 6, &buf, &buflen, &buf_datalen, &eof);
+  test_eq(buflen, 16);
+  test_eq(buf_datalen, 16);
+  test_eq(eof, 0);
+  test_eq(i, 6);
+  test_memeq(str, buf, 16);
+  
+  /* Now test when buffer is filled with more data to read. */
+  buflen = 32;
+  i = read_to_buf(s, 128, &buf, &buflen, &buf_datalen, &eof);
+  test_eq(buflen, 32);
+  test_eq(buf_datalen, 32);
+  test_eq(eof, 0);
+  test_eq(i, 16);
+  test_memeq(str, buf, 32);
+
+  /* Now read to eof. */
+  buflen = MAX_BUF_SIZE;
+  test_assert(buflen > 256);
+  i = read_to_buf(s, 1024, &buf, &buflen, &buf_datalen, &eof);
+  test_eq(i, (256-32));
   test_eq(buflen, MAX_BUF_SIZE);
+  test_eq(buf_datalen, 256);
+  test_memeq(str, buf, 256);
+  test_eq(eof, 0);
+
+  i = read_to_buf(s, 1024, &buf, &buflen, &buf_datalen, &eof);
+  test_eq(i, 0);
+  test_eq(buflen, MAX_BUF_SIZE);
+  test_eq(buf_datalen, 256);
+  test_eq(eof, 1);
+
+  close(s);
+
+  /**** 
+   * find_on_inbuf
+   ****/
+
+  test_eq(((int)'d') + 1, find_on_inbuf("abcd", 4, buf, buf_datalen));
+  test_eq(-1, find_on_inbuf("xyzzy", 5, buf, buf_datalen));
+  /* Make sure we don't look off the end of the buffef */
+  buf[256] = 'A';
+  buf[257] = 'X';
+  test_eq(-1, find_on_inbuf("\xff" "A", 2, buf, buf_datalen));
+  test_eq(-1, find_on_inbuf("AX", 2, buf, buf_datalen));
+  /* Make sure we use the string length */
+  test_eq(((int)'d')+1, find_on_inbuf("abcdX", 4, buf, buf_datalen));
+
+  /****
+   * fetch_from_buf
+   ****/
+  memset(str2, 255, 256);
+  test_eq(246, fetch_from_buf(str2, 10, &buf, &buflen, &buf_datalen));
+  test_memeq(str2, str, 10);
+  test_memeq(str+10,buf,246);
+  test_eq(buf_datalen,246);
+
+  test_eq(-1, fetch_from_buf(str2, 247, &buf, &buflen, &buf_datalen));
+  test_memeq(str+10,buf,246);
+  test_eq(buf_datalen, 246);
+  
+  test_eq(0, fetch_from_buf(str2, 246, &buf, &buflen, &buf_datalen));
+  test_memeq(str2, str+10, 246);
+  test_eq(buflen,MAX_BUF_SIZE);
+  test_eq(buf_datalen,0);
+
+  /****
+   * write_to_buf
+   ****/
+  memset(buf, (int)'-', 256);
+  i = write_to_buf("Hello world", 11, &buf, &buflen, &buf_datalen);
+  test_eq(i, 11);
+  test_eq(buf_datalen, 11);
+  test_memeq(buf, "Hello world", 11);
+  i = write_to_buf("XYZZY", 5, &buf, &buflen, &buf_datalen);
+  test_eq(i, 16);
+  test_eq(buf_datalen, 16);
+  test_memeq(buf, "Hello worldXYZZY", 16);
+  /* Test when buffer is overfull. */
+  buflen = 18;
+  test_eq(-1, write_to_buf("This string will not fit.", 25, 
+                           &buf, &buflen, &buf_datalen));
+  test_eq(buf_datalen, 16);
+  test_memeq(buf, "Hello worldXYZZY--", 18);
+  buflen = MAX_BUF_SIZE;
+
+  /****
+   * flush_buf
+   ****/
+
+  /***
+   * compress_from_buf (simple)
+   ***/
+  buf_datalen = 0;
+  comp = compression_new();
+  for (i = 0; i < 20; ++i) {
+    write_to_buf("Hello world.  ", 14, &buf, &buflen, &buf_datalen);
+  }
+  i = compress_from_buf(str, 256, &buf, &buflen, &buf_datalen, comp, 1);
+  test_eq(buf_datalen, 0);
+  /*
+  for (j = 0; j <i ; ++j) {
+    printf("%x '%c'\n", ((int) str[j])&0xff, str[j]);
+  }
+  */
+  /* Now try decompressing. */
+  decomp = decompression_new();
+  if (buf_new(&buf2, &buf2len, &buf2_datalen))
+    test_fail();
+  buf_datalen = 0;
+  test_eq(i, write_to_buf(str, i, &buf, &buflen, &buf_datalen));
+  j = decompress_buf_to_buf(&buf, &buflen, &buf_datalen,
+                            &buf2, &buf2len, &buf2_datalen,
+                            decomp, 1);
+  /*XXXX check result *
+  
+  /* Now compress more, into less room. */
+  for (i = 0; i < 20; ++i) {
+    write_to_buf("Hello wxrlx.  ", 14, &buf, &buflen, &buf_datalen);
+  }
+  i = compress_from_buf(str, 256, &buf, &buflen, &buf_datalen, comp, 1);
+  
   test_eq(buf_datalen, 0);
+  
+  
 
+  compression_free(comp);
+  decompression_free(decomp);
+  
   
 
   buf_free(buf);
+  buf_free(buf2);
 }
 
 
 int main(int c, char**v) {
+  setup_directory();
+
   test_buffers();
 
   printf("\n");



More information about the tor-commits mailing list