I have a pointer that is pointing to the start of an array, but I need to check that it is unallocated. I thought of dereferencing the pointer and checking if NULL but that leads to a type error. Can anyone see what I'm doing wrong?

-1? The question shows a lack of understanding, but that's the whole point of asking questions. The code is formatted and the question is clear. If you're going to downvote someone, at least say why.
–
nmichaelsNov 8 '10 at 16:18

6 Answers
6

*array == NULL is wrong. You are dereferencing the pointer first (which could lead to a segfault if the pointer really is null) and then comparing its int value to a pointer value. Moreover, your compiler will perfectly accept that erroneous expression if NULL is defined as just 0 and not (void *) 0.

You should be checking array == NULL to see if the passed pointer refers to anything, and then dereference it only in case it's not NULL.

Be aware, however, that dereferencing a non-null pointer isn't guaranteed to be a safe operation either. If the pointer contains a garbage value because it was allocated on the stack and not initialized, or if it refers to a deallocated region of memory, nasty bugs can happen.

Thanks, this is what I had originally thought, but doesn't this just show me that I have a null pointer, rather than a pointer pointing to an empty array?
–
AlexNov 8 '10 at 17:28

2

There is no such thing as an empty array in C - when passing arrays to functions you should always pass a number that indicates the length. If that number is zero, you could treat the array as empty. There is the notion, however, of an empty string, because by convention strings are delimited with a zero character at the end. If the first character is a zero character, that is considered an empty string.
–
Blagovest BuyuklievNov 8 '10 at 17:49

Okay, thanks BB, so maybe I should test for a zero char? I'm rewriting malloc(), "This function will return 1 if array has the form of a correctly initialised structure with no currently allocated blocks, otherwise it will return 0."
–
AlexNov 8 '10 at 20:45

The alternative to keeping the length of an array separately is adopting the string convention, but that is not always applicable because the "magic" terminating value may as well be a valid, meaningful value, and that implies always allocating at least one element.
–
Blagovest BuyuklievNov 8 '10 at 21:11

You want if (array == NULL) -- but unless you first initialize array to NULL, it won't do any good either. I think you'd be better off backing up and telling us a bit more about what you're trying to accomplish, and trying to get help trying to accomplish your overall goal.

You can't reliably check if some memory location is allocated. *array is not a valid code, because it's the same as array[0], but array[0] is not allocated. Non-allocated memory location can contain any value.

The only option is to ensure that you get the information whether the array is allocated alongside with your array. A popular option is representing unallocated array as NULL, but you may choose other option as well.

By the way, there is a difference between an empty array (that is, array of size 0), and array which is not allocated at all. The first option occurs when you use malloc(0), the second when your pointer is not initialized at all. For malloc(0) it's allowed to return NULL, but it's allowed to return a non-NULL pointer (which you however can't dereference) as well. Both ways are valid according to the standard.

The immediate problem with your code is that you dereferencing array before comparing it to NULL. The type of the expression*array is int, not int *. Leave off the dereference operator and the types will match:

if (array == NULL) {...}

Note that an uninitialized pointer is only guaranteed to contain NULL if it was declared with static extent (i.e. it was either declared at file scope or with the static keyword in front of it). Similarly, calling free on a pointer won't set that pointer value to NULL; it will contain the same pointer value as before, but it will now be invalid.