Beispiel #1
0
/**
 * Frees a block of memory previously allocated by dbus_malloc() or
 * dbus_malloc0(). If passed #NULL, does nothing.
 * 
 * @param memory block to be freed
 */
void
dbus_free (void  *memory)
{
#ifdef DBUS_BUILD_TESTS
  if (guards)
    {
      check_guards (memory, TRUE);
      if (memory)
        {
	  _dbus_atomic_dec (&n_blocks_outstanding);
          
	  _dbus_assert (n_blocks_outstanding.value >= 0);
          
          free (((unsigned char*)memory) - GUARD_START_OFFSET);
        }
      
      return;
    }
#endif
    
  if (memory) /* we guarantee it's safe to free (NULL) */
    {
#ifdef DBUS_BUILD_TESTS
      _dbus_atomic_dec (&n_blocks_outstanding);
      
      _dbus_assert (n_blocks_outstanding.value >= 0);
#endif

      free (memory);
    }
}
Beispiel #2
0
enum ach_status
ach_open( ach_channel_t *chan, const char *channel_name,
          ach_attr_t *attr ) {
    ach_header_t * shm;
    size_t len;
    int fd = -1;

    if( attr ) memcpy( &chan->attr, attr, sizeof(chan->attr) );
    else memset( &chan->attr, 0, sizeof(chan->attr) );

    if( attr && attr->map_anon ) {
        shm = attr->shm;
        len = sizeof(ach_header_t) + sizeof(ach_index_t)*shm->index_cnt + shm->data_size;
    }else {
        if( ! channel_name_ok( channel_name ) )
            return ACH_INVALID_NAME;
        /* open shm */
        if( ! channel_name_ok( channel_name ) ) return ACH_INVALID_NAME;
        if( (fd = fd_for_channel_name( channel_name, 0 )) < 0 ) {
            return check_errno();
        }
        if( (shm = (ach_header_t*) mmap (NULL, sizeof(ach_header_t),
                                         PROT_READ|PROT_WRITE, MAP_SHARED, fd, 0ul) )
            == MAP_FAILED )
            return ACH_FAILED_SYSCALL;
        if( ACH_SHM_MAGIC_NUM != shm->magic )
            return ACH_BAD_SHM_FILE;

        /* calculate mmaping size */
        len = sizeof(ach_header_t) + sizeof(ach_index_t)*shm->index_cnt + shm->data_size;

        /* remap */
        if( -1 ==  munmap( shm, sizeof(ach_header_t) ) )
            return check_errno();

        if( (shm = (ach_header_t*) mmap( NULL, len, PROT_READ|PROT_WRITE,
                                         MAP_SHARED, fd, 0ul) )
            == MAP_FAILED )
            return check_errno();
    }

    /* Check guard bytes */
    {
        enum ach_status r = check_guards(shm);
        if( ACH_OK != r ) return r;
    }

    /* initialize struct */
    chan->fd = fd;
    chan->len = len;
    chan->shm = shm;
    chan->seq_num = 0;
    chan->next_index = 1;
    chan->cancel = 0;

    return ACH_OK;
}
/* returns 1 if valid, *safe == 1 if safe to dump stack */
static inline int check_allocation_locked(struct hdr *hdr, int *safe)
{
    int valid = 1;
    *safe = 1;

    if (hdr->tag != ALLOCATION_TAG && hdr->tag != BACKLOG_TAG) {
        log_message("+++ ALLOCATION %p HAS INVALID TAG %08x (NOT DUMPING STACKTRACE)\n",
                   user(hdr), hdr->tag);
	/* Allocation header is probably corrupt, do not dequeue or dump stack
         * trace.
         */
        *safe = 0;
        return 0;
    }

    if (hdr->tag == BACKLOG_TAG && was_used_after_free(hdr)) {
        log_message("+++ ALLOCATION %p SIZE %d WAS USED AFTER BEING FREED\n",
                   user(hdr), hdr->size);
        valid = 0;
	/* check the guards to see if it's safe to dump a stack trace */
        (void)check_guards(hdr, safe);
    }
    else
        valid = check_guards(hdr, safe);

    if (!valid && *safe) {
        log_message("+++ ALLOCATION %p SIZE %d ALLOCATED HERE:\n",
                        user(hdr), hdr->size);
        print_backtrace(hdr->bt, hdr->bt_depth);
        if (hdr->tag == BACKLOG_TAG) {
            log_message("+++ ALLOCATION %p SIZE %d FREED HERE:\n",
                       user(hdr), hdr->size);
            print_backtrace(hdr->freed_bt, hdr->freed_bt_depth);
        }
    }

    return valid;
}
Beispiel #4
0
/**
 * Frees a block of memory previously allocated by dbus_malloc() or
 * dbus_malloc0(). If passed #NULL, does nothing.
 * 
 * @param memory block to be freed
 */
