free() question

B

bart.c

sandeep said:
It's a simple question..... can the free() function sometimes fail??

It can sometimes give undefined behaviour with invalid input (according to
the docs). But it doesn't return any status or set any error code.
 
K

Keith Thompson

sandeep said:
It's a simple question..... can the free() function sometimes fail??

Yes, but it can do so only in cases where the program's behavior
is undefined, which is why it has no mechanism for reporting failure.

For example:

int *p = malloc(sizeof *p); /* assume this succeded */
free(p); /* ok */
free(p); /* undefined behavior */

Another example:

int i;
int *p = &i;
free(p); /* undefined behavior */

I suppose it's debatable whether the undefined free() calls "fail";
it might be more accurate to say that the program failed by calling
free() with an invalid argument.
 
E

Eric Sosman

It's a simple question..... can the free() function sometimes fail??

It depends on what you mean by "fail."

If you mean "attempt an operation and report whether the operation
was or was not carried out," the answer is No. That is, free() cannot
"fail" the way malloc() can, or fopen(), or even the way strchr() can.

If you include "exhibit undefined behavior" in your definition of
"fail," then the answer is Yes. If you try to free() something not
obtained from malloc() et al., or free() something more than once, or
scribble on your memory, or invoke U.B. somewhere else in the program,
the entire program -- including free() -- exhibits U.B.
 
S

Seebs

It depends on what you mean by "fail."
If you mean "attempt an operation and report whether the operation
was or was not carried out," the answer is No. That is, free() cannot
"fail" the way malloc() can, or fopen(), or even the way strchr() can.
If you include "exhibit undefined behavior" in your definition of
"fail," then the answer is Yes. If you try to free() something not
obtained from malloc() et al., or free() something more than once, or
scribble on your memory, or invoke U.B. somewhere else in the program,
the entire program -- including free() -- exhibits U.B.

The most interesting question, I think, is:

Can there ever be a valid input to free(), such that the implementation
cannot actually free the memory? I can easily describe an implementation
in which this could be the case. You could construct an implementation in
which there was some sort of "free list" which could require allocation
in order to add items to that list, and if you had precisely filled available
memory, it could be that you couldn't free something because there'd be no
way to add it to the available-things list.

That would be an unusual implementation, at best, but I'm not sure that it
is prohibited.

Of course, there'd be no way to find OUT that this had happened.

-s
 
S

Seebs

Well, it would violate the requirement that "The free function causes
the space pointed to by ptr to be deallocated, that is, made available
for further allocation." (C99 7.20.3.2p2), so one could argue that
it would be as non-conforming as this implementation:
But yes, as long as there are no visible symptoms of the failure,
it can't be detected. (Failure of later allocations doesn't count,
since that can happen for any arbitrary reasons.)

Exactly. I'm not sure how you could tell. It seems like it'd be a pretty
bad implementation, but...

-s
 
K

Keith Thompson

Seebs said:
The most interesting question, I think, is:

Can there ever be a valid input to free(), such that the implementation
cannot actually free the memory? I can easily describe an implementation
in which this could be the case. You could construct an implementation in
which there was some sort of "free list" which could require allocation
in order to add items to that list, and if you had precisely filled available
memory, it could be that you couldn't free something because there'd be no
way to add it to the available-things list.

That would be an unusual implementation, at best, but I'm not sure that it
is prohibited.

Of course, there'd be no way to find OUT that this had happened.

Well, it would violate the requirement that "The free function causes
the space pointed to by ptr to be deallocated, that is, made available
for further allocation." (C99 7.20.3.2p2), so one could argue that
it would be as non-conforming as this implementation:

void free(void *ptr)
{
/* nyaah nyaah! */
}

But yes, as long as there are no visible symptoms of the failure,
it can't be detected. (Failure of later allocations doesn't count,
since that can happen for any arbitrary reasons.)

Practically speaking, of course, the implementation could use the
space being freed to hold any bookkeeping data for the free list,
but implementations aren't required to behave sanely.
 
S

spinoza1111

Yes, but it can do so only in cases where the program's behavior
is undefined, which is why it has no mechanism for reporting failure.

For example:

    int *p = malloc(sizeof *p); /* assume this succeded */
    free(p); /* ok */
    free(p); /* undefined behavior */

Another example:

    int i;
    int *p = &i;
    free(p); /* undefined behavior */

I suppose it's debatable whether the undefined free() calls "fail";
it might be more accurate to say that the program failed by calling
free() with an invalid argument.

--
Keith Thompson (The_Other_Keith) (e-mail address removed)  <http://www.ghoti.net/~kst>
Nokia
"We must do something.  This is something.  Therefore, we must do this."
    -- Antony Jay and Jonathan Lynn, "Yes Minister"

Good reply.
 
R

Richard Bos

bart.c said:
It can sometimes give undefined behaviour with invalid input (according to
the docs).

That's not a failure of free(), but a failure of the code that calls it.

Richard
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,756
Messages
2,569,535
Members
45,008
Latest member
obedient dusk

Latest Threads

Top