delorie.com/archives/browse.cgi   search  
Mail Archives: djgpp/1994/01/04/18:11:30

To: ryoung AT clark DOT dgim DOT doc DOT ca (Richard Young)
Cc: djgpp AT sun DOT soe DOT clarkson DOT edu
Subject: Re: Complex new/delete bug
Organization: Code Generation Technology, San Francisco, CA
Date: Tue, 04 Jan 94 14:55:12 -0800
From: "Thomas J. Merritt" <tjm AT netcom DOT com>

|<><><><><> Original message from ryoung AT clark DOT dgim DOT doc DOT ca  <><><><><>
|I have found a bug when creating complex arrays with new and then deleting
|them.  The deletion of the complex array does not seem to free up the memory
|that was allocated and a succession of new/delete will eventually result in
|an insufficient memory error.

The bug is in your code.

|I have been able to circumvent the bug by refraining from using new complex[n].
|In place of 
|		complex * x = new complex[n];
|I  use
|		complex * x = (complex *)malloc(n*sizeof(complex));

This is just masking the bug.

|The following test program, which I named testmemf.cc, illustrates the problem.
|  I have listed the various tests that I ran below:  
|>  testmemf 1    using new complex[n], will eat up memory and die, note new'ed 
|                 ptr increasing

		Yup.

|>  testmemf 2    no problem with double arrays, ptr not increasing

		Not suprising.

|>  testmemf 3    no problem with single complex objects, ptr not increasing

		Yup.

|>  testmemf 4    no problem with malloc(n*sizeof(complex)) instead of new
|                 complex(n)

		Not suprising.

|>  testmemf 5    seems to show that the amount of memory allocated with new is 
|                 OK, that is, the delta between ptrs is n*sizeof(complex) bytes

		Strange.  There should be a little bit of overhead for malloc.

|>  testmemf 6    same delta as test 5 but I found it odd when the address of
|		  the 1st ptr here was consistently different than in test 5

		Not suprising.

|Although I am avoiding the problem for now I would appreciate if someone could 
|locate and
|fix the bug.  
|
|Thanks and Merry Christmas!!!
|
|Richard Young, DSP engineer
|Communications Research Centre
|3701 Carling Ave.,
|Ottawa, Ontario
|Canada 
|K2H 8S2
|(tel) (613)998-2235
|(fax) (613)990-6339
|(e-mail) richard DOT young AT crc DOT doc DOT ca
|
|//--------------------   testmemf.cc ------------------------------------------
|--------------
|
|#include <complex.h>
|#include <stdio.h>
|#include <stdlib.h>
|
|int main (int argc, char *argv[])
|{
|   if (argv[1][0] == '1')     	// successive new/delete with complex arrays
|   {
|      for (;1;)   
|      {
|         complex * x = new complex[1000];
|         printf("%c x=%p\n",argv[1][0],x);
|         delete x;

	Need to do a 'delete[] x;'

|      }
|   }
|   else if (argv[1][0] == '2')  // successive new/delete with double arrays
|   {
|      for (;1;)
|      {
|         double * x = new double[1000];
|         printf("%c x=%p\n",argv[1][0],x);
|         delete x;

	Still need to do a 'delete[] x;'

|      }
|   }
|   else if (argv[1][0] == '3')	// successive new/delete with single complex ob
|jects
|   {
|      for (;1;)
|      {
|         complex * x = new complex;
|         printf("%c x=%p\n",argv[1][0],x);
|         delete x;

	This is OK.

|      }
|   }
|   if (argv[1][0] == '4')	// successive new/delete with malloc'ed complex
| array store
|   {
|      for (;1;)
|      {
|         complex * x = (complex *)malloc(sizeof(complex[1000]));
|         printf("%c x=%p\n",argv[1][0],x);
|         delete x;

	This is undefined behaviour.  You can't mix malloc/free with new/delete.

|      }
|   }
|   if (argv[1][0] == '5')	// to check amount of memory allocated to each 
|new array
|   {				//   using new
|      complex * x = new complex[1000];
|      complex * y = new complex[1000];
|      complex * z = new complex[1000];
|      printf("%c x=%p y=%p z=%p\n",argv[1][0],x,y,z);
|   }
|   if (argv[1][0] == '6')	// to check amount of memory allocated to each 
|new array
|   {				//   using malloc
|      complex * x = (complex *)malloc(sizeof(complex[1000]));
|      complex * y = (complex *)malloc(sizeof(complex[1000]));
|      complex * z = (complex *)malloc(sizeof(complex[1000]));
|      printf("%c x=%p y=%p z=%p\n",argv[1][0],x,y,z);

	This may take slightly less memory since C++ arrays are prefixed with
	a length count.

|   }
|   return 0;
|}
|
|//--------------------   end of testmemf.cc -----------------------------------
|---------------

TJ Merritt
tjm AT netcom DOT com

- Raw text -


  webmaster     delorie software   privacy  
  Copyright © 2019   by DJ Delorie     Updated Jul 2019