void
dbus_free (void  *memory)
{
#ifdef DBUS_ENABLE_EMBEDDED_TESTS
  if (guards)
    {
      check_guards (memory, TRUE);
      if (memory)
        {
#ifdef DBUS_DISABLE_ASSERT
          _dbus_atomic_dec (&n_blocks_outstanding);
#else
          dbus_int32_t old_value;

          old_value = _dbus_atomic_dec (&n_blocks_outstanding);
          _dbus_assert (old_value >= 1);
#endif

          free (((unsigned char*)memory) - GUARD_START_OFFSET);
          dbus_track_free (memory);
        }
      
      return;
    }
#endif
    
  if (memory) /* we guarantee it's safe to free (NULL) */
    {
#ifdef DBUS_ENABLE_EMBEDDED_TESTS
#ifdef DBUS_DISABLE_ASSERT
      _dbus_atomic_dec (&n_blocks_outstanding);
#else
      dbus_int32_t old_value;

      old_value = _dbus_atomic_dec (&n_blocks_outstanding);
      _dbus_assert (old_value >= 1);
#endif
#endif

      free (memory);
      dbus_track_free (memory);
    }
}
Beispiel #5
0
static void*
set_guards (void       *real_block,
            size_t      requested_bytes,
            BlockSource source)
{
  unsigned char *block = real_block;
  unsigned int i;
  
  if (block == NULL)
    return NULL;

  _dbus_assert (GUARD_START_OFFSET + GUARD_END_PAD == GUARD_EXTRA_SIZE);
  
  *((dbus_uint32_t*)block) = requested_bytes;
  *((dbus_uint32_t*)(block + 4)) = source;

  i = GUARD_INFO_SIZE;
  while (i < GUARD_START_OFFSET)
    {
      (*(dbus_uint32_t*) &block[i]) = GUARD_VALUE;
      
      i += 4;
    }

  i = GUARD_START_OFFSET + requested_bytes;
  while (i < (GUARD_START_OFFSET + requested_bytes + GUARD_END_PAD))
    {
      (*(dbus_uint32_t*) &block[i]) = GUARD_VALUE;
      
      i += 4;
    }
  
  check_guards (block + GUARD_START_OFFSET, FALSE);
  
  return block + GUARD_START_OFFSET;
}
Beispiel #6
0
/**
 * Resizes a block of memory previously allocated by dbus_malloc() or
 * dbus_malloc0(). Guaranteed to free the memory and return #NULL if bytes
 * is zero on all platforms. Returns #NULL if the resize fails.
 * If the resize fails, the memory is not freed.
 *
 * @param memory block to be resized
 * @param bytes new size of the memory block
 * @return allocated memory, or #NULL if the resize fails.
 */
