[comp.lang.c] Question about malloc

rtidd@ccels3.mitre.org (Randy Tidd) (08/25/90)

I ran into what I think is an interesting question, I hope someone can
help me out. I hope this hasn't been beaten to death around here, but
I haven't seen it recently.

Say I have a routine that allocates big block of memory and returns a
pointer to it, something like:

char *get_chars()
{
  char *big_block;
  int i;

  big_block = malloc(10001);
  for(i=0; i<10000; i++)
    big_block[i] = getchar();
  big_block[i] = '\0';         /* NULL-terminate the array */
  return(big_block);
]

And the calling function does something like:

main()
{
  char foo[10001];

  strcpy(foo,get_chars());
  printf("%s\n",foo);    
}

What happens to the space that was malloc'ed? It is never freed by me;
will the compiler figure this out and arrange for it to be freed?  Is
the resolution method standard over compilers?

While this is an extreme case, I ran into something more moderate and
am curious, for performance reasons, of the turnout.

Any help is appreciated. Please e-mail me if you feel the rest of The
Net doesn't want to hear about it.
Randy Tidd				GOOD
rtidd@mwunix.mitre.org			FAST
#define DISCLAIM TRUE			CHEAP
						-pick any two

roger@everexn.uucp (Roger House) (08/28/90)

In <118073@linus.mitre.org> rtidd@ccels3.mitre.org (Randy Tidd) writes:

>What happens to the space that was malloc'ed? It is never freed by me;
>will the compiler figure this out and arrange for it to be freed?  Is
>the resolution method standard over compilers?

The compiler will NOT figure out that something can be freed and then free
it.  Most likely the compiler has no idea that malloc is allocating memory.l
The compiler simply compiles the code needed to pass the parameters and
call the function.  It is up to the programmer to take care of freeing mem-
ory allocated by the programmer.

						Roger House

browns@iccgcc.decnet.ab.com (Stan Brown, Oak Road Systems) (08/31/90)

In article <1990Aug27.184058.1936@everexn.uucp>, roger@everexn.uucp (Roger House) writes:
> In <118073@linus.mitre.org> rtidd@ccels3.mitre.org (Randy Tidd) writes:
> 
>>What happens to the space that was malloc'ed? It is never freed by me;
>>will the compiler figure this out and arrange for it to be freed?  Is
>>the resolution method standard over compilers?
> 
> The compiler will NOT figure out that something can be freed and then free
> it.  Most likely the compiler has no idea that malloc is allocating memory.l
> The compiler simply compiles the code needed to pass the parameters and
> call the function.  It is up to the programmer to take care of freeing mem-
> ory allocated by the programmer.

Well, yes and no....

The idea of "allocating" memory is operating system dependent.  For
example, in MS-DOS your .EXE program has all of available memory unless it
gives some of it up.  When you execute malloc( ) it takes from this space
and puts an appropriate header on the block.  So on a DOS machine, when
your .EXE stops running, even if you malloc'd a couple of hundred K, you
should see exactly the same amount of available memory as before you ran
the program.

Multi-user systems typically work the same way.  For instance, on VAX/VMS
the system ssomehow makes sure that your program no longer has memory when
it exits.  (If the system _didn't_ do that, a program that crashed between
the malloc( ) and the free( ) would eat up some of main memory every time
it was run.)

I don't want to encourage sloppy programming :-), so I'll say you should
always free( ) any memory you malloc( ).  But in the interests of accuracy,
I'll have to add that on many (most?) systems there's probably no penalty
if you fail to do so.  Of course, if your program iss doing a great many
malloc( )s it may run out of memory and _have_ to do some free( )s to make
space available for more malloc( )s.

Stan Brown, Oak Road Systems, Cleveland, Ohio, U.S.A.         (216) 371-0043

Oak Road Systems stands behind my opinions 100%  However, nobody stands
behind the opinions of Oak Road Systems but me.  Does this tell you
something?

rssutor@broccoli.princeton.edu (Robert S. Sutor) (08/31/90)

