When a function is given a pointer, it is tempting to do an assert on
the pointer to see if it is not NULL. But even if it is not NULL, it
could still be invalid or wrong. What we really want to know is that it
points to memory that we have access to.
That's not really good enough. What you really want to
know is that the pointer points "where it ought to," which
is much harder to characterize. Using assorted non-portable
tricks you might be able to learn whether a pointer points to
a valid memory location, whether it's correctly aligned for
its type, whether the memory is readable and/or writeable,
and maybe other things, too. If these tests fail you may
conclude that a pointer is incorrect, but if they all pass
you still don't know if the pointer is "right."
How about doing this:
void f(int* p)
{
assert(*((char*)p) == *((char*)p);
}
To see if pointer points to something that I have access to?
If `p' doesn't have a valid pointer value, the attempt
to use it causes undefined behavior. (Another respondent
said "accessing it will cause exception," but he is wrong.
"An exception" is among the things that might happen -- but
it might not, too.) In other words, your test is reliable
only if `p' is valid; if `p' is invalid there is no telling
what might happen.
Is there another way of do something like this?
I can think of nothing portable. And, as I've suggested
above, I think the various non-portable tests you might be
able to make are at best half-measures. (Confession: I have
not personally used things like Purify or valgrind and cannot
speak to their effectiveness -- but certainly a "spot-check"
test unsupported by considerable additional machinery is of
limited effectiveness.)
C programmers find themselves doing a lot of "manual"
memory management. This has its good side (flexibility) and
its bad (susceptibility to error). The kind of test you
propose can detect some kinds of errors, but my impression
is that they are the minority: it's much more common to use
a "stale" pointer by mistake or to make an off-by-one error
and point to the neighbor of the intended object than it is
to pull a completely garbage pointer right out of the blue.
It may sound like a counsel of perfection, but I think the
only way to survive is discipline: you need to construct little
"mini-proofs" of correctness as you go along. It's not infallible
(so few things are), but it seems more effective than trying
to apply an unreliable test after the fact.