#include <unistd.h>
#include "tests/sys_mman.h"
#include <assert.h>
#include <stdlib.h>

#include "../memcheck.h"

#define SUPERBLOCK_SIZE    100000

//-------------------------------------------------------------------------
// Allocator
//-------------------------------------------------------------------------

void* get_superblock(void)
{
   void* p = mmap( 0, SUPERBLOCK_SIZE, PROT_READ|PROT_WRITE|PROT_EXEC,
                   MAP_PRIVATE|MAP_ANONYMOUS, -1, 0 );

   assert(p != ((void*)(-1)));

   // Mark it no access;  although it's addressible we don't want the 
   // program to be using it unless its handed out by custom_alloc()

   // with redzones, better not to have it
   VALGRIND_MAKE_MEM_NOACCESS(p, SUPERBLOCK_SIZE);

   return p;
}

// has a redzone
static void* custom_alloc(int size)
{
#define RZ  8
   static void* hp     = 0;    // current heap pointer
   static void* hp_lim = 0;    // maximum usable byte in current block
   int          size2  = size + RZ*2;
   void*        p;

   if (hp + size2 > hp_lim) {
      hp = get_superblock();
      hp_lim = hp + SUPERBLOCK_SIZE - 1;
   }  

   p = hp + RZ;
   hp += size2;

   VALGRIND_MALLOCLIKE_BLOCK( p, size, RZ, /*is_zeroed*/1 );
   return (void*)p;
}     

static void custom_free(void* p)
{
   // don't actually free any memory... but mark it as freed
   VALGRIND_FREELIKE_BLOCK( p, RZ );
}

static void checkredzone(void)
{
   /* check that accessing the redzone of a MALLOCLIKE block
      is detected  when the superblock was not marked as no access. */
   char superblock[1 + RZ + 20 + RZ + 1];
   char *p = 1 + RZ + superblock;
   assert(RZ > 0);

   // Indicate we have allocated p from our superblock:
   VALGRIND_MALLOCLIKE_BLOCK( p, 20, RZ, /*is_zeroed*/1 );
   p[0] = 0; 
   p[-1] = p[0]; // error expected
   p[-RZ] = p[0]; // error expected
   p[-RZ-1] = p[0]; // no error expected
   
   p[19] = 0; 
   p[19 + 1]  = p[0]; // error expected
   p[19 + RZ] = p[0]; // error expected
   p[19 + RZ + 1] = p[0]; // no error expected

   VALGRIND_FREELIKE_BLOCK( p, RZ );

   // Now, indicate we have re-allocated p from our superblock
   // but with only a size 10.
   VALGRIND_MALLOCLIKE_BLOCK( p, 10, RZ, /*is_zeroed*/1 );
   p[0] = 0; 
   p[-1] = p[0]; // error expected
   p[-RZ] = p[0]; // error expected
   p[-RZ-1] = p[0]; // no error expected
   
   p[9] = 0; 
   p[9 + 1]  = p[0]; // error expected
   p[9 + RZ] = p[0]; // error expected
   p[9 + RZ + 1] = p[0]; // no error expected

   VALGRIND_FREELIKE_BLOCK( p, RZ );

}



//-------------------------------------------------------------------------
// Rest
//-------------------------------------------------------------------------

void make_leak(void)
{
   int* array2 __attribute__((unused)) = custom_alloc(sizeof(int) * 10);
   array2 = 0;          // leak
   return;
}

int main(void)
{
   int *array, *array3;
   int x;

   array = custom_alloc(sizeof(int) * 10);
   array[8]  = 8;
   array[9]  = 8;
   array[10] = 10;      // invalid write (ok w/o MALLOCLIKE -- in superblock)

   VALGRIND_RESIZEINPLACE_BLOCK(array, sizeof(int) * 10, sizeof(int) * 5, RZ);
   array[4] = 7;
   array[5] = 9; // invalid write

   // Make the entire array defined again such that it can be verified whether
   // the red zone is marked properly when resizing in place.
   VALGRIND_MAKE_MEM_DEFINED(array, sizeof(int) * 10);

   VALGRIND_RESIZEINPLACE_BLOCK(array, sizeof(int) * 5, sizeof(int) * 7, RZ);
   if (array[5]) array[4]++; // uninitialized read of array[5]
   array[5]  = 11;
   array[6]  = 7;
   array[7] = 8; // invalid write

   // invalid realloc
   VALGRIND_RESIZEINPLACE_BLOCK(array+1, sizeof(int) * 7, sizeof(int) * 8, RZ);

   custom_free(array);  // ok

   custom_free((void*)0x1);  // invalid free

   array3 = malloc(sizeof(int) * 10);
   custom_free(array3); // mismatched free (ok without MALLOCLIKE)

   make_leak();
   x = array[0];        // use after free (ok without MALLOCLIKE/MAKE_MEM_NOACCESS)

   // Bug 137073: passing 0 to MALLOCLIKE_BLOCK was causing an assertion
   // failure.  Test for this (and likewise for FREELIKE_BLOCK).
   VALGRIND_MALLOCLIKE_BLOCK(0,0,0,0);
   VALGRIND_FREELIKE_BLOCK(0,0);

   checkredzone();

   return x;

   // leak from make_leak()
}

#undef RZ
