]> mj.ucw.cz Git - libucw.git/blobdiff - lib/lizard-safe.c
CONFIG_INCREMENTAL doesn't belong to the free version
[libucw.git] / lib / lizard-safe.c
index dcc01d11f59a6a69528eac1fd75f86f867230d35..4ca3d9befec41ed9ef001ca16cbc3d28aeac56e4 100644 (file)
@@ -10,7 +10,6 @@
 #include "lib/lib.h"
 #include "lib/lizard.h"
 
-#include <stdlib.h>
 #include <sys/mman.h>
 #include <sys/user.h>
 #include <fcntl.h>
@@ -21,7 +20,7 @@
 struct lizard_buffer {
   uns len;
   void *ptr;
-  struct sigaction *old_sigsegv_handler;
+  struct sigaction old_sigsegv_handler;
 };
 
 struct lizard_buffer *
@@ -30,8 +29,7 @@ lizard_alloc(void)
   struct lizard_buffer *buf = xmalloc(sizeof(struct lizard_buffer));
   buf->len = 0;
   buf->ptr = NULL;
-  buf->old_sigsegv_handler = xmalloc(sizeof(struct sigaction));
-  handle_signal(SIGSEGV, buf->old_sigsegv_handler);
+  handle_signal(SIGSEGV, &buf->old_sigsegv_handler);
   return buf;
 }
 
@@ -40,8 +38,7 @@ lizard_free(struct lizard_buffer *buf)
 {
   if (buf->ptr)
     munmap(buf->ptr, buf->len + PAGE_SIZE);
-  unhandle_signal(SIGSEGV, buf->old_sigsegv_handler);
-  xfree(buf->old_sigsegv_handler);
+  unhandle_signal(SIGSEGV, &buf->old_sigsegv_handler);
   xfree(buf);
 }
 
@@ -73,8 +70,8 @@ sigsegv_handler(int signal UNUSED)
   return 1;
 }
 
-int
-lizard_decompress_safe(byte *in, struct lizard_buffer *buf, uns expected_length, byte **ptr)
+byte *
+lizard_decompress_safe(byte *in, struct lizard_buffer *buf, uns expected_length)
   /* Decompresses in into buf, sets *ptr to the data, and returns the
    * uncompressed length.  If an error has occured, -1 is returned and errno is
    * set.  The buffer buf is automatically reallocated.  SIGSEGV is caught in
@@ -86,18 +83,22 @@ lizard_decompress_safe(byte *in, struct lizard_buffer *buf, uns expected_length,
     lizard_realloc(buf, lock_offset);
   volatile sh_sighandler_t old_handler = signal_handler[SIGSEGV];
   signal_handler[SIGSEGV] = sigsegv_handler;
-  int len;
+  byte *ptr;
   if (!setjmp(safe_decompress_jump))
   {
-    *ptr = buf->ptr + buf->len - lock_offset;
-    len = lizard_decompress(in, *ptr);
+    ptr = buf->ptr + buf->len - lock_offset;
+    int len = lizard_decompress(in, ptr);
+    if (len != (int) expected_length)
+    {
+      ptr = NULL;
+      errno = EINVAL;
+    }
   }
   else
   {
-    *ptr = NULL;
-    len = -1;
+    ptr = NULL;
     errno = EFAULT;
   }
   signal_handler[SIGSEGV] = old_handler;
-  return len;
+  return ptr;
 }