void*
dbus_realloc (void  *memory,
              size_t bytes)
{
#ifdef DBUS_BUILD_TESTS
  _dbus_initialize_malloc_debug ();
  
  if (_dbus_decrement_fail_alloc_counter ())
    {
      _dbus_verbose (" FAILING realloc of %ld bytes\n", (long) bytes);
      
      return NULL;
    }
#endif
  
  if (bytes == 0) /* guarantee this is safe */
    {
      dbus_free (memory);
      return NULL;
    }
#ifdef DBUS_BUILD_TESTS
  else if (fail_size != 0 && bytes > fail_size)
    return NULL;
  else if (guards)
    {
      if (memory)
        {
          size_t old_bytes;
          void *block;
          
          check_guards (memory, FALSE);
          
          block = realloc (((unsigned char*)memory) - GUARD_START_OFFSET,
                           bytes + GUARD_EXTRA_SIZE);

	  old_bytes = *(dbus_uint32_t*)block;
          if (block && bytes >= old_bytes)
            /* old guards shouldn't have moved */
            check_guards (((unsigned char*)block) + GUARD_START_OFFSET, FALSE);
          
          return set_guards (block, bytes, SOURCE_REALLOC);
        }
      else
        {
          void *block;
          
          block = malloc (bytes + GUARD_EXTRA_SIZE);

          if (block)
	    _dbus_atomic_inc (&n_blocks_outstanding);
          
          return set_guards (block, bytes, SOURCE_REALLOC_NULL);   
        }
    }
#endif
  else
    {
      void *mem;
      mem = realloc (memory, bytes);
#ifdef DBUS_BUILD_TESTS
      if (memory == NULL && mem != NULL)
	    _dbus_atomic_inc (&n_blocks_outstanding);
#endif
      return mem;
    }
}
Beispiel #7
0
/**
 * Resizes a block of memory previously allocated by dbus_malloc() or
 * dbus_malloc0(). Guaranteed to free the memory and return #NULL if bytes
 * is zero on all platforms. Returns #NULL if the resize fails.
 * If the resize fails, the memory is not freed.
 *
 * @param memory block to be resized
 * @param bytes new size of the memory block
 * @return allocated memory, or #NULL if the resize fails.
 */
void*
_dbus_realloc (void  *memory,
               size_t bytes,
               const char *file,
               int line)
{
#ifdef DBUS_ENABLE_EMBEDDED_TESTS
  _dbus_initialize_malloc_debug ();
  
  if (_dbus_decrement_fail_alloc_counter ())
    {
      _dbus_verbose (" FAILING realloc of %ld bytes\n", (long) bytes);
      
      return NULL;
    }
#endif
  
  if (bytes == 0) /* guarantee this is safe */
    {
      dbus_free (memory);
      return NULL;
    }
#ifdef DBUS_ENABLE_EMBEDDED_TESTS
  else if (fail_size != 0 && bytes > fail_size)
    return NULL;
  else if (guards)
    {
      if (memory)
        {
          size_t old_bytes;
          void *block;
          
          check_guards (memory, FALSE);
          
          block = realloc (((unsigned char*)memory) - GUARD_START_OFFSET,
                           bytes + GUARD_EXTRA_SIZE);

          if (block == NULL)
            {
              if (malloc_cannot_fail)
                {
                  _dbus_warn ("out of memory: realloc (%p, %ld + %ld)\n",
                      memory, (long) bytes, (long) GUARD_EXTRA_SIZE);
                  _dbus_abort ();
                }

              return NULL;
            }
          dbus_track_free (((unsigned char*)memory) - GUARD_START_OFFSET);
          dbus_track_realloc (((unsigned char*)memory) - GUARD_START_OFFSET, bytes + GUARD_EXTRA_SIZE, file, line);

          old_bytes = *(dbus_uint32_t*)block;
          if (bytes >= old_bytes)
            /* old guards shouldn't have moved */
            check_guards (((unsigned char*)block) + GUARD_START_OFFSET, FALSE);
          
          return set_guards (block, bytes, SOURCE_REALLOC);
        }
      else
        {
          void *block;
          
          block = malloc (bytes + GUARD_EXTRA_SIZE);

          if (block)
            {
              _dbus_atomic_inc (&n_blocks_outstanding);
              dbus_track_malloc(block, bytes + GUARD_EXTRA_SIZE, file, line);
            }
          else if (malloc_cannot_fail)
            {
              _dbus_warn ("out of memory: malloc (%ld + %ld)\n",
                  (long) bytes, (long) GUARD_EXTRA_SIZE);
              _dbus_abort ();
            }

          return set_guards (block, bytes, SOURCE_REALLOC_NULL);   
        }
    }
#endif
  else
    {
      void *mem;
      mem = realloc (memory, bytes);

#ifdef DBUS_ENABLE_EMBEDDED_TESTS
      if (mem == NULL && malloc_cannot_fail)
        {
          _dbus_warn ("out of memory: malloc (%ld)\n", (long) bytes);
          _dbus_abort ();
        }

      if (memory == NULL && mem != NULL)
	    _dbus_atomic_inc (&n_blocks_outstanding);
#endif
      dbus_track_free (memory);
      dbus_track_realloc (mem, bytes, file, line);
      return mem;
    }
}