Another good argument to free what you have malloc'ed, as has been stated
before (here?), is that someone might decode to use your program or functions
as subroutines of another program.  In that case it is definitely not a good
idea to leave dead data tying up memory.

del@thrush.mlb.semi.harris.com (Don Lewis) (08/31/90)

In article <2223@idunno.Princeton.EDU> rssutor@broccoli.Princeton.EDU (Robert S. Sutor) writes:
>
>Another good argument to free what you have malloc'ed, as has been stated
>before (here?), is that someone might decode to use your program or functions
>as subroutines of another program.  In that case it is definitely not a good
>idea to leave dead data tying up memory.

#define asbestos_suit_on

I'm going to argue against doing this blindly.  There is one particular
application that I have used and which will remain nameless.  This
application reads a bunch of data files on startup and builds a large
data structure in memory.  The data structure is significantly larger
than than available physical memory, but since this program is running
on a machine with virtual memory (sound of page faults happening...),
here is no problem, right?  After it has finished reading the data, the
program walks around the data structure (sound of more page faults)
and writes its output (except the last stdio buffer full) to a file.
Then the program goes into serious page fault mode for about 45
minutes.  I don't know what it does during this time, but I'd be willing
to bet that it is walking the data structure, freeing all the bits and
pieces of memory it has malloc'ed along the way.  Finally it calls
exit() which fflush's the rest of the output data.

It sure would be considerate if this program just called exit()
instead of wasting my time and a lot of cpu cycles doing something
totally useless.  I'd even be happy with a strategically placed
fflush() so that I could send the process a well deserved "kill -9".

#define asbestos_suit_off

Now that feels much better.
--
Don "Truck" Lewis                      Harris Semiconductor
Internet:  del@mlb.semi.harris.com     PO Box 883   MS 62A-028
Phone:     (407) 729-5205              Melbourne, FL  32901

nathan@elberton.inmos.co.uk (Nathan Sidwell) (09/04/90)

In article <1990Aug31.005355.17898@mlb.semi.harris.com> del@thrush.mlb.semi.harris.com (Don Lewis) writes:
>Then the program goes into serious page fault mode for about 45
>minutes.  I don't know what it does during this time, but I'd be willing
>to bet that it is walking the data structure, freeing all the bits and
>pieces of memory it has malloc'ed along the way.  Finally it calls
>exit() which fflush's the rest of the output data.
>
>It sure would be considerate if this program just called exit()
>instead of wasting my time and a lot of cpu cycles doing something
>totally useless.  I'd even be happy with a strategically placed
>fflush() so that I could send the process a well deserved "kill -9".
>

While I agree that it would be more considerate of the program to just
exit (in this case), IMHO I think it a good idea to free malloc'd space
_during_ a program run (especially in an interactive program).
Also, during debugging, I explicitly free
blocks, so I can see if any are left that I've forgotten about.

One problem I have found is that the implementation of malloc I had
(this is MS C 5.1) was seriously flawed for a VM machine (OS/2). The problem
only came to light when the software was being used by users. After
several images had been read in, the machine started thrashing continuously.
I had explicitly prevented the program from slurping in more than X bytes of
total image, and figured that if it segment faulted it would do so only when
accessing the swapped out image etc. (OS/2 swaps whole segments, not pages.)

It turned out that [because of the way I had built the windowing system] every
mouse event causing a window notification, caused memory to be malloc'd and
free'd. Malloc would run through its linked list of empty blocks to find
one which fitted -- thereby touching every segment allocated. The clock
display was updated every two seconds, thereby guaranteeing a thrash
on this timescale.

I supplied my own malloc which kept a list of segments in a table, with enough
information in it to work out whether it was worth while examining a segment
for a possible empty block. This gave the additional win that I could remove
the debug code which checked that I was freeing blocks I'd actually
malloc'd :-)

I don't know if this is just a one off, but I would suspect other
implementations to suffer the same.

Nathan Sidwell, INMOS Ltd, UK         JANET:    nathan@uk.co.inmos
Generic disclaimer applies            UUCP:     ukc!inmos!nathan
My indicision is final (I think)      INTERNET: nathan@inmos.com