By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
446,191 Members | 781 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 446,191 IT Pros & Developers. It's quick & easy.

Debugging standard C library routines

P: n/a
I am working on MontaVista Linux on a PPC board.
The compiler I am using is a gnu cross compiler cross compiler
(ppc-82xx-gcc)

The application/software that is being run, is messing up the memory
due to which a subsequent malloc fails.

When the application core is dumped I do not get any backtrace in the
code (although the application is compiled with debug symbols, with -g
option). The only thing I get is the address of the function (and not
the name) where the crash is happening.

Using prints in the code I found that application crashes while calling
malloc. I am linking the standard C library as .so, and thats probably
why there is not backtrace conatining the functions of my application.

There is not enough memory on the board to run gdb. Also due to the
complexity of the scenarios it is not always possible to run gdbserver.
It there a possible way to:
1. Link a debuggable version of stdlib which would put more information
in the core, when it is dumped.
2. Can I enable some asserts or extra information in stdlib which would
tell me if memry is being messed up.
3. Is there a way by which I can map an address to a function of .so
loaded in the memory. Or even if i know that the address belongs t a
perticaular .so

Thanks in advance.

Sep 30 '06 #1
Share this Question
Share on Google+
83 Replies


P: n/a
ac*********@gmail.com wrote:
I am working on MontaVista Linux on a PPC board.
The compiler I am using is a gnu cross compiler cross compiler
(ppc-82xx-gcc)

The application/software that is being run, is messing up the memory
due to which a subsequent malloc fails.

When the application core is dumped I do not get any backtrace in the
code (although the application is compiled with debug symbols, with -g
option). The only thing I get is the address of the function (and not
the name) where the crash is happening.

Using prints in the code I found that application crashes while calling
malloc. I am linking the standard C library as .so, and thats probably
why there is not backtrace conatining the functions of my application.

There is not enough memory on the board to run gdb. Also due to the
complexity of the scenarios it is not always possible to run gdbserver.
It there a possible way to:
1. Link a debuggable version of stdlib which would put more information
in the core, when it is dumped.
2. Can I enable some asserts or extra information in stdlib which would
tell me if memry is being messed up.
3. Is there a way by which I can map an address to a function of .so
loaded in the memory. Or even if i know that the address belongs t a
perticaular .so

Thanks in advance.
You have a hard problem there.

To (1) and (2)

First thing, you do not need a full debug version of the c library but
just of malloc/free. I suppose you do not suspect asin() as beeing the
source of your problems. One such a debug library is
http://www.hexco.de/rmdebug/

To (3)

If I do an
objdump -T /lib/libc-2.2.4.so

I obtain a list of entry points with their addresses. If you get to know
at which address the .so is loaded you are all set.

Sep 30 '06 #2

P: n/a
ac*********@gmail.com said:
The application/software that is being run, is messing up the memory
due to which a subsequent malloc fails.
Initialise every pointer. Check every malloc/calloc/realloc to ensure it
succeeded before you rely on its return value. Check that every array
access is within bounds (0 to n - 1, for an array of n elements). Set
indeterminate ('dangling') pointers to NULL.

Following these simple steps will get rid of 99.90072% of all known
memory-related crashes.

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 1 '06 #3

P: n/a
Richard Heathfield posted:
ac*********@gmail.com said:
>The application/software that is being run, is messing up the memory
due to which a subsequent malloc fails.

Initialise every pointer.

I wouldn't go so far as to advise to initialise _every_ pointer.

#define POVER(arr) ((arr) + sizeof(arr)/sizeof*(arr))

int *p;

for(p=array1;POVER(array1)!=p;++p) /* Something */ ;

for(p=array2;POVER(array2)!=p;++p) /* Something */ ;

Check every malloc/calloc/realloc to ensure it succeeded before you rely
on its return value.

If malloc'ing less than a kilobyte, I wouldn't bother.

Check that every array access is within bounds (0 to n - 1, for an array
of n elements).

One should _always_ watch out for such things when looking back over one's
code.

Set indeterminate ('dangling') pointers to NULL.

In Debug Mode, maybe. It wastes valuable nanoseconds (if not microseconds)
in Release Mode. Maybe something like the following would be a compromise:

#ifdef NDEBUG
#define DMODE(statement)
#else
#define DMODE(statement) statement
#endif

int main()
{
int *p;

...

free(p); DMODE(p=0);
}

--

Frederick Gotham
Oct 1 '06 #4

P: n/a
Frederick Gotham said:
Richard Heathfield posted:
>ac*********@gmail.com said:
>>The application/software that is being run, is messing up the memory
due to which a subsequent malloc fails.

Initialise every pointer.


I wouldn't go so far as to advise to initialise _every_ pointer.
At least until he is ready to apply for re-admission to civilisation, Mr
Gotham's opinion on style is of no consequence to me...
>Check every malloc/calloc/realloc to ensure it succeeded before you rely
on its return value.


If malloc'ing less than a kilobyte, I wouldn't bother.
....but when he offers dangerously stupid advice such as that, it's a good
idea for people to point it out. Such stupid advice leads, when followed,
to buggy, unstable software.
>Set indeterminate ('dangling') pointers to NULL.

In Debug Mode, maybe. It wastes valuable nanoseconds (if not microseconds)
in Release Mode.
Yet more stupid advice. Is there no beginning to this man's talent?
--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 1 '06 #5

P: n/a
Frederick Gotham wrote:
Richard Heathfield posted:
>>
Check every malloc/calloc/realloc to ensure it succeeded before you rely
on its return value.

If malloc'ing less than a kilobyte, I wouldn't bother.
Your camel's back can carry an infinite number of straws?

#include <stdlib.h>
#include <string.h>
int main(void) {
while (1) {
(char*)malloc(1) = 'X'; /* don't bother checking */
}
}

--
Eric Sosman
es*****@acm-dot-org.invalid
Oct 1 '06 #6

P: n/a
Eric Sosman said:
Frederick Gotham wrote:
>Richard Heathfield posted:
>>>
Check every malloc/calloc/realloc to ensure it succeeded before you rely
on its return value.

If malloc'ing less than a kilobyte, I wouldn't bother.

Your camel's back can carry an infinite number of straws?

#include <stdlib.h>
#include <string.h>
int main(void) {
while (1) {
(char*)malloc(1) = 'X'; /* don't bother checking */
You mean *(char *)malloc(1) = 'X', of course, but your point is nevertheless
correct.

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 1 '06 #7

P: n/a
Frederick Gotham wrote:
Richard Heathfield posted:

>>ac*********@gmail.com said:

>>>The application/software that is being run, is messing up the memory
due to which a subsequent malloc fails.

Initialise every pointer.

I wouldn't go so far as to advise to initialise _every_ pointer.

#define POVER(arr) ((arr) + sizeof(arr)/sizeof*(arr))

int *p;

for(p=array1;POVER(array1)!=p;++p) /* Something */ ;

for(p=array2;POVER(array2)!=p;++p) /* Something */ ;
Initializing every pointer does no harm, but it is unlikely to
improve the situation of the original poster. Here we have a
malloc/free problem, so he needs to debug that part of the
library. And it is not an uninitialized pointer probably,
but a double free, or a more serius problem.
>
>>Check every malloc/calloc/realloc to ensure it succeeded before you rely
on its return value.

If malloc'ing less than a kilobyte, I wouldn't bother.

In a debug setting is better to never check malloc, so, if there is any
failure the program crashes immediately at the point of failure.

In a production setting it is obvious that some recovery action must be
started when there is no more memory.

>
>>Check that every array access is within bounds (0 to n - 1, for an array
of n elements).

This is like saying to the kids:

Be a good kid and do not do any stupid actions ok?

HOW could that advise be implemented? It is all the difficulty of
C. Telling people "check every array access" leads to no concrete
solutions for the OP.
>
One should _always_ watch out for such things when looking back over one's
code.
>>Set indeterminate ('dangling') pointers to NULL.

This is good advice. Start with KNOWN conditions.
>
In Debug Mode, maybe. It wastes valuable nanoseconds (if not microseconds)
in Release Mode. Maybe something like the following would be a compromise:

#ifdef NDEBUG
#define DMODE(statement)
#else
#define DMODE(statement) statement
#endif

int main()
{
int *p;

...

free(p); DMODE(p=0);
}
Oct 1 '06 #8

P: n/a
Richard Heathfield posted:
At least until he is ready to apply for re-admission to civilisation, Mr
Gotham's opinion on style is of no consequence to me...

Congratulations Great Dictator Richard. I shall rejoin your fascist regime
post haste.

>>Check every malloc/calloc/realloc to ensure it succeeded before you
rely
>>on its return value.


If malloc'ing less than a kilobyte, I wouldn't bother.

...but when he offers dangerously stupid advice such as that, it's a good
idea for people to point it out. Such stupid advice leads, when followed,
to buggy, unstable software.

Many people disagree with you.

>>Set indeterminate ('dangling') pointers to NULL.

In Debug Mode, maybe. It wastes valuable nanoseconds (if not
microseconds)
>in Release Mode.

Yet more stupid advice. Is there no beginning to this man's talent?

You're on a roll today Richard, tossing your civility out the window so
that people will pay attention to your dim-witted attitude. You've yet to
call me a bonehead though -- that _really_ sealed the argument for you the
last time.

--

Frederick Gotham
Oct 1 '06 #9

P: n/a
jacob navia wrote:
Frederick Gotham wrote:
>Richard Heathfield posted:
>
Initialise every pointer.

Initializing every pointer does no harm, [...]
It does no harm to the running program, certainly. But
it *does* harm the process of developing the program, by
removing the compiler's ability to warn about certain kinds
of errors. Example:

char *next_field(char **start)
{
char *p /* = NULL */, *q /* = NULL */;
/* Skip white space to find the start of the field: */
p = *start + strspn(*start, " \t\f\r\n");
/* Skip non-whites to find the end of the field: */
p = p + strcspn(p, " \t\f\r\n");
/* Record where the next search should start: */
*start = q + (*q != '\0');
/* Zero-terminate the field just located: */
*q = '\0';
/* Return a pointer to its beginning: */
return p;
}

.... is an erroneous attempt to locate and snip a white-space-
delimited field from a string. The error is in the second
assignment: The result of the expression involving strcspn()
ought to have been assigned to q, not to p (we want p to point
to the start of the field, q to point just past its end). If
q is not initialized at the point of declaration, many compilers
will warn about its use in the third assignment: they will see
that it is being read without having been given a value and will
squawk about it. But if the declaration of q also initializes it,
the compiler won't complain about using a variable that may not
have been initialized, and the error may go undetected longer.

The cheapest errors are those not made in the first place.
The next-cheapest are those caught by the compiler and fixed
before committing the code. Errors that actually make it as far
as a testing phase -- or into deployment, may the Lord have mercy
on us! -- are more expensive than those caught earlier, so it is
a good idea to give the compiler every encouragement to catch
errors early. Wanton initialization of pointers (of any variables,
actually) discourages the compiler's assistance and therefore ought
not to be indulged in.

--
Eric Sosman
es*****@acm-dot-org.invalid
Oct 1 '06 #10

P: n/a
jacob navia said:

<snip>
Initializing every pointer does no harm, but it is unlikely to
improve the situation of the original poster.
What I gave was a list of several easy steps (initialisation being one of
those steps) which, taken together, make it easier to debug memory-related
problems. In that context, it will certainly improve the situation of the
original poster.

<snip>
In a debug setting is better to never check malloc,
Oh deary deary me. You surely cannot be serious?
so, if there is any
failure the program crashes immediately at the point of failure.
The Standard offers no such guarantee.
>>>Check that every array access is within bounds (0 to n - 1, for an array
of n elements).

This is like saying to the kids:

Be a good kid and do not do any stupid actions ok?
Yes. And if you're a good kid and don't do anything stupid, you improve the
chances that your code's going to work.
HOW could that advise be implemented?
for(i = 0; i < n; i++)
{
x[i] = foo(i);
}

It's not rocket science.
It is all the difficulty of C.
I don't see what's so difficult about it. If you're writing outside your
array, your mental model of the program is wrong. And so, whether or not
the language cushions you from the bad effects of writing out of bounds,
you still need to fix the program. Anyone who can drive safely along the
road knows the importance, and *ease*, of keeping within bounds.
Telling people "check every array access" leads to no concrete
solutions for the OP.
Here's what I actually said:

"Initialise every pointer. Check every malloc/calloc/realloc to ensure it
succeeded before you rely on its return value. Check that every array
access is within bounds (0 to n - 1, for an array of n elements). Set
indeterminate ('dangling') pointers to NULL.

Following these simple steps will get rid of 99.90072% of all known
memory-related crashes."

I reckon that *will* lead to a concrete solution for the OP.

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 1 '06 #11

P: n/a
Frederick Gotham said:
Richard Heathfield posted:
>>>Check every malloc/calloc/realloc to ensure it succeeded before
you rely on its return value.

If malloc'ing less than a kilobyte, I wouldn't bother.

...but when he offers dangerously stupid advice such as that, it's a good
idea for people to point it out. Such stupid advice leads, when followed,
to buggy, unstable software.

Many people disagree with you.
Yes, and many people aren't very good C programmers.

>>>Set indeterminate ('dangling') pointers to NULL.

In Debug Mode, maybe. It wastes valuable nanoseconds (if not
microseconds)
>>in Release Mode.

Yet more stupid advice. Is there no beginning to this man's talent?

You're on a roll today Richard, tossing your civility out the window
Hypocrisy. In any case, you have surrendered your right to demand civility
from anyone else, by showing such appalling incivility to Keith Thompson -
as you are well aware.
so
that people will pay attention to your dim-witted attitude. You've yet to
call me a bonehead though -- that _really_ sealed the argument for you the
last time.
It seems that the point of that "bonehead" comment passed right over your
head.

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 1 '06 #12

P: n/a
Richard Heathfield posted:
Hypocrisy. In any case, you have surrendered your right to demand
civility from anyone else, by showing such appalling incivility to Keith
Thompson - as you are well aware.
Allow me to reshape your words in an effort to show you how we express
ourselves in the non-fascist world:

"Hypocrisy, in my opinion. In any case, I think you have surrendered your
right to demand civility from anyone else, by showing what I deem to be
appalling incivility to Keith Thompson -- as I believe you are well aware."

In any case, may we end this Babysitters' Club masquerade? Neither you nor
Keith like me, that's fine -- I haven taken quite a disliking to the both of
you. Notwithstanding that, I'll continue to post here and respond to whatever
post captures my interest with regard to C programming, regardless of the
post's author. So do me a favour and save all your little diatribes for your
next teen book. If you want to talk about C, you're in the right place. I
quite like how Keith Thompson has accepted his disliking of me and ceased
responding -- please follow suit, it will make comp.lang.c a more pleasant
place.

--

Frederick Gotham
Oct 1 '06 #13

P: n/a
Eric Sosman said:
jacob navia wrote:
>Frederick Gotham wrote:
>>Richard Heathfield posted:

Initialise every pointer.

Initializing every pointer does no harm, [...]

It does no harm to the running program, certainly. But
it *does* harm the process of developing the program, by
removing the compiler's ability to warn about certain kinds
of errors.
I beg to differ. I mean, yes, it has the effect that you say it has - on
some compilers, anyway - but it doesn't harm the development process at
all.
Example:

char *next_field(char **start)
{
char *p /* = NULL */, *q /* = NULL */;
/* Skip white space to find the start of the field: */
p = *start + strspn(*start, " \t\f\r\n");
/* Skip non-whites to find the end of the field: */
p = p + strcspn(p, " \t\f\r\n");
/* Record where the next search should start: */
*start = q + (*q != '\0');
/* Zero-terminate the field just located: */
*q = '\0';
/* Return a pointer to its beginning: */
return p;
}
Great example. Well done. If you omit the initialisation, okay, let's say
the compiler issues a warning (despite the fact that it needn't and some
don't). But you know and I know that some people will say "oh, it's only a
warning, it's fine", and they'll be scratching their heads trying to debug
it. Whereas, if you set q to NULL, then it doesn't take a genius to
discover that *start is being set to an obviously silly value (probably
NULL, possibly 1). So the debugging process is very swift after all.
The cheapest errors are those not made in the first place.
The next-cheapest are those caught by the compiler and fixed
before committing the code.
That's fine, provided people treat diagnostic messages seriously. We have
ample evidence here on comp.lang.c that this is not the case.
Wanton initialization of pointers (of any variables,
actually) discourages the compiler's assistance and therefore ought
not to be indulged in.
Giving the program deterministic behaviour by ensuring that all variables
are initialised helps the programmer to understand the program better and
debug it more quickly, and therefore ought to be encouraged. :-)

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 1 '06 #14

P: n/a
Frederick Gotham said:
In any case, may we end this Babysitters' Club masquerade? Neither you nor
Keith like me, that's fine
You are mistaken. I got on with you just fine until you called Keith a
fascist. I continue to hope that you will apologise to him because I
continue to believe you are a reasonable man, albeit somewhat stubborn.

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 1 '06 #15

P: n/a
Frederick Gotham wrote:
Richard Heathfield posted:
Set indeterminate ('dangling') pointers to NULL.


In Debug Mode, maybe. It wastes valuable nanoseconds (if not microseconds)
in Release Mode. Maybe something like the following would be a compromise:

#ifdef NDEBUG
#define DMODE(statement)
#else
#define DMODE(statement) statement
#endif
Yikes, that sounds like a great way to introduce heisenbugs. I could
_maybe_ see this in a very tight inner loop, but aside from that it's
unlikely that the time difference would even be measureable within the
context of the whole program running, let alone noticeable.

Oct 1 '06 #16

P: n/a
Richard Heathfield wrote:
Eric Sosman said:

>>jacob navia wrote:
>>>Frederick Gotham wrote:
Richard Heathfield posted:

>Initialise every pointer.

Initializing every pointer does no harm, [...]

It does no harm to the running program, certainly. But
it *does* harm the process of developing the program, by
removing the compiler's ability to warn about certain kinds
of errors.


I beg to differ. I mean, yes, it has the effect that you say it has - on
some compilers, anyway - but it doesn't harm the development process at
all.

>>Example:

char *next_field(char **start)
{
char *p /* = NULL */, *q /* = NULL */;
/* Skip white space to find the start of the field: */
p = *start + strspn(*start, " \t\f\r\n");
/* Skip non-whites to find the end of the field: */
p = p + strcspn(p, " \t\f\r\n");
/* Record where the next search should start: */
*start = q + (*q != '\0');
/* Zero-terminate the field just located: */
*q = '\0';
/* Return a pointer to its beginning: */
return p;
}


Great example. Well done. If you omit the initialisation, okay, let's say
the compiler issues a warning (despite the fact that it needn't and some
don't). But you know and I know that some people will say "oh, it's only a
warning, it's fine", and they'll be scratching their heads trying to debug
it. Whereas, if you set q to NULL, then it doesn't take a genius to
discover that *start is being set to an obviously silly value (probably
NULL, possibly 1). So the debugging process is very swift after all.
This programmer you describe seems a bit of an odd fish. He's
reckless enough to ignore warning messages, yet diligent enough to
initialize all his pointers. Sounds like a person with a multiple
personality disorder ...
> The cheapest errors are those not made in the first place.
The next-cheapest are those caught by the compiler and fixed
before committing the code.

That's fine, provided people treat diagnostic messages seriously. We have
ample evidence here on comp.lang.c that this is not the case.
It's interesting to read this in light of remarks about "drool-
proof languages" on another current thread ...

I feel -- without quantitative evidence, I admit -- that there's
more to be gained from improving a programmer's skills than by trying
to compensate for his deficiencies. A person can be taught to pay
attention to warnings, or to initialize everything in sight so the
warnings go away and their Heisenbugs become reproducible. The first
course seems to me to offer more benefits, on balance, than the second.
Yes, a Heisenbug can be a royal PITA -- but it's not a certainty that
a reproducible error arising from a wrongly-initialized variable will
be reliably detected, either. Even if that variable is a pointer and
the initialization is to NULL, it's not a sure bet that there will be
a catastrophic failure, easily spotted: Maybe the pointer will be used
as the argument to fflush() or the first argument to strtok() or in
some other context where NULL is perfectly legal -- but perhaps not
what was intended.
>>Wanton initialization of pointers (of any variables,
actually) discourages the compiler's assistance and therefore ought
not to be indulged in.

Giving the program deterministic behaviour by ensuring that all variables
are initialised helps the programmer to understand the program better and
debug it more quickly, and therefore ought to be encouraged. :-)
Get rid of the STOP sign at the busy intersection, but make sure
that anyone who fails to stop *will* be run over by a cement truck.
Well, there won't be many repeat offenders ... (An old Dilbert strip
involved Dogbert trying to teach common sense to those who lacked it
rather conspicuously. "Larry the auto mechanic liked to smoke cigars
while working on gasoline engines," says Dogbert. "Can anybody think
of a problem this might cause?" The answer comes from someone swathed
in bandages and smoking a cigar: "He gets struck by lightning every
time?")

--
Eric Sosman
es*****@acm-dot-org.invalid

Oct 1 '06 #17

P: n/a
Richard Heathfield wrote:
Eric Sosman said:

>>jacob navia wrote:
>>>Frederick Gotham wrote:
Richard Heathfield posted:

>Initialise every pointer.

Initializing every pointer does no harm, [...]

It does no harm to the running program, certainly. But
it *does* harm the process of developing the program, by
removing the compiler's ability to warn about certain kinds
of errors.


I beg to differ. I mean, yes, it has the effect that you say it has - on
some compilers, anyway - but it doesn't harm the development process at
all.
Thank goodness C99 gave us the ability to declare variables at point of
use, this entire debate becomes moot.

--
Ian Collins.
Oct 1 '06 #18

P: n/a
Richard Heathfield wrote:
it. Whereas, if you set q to NULL, then it doesn't take a genius to
discover that *start is being set to an obviously silly value (probably
NULL, possibly 1). So the debugging process is very swift after all.
Right. There should be an immediate crash upon (*q != '\0') .
Hopefully.
That's fine, provided people treat diagnostic messages seriously. We have
ample evidence here on comp.lang.c that this is not the case.
Yes. But is that really a good enough reason to say "always initialize every
pointer and tie your shoes before going outdoors?" Might as well never
use malloc and always use calloc while we're at it.
Giving the program deterministic behaviour by ensuring that all variables
are initialised helps the programmer to understand the program better and
debug it more quickly, and therefore ought to be encouraged. :-)
I pretty much agree - but after a certain point where it reaches
compulsiveness, then it starts to head into doubting something you already
know or have enough experience with that pre-initializing ends up being token
exercise. What I mean by this is that, given a long chain of string
wrangling, like Eric pointed out, setting a pointer to NULL, beforehand, as a
method of insta-crash due to coding mistakes is almost like saying "I am
initializing this because I might make a mistake here." as opposed to
something like:

list_s *head = NULL;

Which has a functional purpose rather than a "I might screw up" purpose.
Oct 1 '06 #19

P: n/a
Ian Collins wrote:
Thank goodness C99 gave us the ability to declare variables at point of
use, this entire debate becomes moot.
Yea instead the code looks like crap to read.
Oct 1 '06 #20

P: n/a
Eric Sosman said:
This programmer you describe seems a bit of an odd fish. He's
reckless enough to ignore warning messages, yet diligent enough to
initialize all his pointers. Sounds like a person with a multiple
personality disorder ...
Well, of course what we're really talking about is "what constitutes good
practice?" What kind of code is easiest to debug? What kind of strategy
works best for dealing with diagnostic messages? Do we strive for a clean
compile at all costs? I used to do so, but I found that sometimes I
couldn't /get/ a clean compile without adding spurious casts to the code,
which I was loathe to do. So we have to consider a strategy on how to deal
with warnings. When is a warning significant? To me, the answer is "it's
significant for as long as you can't understand why it's there". So - if a
compiler told me "hey, you might be using this thing before giving it a
proper value", then yes, I'd take it seriously. Unfortunately, it is not a
panacea (and yet it certainly looks like one). It can't, for example, deal
with foo(&obj); - and so now you have the worst of both worlds - no
diagnostic message AND no initialisation. Oopsie.
>> The cheapest errors are those not made in the first place.
The next-cheapest are those caught by the compiler and fixed
before committing the code.

That's fine, provided people treat diagnostic messages seriously. We have
ample evidence here on comp.lang.c that this is not the case.

It's interesting to read this in light of remarks about "drool-
proof languages" on another current thread ...
Yes, I'm trying hard to avoid quoting Sturgeon's Law here...
I feel -- without quantitative evidence, I admit -- that there's
more to be gained from improving a programmer's skills than by trying
to compensate for his deficiencies.
I'm sticking my neck out here, but I am willing to bet any amount up to and
including a penny that you spend hardly any time debugging your own code.
Not *no* time, but hardly any time. I suspect that you make a low number of
mistakes, and that most of those you do make are fixed within seconds or,
at most, minutes of your seeing their symptoms emerge for the first time.
It's certainly true for me, anyway, and I'd be surprised if it weren't true
for you too. And the reason is obvious - you know what you're doing, and
you've evolved a strategy for successful code development that *works* -
for you. And I've evolved a strategy that works for me. There's nothing in
the rules says we have to have evolved the /same/ strategy. And maybe
that's why we're arguing. :-)

Now, when I have to debug someone else's code, that can take a bit longer,
because they didn't write it the way I would have wanted them to write it.
When debugging other people's code, then, and given the choice, I'd rather
chase a stable target than a Heisenbug. So I recommend to people that they
write the code in a way that makes it easy for /me/ to debug it. (After
all, that's probably what I'll end up doing anyway!)
>
>>>Wanton initialization of pointers (of any variables,
actually) discourages the compiler's assistance and therefore ought
not to be indulged in.

Giving the program deterministic behaviour by ensuring that all variables
are initialised helps the programmer to understand the program better and
debug it more quickly, and therefore ought to be encouraged. :-)

Get rid of the STOP sign at the busy intersection, but make sure
that anyone who fails to stop *will* be run over by a cement truck.
Yes, absolutely. In a computer, nobody gets hurt (at least, not during
initial program development!) - we can run the little variables up to the
stop sign over and over again, and watch them go over the line and get
crushed by the truck over and over, and eventually we figure there's
something wrong with their brakes. So we go fix that. Typically, it takes a
few seconds, half of which are spent recovering from slapping our own heads
- "DUH!" - as we marvel at how we could have been so dumb.

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 1 '06 #21

P: n/a
Ian Collins said:
Thank goodness C99 gave us the ability to declare variables at point of
use, this entire debate becomes moot.
Only when C99 becomes widely implemented.

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 1 '06 #22

P: n/a
Christopher Layne said:
Richard Heathfield wrote:
>That's fine, provided people treat diagnostic messages seriously. We have
ample evidence here on comp.lang.c that this is not the case.

Yes. But is that really a good enough reason to say "always initialize
every pointer and tie your shoes before going outdoors?" Might as well
never use malloc and always use calloc while we're at it.
If calloc guaranteed to initialise objects to their static default
initialiser values, then I would indeed use it. But it doesn't. In fact, it
can't. So you have to put in the explicit assignment code yourself. No
getting around it. :-(
>
>Giving the program deterministic behaviour by ensuring that all variables
are initialised helps the programmer to understand the program better and
debug it more quickly, and therefore ought to be encouraged. :-)

I pretty much agree - but after a certain point where it reaches
compulsiveness, then it starts to head into doubting something you already
know or have enough experience with that pre-initializing ends up being
token exercise.
I think of it as "defence in depth", and I've found it to be a valuable
strategy over the years. I have twice been bitten by failing to follow it
(in each case, no compiler diagnostic message would have helped me, since
the first use of the object in each case was to pass its address to another
routine). In each case, the bug was only discovered in production. I'm not
prepared to risk a third such occasion.

<snip>

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 1 '06 #23

P: n/a
Frederick Gotham wrote:
Richard Heathfield posted:
.... snip ...
>
>Check every malloc/calloc/realloc to ensure it succeeded before
you rely on its return value.

If malloc'ing less than a kilobyte, I wouldn't bother.
This is a stupid and foolish attitude, and requires warning other
readers. I still haven't seen your apology.

--
Some informative links:
<news:news.announce.newusers
<http://www.geocities.com/nnqweb/>
<http://www.catb.org/~esr/faqs/smart-questions.html>
<http://www.caliburn.nl/topposting.html>
<http://www.netmeister.org/news/learn2quote.html>
<http://cfaj.freeshell.org/google/>
Oct 1 '06 #24

P: n/a
Ian Collins wrote:
Richard Heathfield wrote:
.... snip about preinitializing everything ...
>>
I beg to differ. I mean, yes, it has the effect that you say it
has - on some compilers, anyway - but it doesn't harm the
development process at all.

Thank goodness C99 gave us the ability to declare variables at
point of use, this entire debate becomes moot.
On the contrary, to my mind this simply opens up another area in
which to foul things. In particular such declarations are
inordinately sensitive to goto to points within the block. Without
initialization, this problem goes away.

I don't buy the argument that goto should never be used. I do
agree that general use in place of structured constructs leads to
spaghetti code. The rarer such use becomes, the more likely the
coder will not recognize the dangers involved.

Besides, I like knowing where to find the variable declarations.
If there are too many for convenience, or the function is too long,
it is a sign that the code is mis-structured.

--
Some informative links:
<news:news.announce.newusers
<http://www.geocities.com/nnqweb/>
<http://www.catb.org/~esr/faqs/smart-questions.html>
<http://www.caliburn.nl/topposting.html>
<http://www.netmeister.org/news/learn2quote.html>
<http://cfaj.freeshell.org/google/>
Oct 2 '06 #25

P: n/a
CBFalconer wrote:
Besides, I like knowing where to find the variable declarations.
If there are too many for convenience, or the function is too long,
it is a sign that the code is mis-structured.
I personally despise this C++/"declare on a whim" style. I like to know what
I'm getting into when I read over a function - and a function which has it's
table of contents spread out and buried within individual chapters just
pisses me off more than it helps anything.
Oct 2 '06 #26

P: n/a
Christopher Layne wrote:
CBFalconer wrote:
>Besides, I like knowing where to find the variable declarations.
If there are too many for convenience, or the function is too long,
it is a sign that the code is mis-structured.

I personally despise this C++/"declare on a whim" style.
I agree that declarations should be at the top of a block. But I remain
fond of one exception:

int k=SOME_MAX;
for( int i=0; i<k; i++ ){/* wobble */}

I only recently realized that was a non-portable extension, even though
I've been using it since, oh, forever.

Oct 2 '06 #27

P: n/a
Christopher Layne wrote:
CBFalconer wrote:
>>Besides, I like knowing where to find the variable declarations.
If there are too many for convenience, or the function is too long,
it is a sign that the code is mis-structured.


I personally despise this C++/"declare on a whim" style. I like to know what
I'm getting into when I read over a function - and a function which has it's
table of contents spread out and buried within individual chapters just
pisses me off more than it helps anything.
Not a problem when you keep your functions down to a dozen or so lines.

I guess it depends on where you are coming form, having been a C++
developer for the past decade and a bit, I'm used to declaring variables
where they are used (and where I realise they are required!).

--
Ian Collins.
Oct 2 '06 #28

P: n/a
In article <45***************@yahoo.com>,
CBFalconer <cb********@maineline.netwrote:
>Frederick Gotham wrote:
>Richard Heathfield posted:
... snip ...
>>
>>Check every malloc/calloc/realloc to ensure it succeeded before
you rely on its return value.

If malloc'ing less than a kilobyte, I wouldn't bother.

This is a stupid and foolish attitude, and requires warning other
readers. I still haven't seen your apology.
I trust you are holding your breath...

Oct 2 '06 #29

P: n/a
jmcgill wrote:
Christopher Layne wrote:
>CBFalconer wrote:
>>Besides, I like knowing where to find the variable declarations.
If there are too many for convenience, or the function is too long,
it is a sign that the code is mis-structured.

I personally despise this C++/"declare on a whim" style.

I agree that declarations should be at the top of a block. But I remain
fond of one exception:

int k=SOME_MAX;
for( int i=0; i<k; i++ ){/* wobble */}

I only recently realized that was a non-portable extension, even though
I've been using it since, oh, forever.
It's portable, under C99.

--
Some informative links:
<news:news.announce.newusers
<http://www.geocities.com/nnqweb/>
<http://www.catb.org/~esr/faqs/smart-questions.html>
<http://www.caliburn.nl/topposting.html>
<http://www.netmeister.org/news/learn2quote.html>
<http://cfaj.freeshell.org/google/>
Oct 2 '06 #30

P: n/a
CBFalconer wrote:
It's portable, under C99.
For me, "recently" long predates "C99". C99 is yesterday. I'm ancient.
Oct 2 '06 #31

P: n/a
CBFalconer said:
Ian Collins wrote:
>Richard Heathfield wrote:
... snip about preinitializing everything ...
>>>
I beg to differ. I mean, yes, it has the effect that you say it
has - on some compilers, anyway - but it doesn't harm the
development process at all.

Thank goodness C99 gave us the ability to declare variables at
point of use, this entire debate becomes moot.

On the contrary, to my mind this simply opens up another area in
which to foul things. In particular such declarations are
inordinately sensitive to goto to points within the block.
Not for people who avoid goto like the... the... like they avoid cliches.
Without initialization, this problem goes away.
You seem to be saying that, IF I adopt one particular coding practice that I
find unwise (the use of goto), AND if I adopt another particular coding
practice that I find unwise (the use of on-the-fly declarations), THEN a
practice that I find useful may become less useful. Well, perhaps. And IF I
start walking around with my eyes shut, AND changing my direction of motion
randomly, THEN I won't bother glancing right, left, and right again before
crossing, since there won't be any point. But until then...
I don't buy the argument that goto should never be used.
I have never tried to sell that argument, as far as I can recall. On the day
a goto makes my code clearer to me than a more structured approach, I'm
quite prepared to use it. Programming is about clarity, after all. But a
goto that dives back up above an uninitialised mixed declaration is even
less likely than usual to strike me as constituting a way of making the
code clearer.

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 2 '06 #32

P: n/a
CBFalconer said:
jmcgill wrote:
>>
int k=SOME_MAX;
for( int i=0; i<k; i++ ){/* wobble */}

I only recently realized that was a non-portable extension, even though
I've been using it since, oh, forever.

It's portable, under C99.
But C99 is itself not portable.

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 2 '06 #33

P: n/a
On Mon, 02 Oct 2006 05:04:21 +0000, Richard Heathfield
<in*****@invalid.invalidwrote:
>CBFalconer said:
>jmcgill wrote:
>>>
int k=SOME_MAX;
for( int i=0; i<k; i++ ){/* wobble */}

I only recently realized that was a non-portable extension, even though
I've been using it since, oh, forever.

It's portable, under C99.

But C99 is itself not portable.
And the reasons that support that argument make C90 (strictly) not
portable as well.

--
jay
Oct 3 '06 #34

P: n/a
jaysome said:
On Mon, 02 Oct 2006 05:04:21 +0000, Richard Heathfield
<in*****@invalid.invalidwrote:
>>CBFalconer said:
>>jmcgill wrote:

int k=SOME_MAX;
for( int i=0; i<k; i++ ){/* wobble */}

I only recently realized that was a non-portable extension, even though
I've been using it since, oh, forever.

It's portable, under C99.

But C99 is itself not portable.

And the reasons that support that argument make C90 (strictly) not
portable as well.
Sure - strictly speaking. But in practice, I can write normal C90 code -
stuff that doesn't mess around in the dark cobwebby corners of the language
- and expect it to compile just about anywhere. But just about any single
C99 feature I choose to employ could render my code non-portable. Even //
comments will cause my code to be rejected by some implementations
(including the one I use most often myself).

Almost all of the code I write nowadays falls into one of four categories:

1) I know it's for S16ILP32 Linux
2) I know it's for S16ILP32 Windows
3) I know it's for both 1) and 2) above
4) I haven't the faintest idea what it will end up on

And most tends to be in the last category. So I have to choose - what do I
consider to be the *most portable* way to write code? And as far as I can
make out, the most portable strategy is to write code in the common subset
of C90 and C99. If anyone has any better ideas, I'd love to hear them.

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 3 '06 #35

P: n/a
Frederick Gotham <fg*******@SPAM.comwrote:
Richard Heathfield posted:
ac*********@gmail.com said:
The application/software that is being run, is messing up the memory
due to which a subsequent malloc fails.
Check every malloc/calloc/realloc to ensure it succeeded before you rely
on its return value.

If malloc'ing less than a kilobyte, I wouldn't bother.
On a board which doesn't have the memory to run gdb? You'd better.

Richard
Oct 3 '06 #36

P: n/a
jacob navia <ja***@jacob.remcomp.frwrote:
Frederick Gotham wrote:
Richard Heathfield posted:
>Check every malloc/calloc/realloc to ensure it succeeded before you rely
on its return value.
If malloc'ing less than a kilobyte, I wouldn't bother.

In a debug setting is better to never check malloc, so, if there is any
failure the program crashes immediately at the point of failure.
Assuming that writing through a null pointer - on an unusual kind of
board, no less - _will always immediately_ crash is unbelievably stupid.
>Set indeterminate ('dangling') pointers to NULL.

This is good advice. Start with KNOWN conditions.
It is bad advice. It makes you rely on the assumption that you have
determined all such pointers.

Richard
Oct 3 '06 #37

P: n/a
Richard Bos said:
jacob navia <ja***@jacob.remcomp.frwrote:
>Frederick Gotham wrote:
Richard Heathfield posted:

Check every malloc/calloc/realloc to ensure it succeeded before you
rely on its return value.

If malloc'ing less than a kilobyte, I wouldn't bother.

In a debug setting is better to never check malloc, so, if there is any
failure the program crashes immediately at the point of failure.

Assuming that writing through a null pointer - on an unusual kind of
board, no less - _will always immediately_ crash is unbelievably stupid.
The latest party line appears to be that Mr Navia isn't unbelievably stupid,
but merely not very skilled at English. It may be that he intended to say
"Whether or not in a debug setting, it is better always to check malloc;
there is no guarantee that the program will crash immediately at the point
of failure" but that he accidentally said pretty much the exact opposite.

>>Set indeterminate ('dangling') pointers to NULL.

This is good advice. Start with KNOWN conditions.

It is bad advice. It makes you rely on the assumption that you have
determined all such pointers.
No, it isn't bad advice, and no, it doesn't make you rely on any such thing.
It merely increases your confidence that your program's behaviour is
deterministic, and makes debugging a lot easier.

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 3 '06 #38

P: n/a
Richard Bos wrote:
jacob navia <ja***@jacob.remcomp.frwrote:

>>Frederick Gotham wrote:
>>>Richard Heathfield posted:
Check every malloc/calloc/realloc to ensure it succeeded before you rely
on its return value.

If malloc'ing less than a kilobyte, I wouldn't bother.

In a debug setting is better to never check malloc, so, if there is any
failure the program crashes immediately at the point of failure.


Assuming that writing through a null pointer - on an unusual kind of
board, no less - _will always immediately_ crash is unbelievably stupid.
The OP is running linux. Linux has memory protection, as far
as I remember.

But better treat people of stupid immediately, specially if
its Jacob Navia...

That doesn't cost anything since the guy never gets upset...
Oct 3 '06 #39

P: n/a
Richard Heathfield wrote:
Richard Bos said:

>>jacob navia <ja***@jacob.remcomp.frwrote:

>>>Frederick Gotham wrote:

Richard Heathfield posted:
>Check every malloc/calloc/realloc to ensure it succeeded before you
>rely on its return value.

If malloc'ing less than a kilobyte, I wouldn't bother.

In a debug setting is better to never check malloc, so, if there is any
failure the program crashes immediately at the point of failure.

Assuming that writing through a null pointer - on an unusual kind of
board, no less - _will always immediately_ crash is unbelievably stupid.


The latest party line appears to be that Mr Navia isn't unbelievably stupid,
but merely not very skilled at English. It may be that he intended to say
"Whether or not in a debug setting, it is better always to check malloc;
there is no guarantee that the program will crash immediately at the point
of failure" but that he accidentally said pretty much the exact opposite.
Linux supposes memory protection as far as I remember.
The OP said it was running some linux system!

jacob
Oct 3 '06 #40

P: n/a
jacob navia said:
Richard Bos wrote:
>jacob navia <ja***@jacob.remcomp.frwrote:
<snip>
>>>
In a debug setting is better to never check malloc, so, if there is any
failure the program crashes immediately at the point of failure.

Assuming that writing through a null pointer - on an unusual kind of
board, no less - _will always immediately_ crash is unbelievably stupid.

The OP is running linux. Linux has memory protection, as far
as I remember.
That is irrelevant in comp.lang.c - even if the OP is running Linux, that
doesn't necessarily mean that Linux is the only system on which his code
will be run. Advice given here about C should be /general/ advice; it
should be good for /any/ hosted implementation (and, if applicable, on
freestanding implementations).

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 3 '06 #41

P: n/a
jacob navia said:

<snip>
Linux supposes memory protection as far as I remember.
What has that to do with C?
The OP said it was running some linux system!
So what? If that's relevant, he's in the wrong newsgroup.

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 3 '06 #42

P: n/a
jacob navia wrote:
Richard Bos wrote:
>jacob navia <ja***@jacob.remcomp.frwrote:
>>Frederick Gotham wrote:
Richard Heathfield posted:

Check every malloc/calloc/realloc to ensure it succeeded before you
rely
on its return value.

If malloc'ing less than a kilobyte, I wouldn't bother.

In a debug setting is better to never check malloc, so, if there is any
failure the program crashes immediately at the point of failure.

Assuming that writing through a null pointer - on an unusual kind of
board, no less - _will always immediately_ crash is unbelievably stupid.

The OP is running linux. Linux has memory protection, as far
as I remember.
You know, it's comp.lang.c -- you either give off-topic advice (when
qualifying it as Linux only answer) or not entirely correct advice.
Even though your statement may be correct for Linux and also for many
hosted environments, I'd still rather not follow it.

But better treat people of stupid immediately, specially if
its Jacob Navia...
There are two sides to something like that.

You often get into heated discussions and present your positions
in a rather unfavourable and unfortunate way. I am glad that people
like you, Paul Hsieh, and Chris Hills participate because you are
clearly intelligent and the positions you represent are decidedly
off the group's mainstream -- this inspires thought. As always in
comp.lang.c, there are issues with the given representation and
its interpretation :-)

That doesn't cost anything since the guy never gets upset...
:-/
Cheers
Michael
--
E-Mail: Mine is an /at/ gmx /dot/ de address.
Oct 3 '06 #43

P: n/a
Richard Heathfield wrote:
jacob navia said:

>>Richard Bos wrote:
>>>jacob navia <ja***@jacob.remcomp.frwrote:

<snip>
>>>>In a debug setting is better to never check malloc, so, if there is any
failure the program crashes immediately at the point of failure.

Assuming that writing through a null pointer - on an unusual kind of
board, no less - _will always immediately_ crash is unbelievably stupid.

The OP is running linux. Linux has memory protection, as far
as I remember.


That is irrelevant in comp.lang.c - even if the OP is running Linux, that
doesn't necessarily mean that Linux is the only system on which his code
will be run. Advice given here about C should be /general/ advice; it
should be good for /any/ hosted implementation (and, if applicable, on
freestanding implementations).
Who are YOU to tell ME what advice should I give?

I give advice adapted to the OP question!

He is running linux, then I assume memory protection!
Who cares about each possible CPU in the planet?
He is in a certain situation, and give specific advice to THAT
situation!

Oct 3 '06 #44

P: n/a
jacob navia said:
Richard Heathfield wrote:
>jacob navia said:
<snip>
>>>The OP is running linux. Linux has memory protection, as far
as I remember.


That is irrelevant in comp.lang.c - even if the OP is running Linux, that
doesn't necessarily mean that Linux is the only system on which his code
will be run. Advice given here about C should be /general/ advice; it
should be good for /any/ hosted implementation (and, if applicable, on
freestanding implementations).

Who are YOU to tell ME what advice should I give?
I'm a guy who subscribes to comp.lang.c, which is for discussions about C,
not for discussions about Linux. That's why it says "c", not "linux", in
the group's name. Who are YOU arbitrarily to CHANGE the topic of discussion
of an INTERNATIONAL NEWSGROUP to suit YOUR whim?
I give advice adapted to the OP question!
Yes, and if you give advice that has absolutely nothing to do with C, then
nobody can stop you doing that, but on the other hand you can't stop other
people complaining about it either. Newsgroups have topics for the
excellent reason that, if they didn't, there'd just be the one newsgroup,
with 10,000,000 posts an hour, on every subject from aardvarks to zymurgy,
and nobody would be able to find anything they were interested in
discussing because everything would be all mixed in together.

I would expect to have to explain this to a Usenet newbie, but you've been
posting to Usenet for longer than I have. You should have worked it out by
now! Are you being deliberately stupid, or just accidentally stupid? It
must be one or the other - you cannot reasonably claim ignorance of
topicality after over a decade of posting to Usenet!
He is running linux, then I assume memory protection!
If Linux is relevant to his question, he's in the wrong group.
Who cares about each possible CPU in the planet?
C programmers.
He is in a certain situation, and give specific advice to THAT
situation!
The best advice you can give him is to ask his question in a newsgroup where
it's topical.

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 3 '06 #45

P: n/a
Frederick Gotham <fg*******@SPAM.comwrites:
Richard Heathfield posted:
[...]
>Check every malloc/calloc/realloc to ensure it succeeded before you rely
on its return value.

If malloc'ing less than a kilobyte, I wouldn't bother.
That is extraordinarily bad advice.

(Frederick, I'm still waiting for your apology.)

--
Keith Thompson (The_Other_Keith) ks***@mib.org <http://www.ghoti.net/~kst>
San Diego Supercomputer Center <* <http://users.sdsc.edu/~kst>
We must do something. This is something. Therefore, we must do this.
Oct 3 '06 #46

P: n/a
In article <45***********************@news.orange.fr>,
jacob navia <ja***@jacob.remcomp.frwrote:
>The OP is running linux. Linux has memory protection, as far
as I remember.
Does Linux promise memory protection on every implementation?
If a system that Linux is ported to cannot do the kind of memory
protection you are thinking of, then is it prohibitted from calling
itself Linux? ucLinux has been ported to a number of embedded
environments: is it Linux on those environments or is it not?

Does Linux promise that the kind of memory protection you are thinking
of is active on -every- page of memory? What if there happens to be
writable memory within the first "page" of process memory?
SGI IRIX "has memory protection" too, but on IRIX 6.4 and later on
"big" systems that run with 16 Kb virtual pages, virtual address 0 is
*not* write protected for reasons having to do with the graphics
subsystems (which were designed to expect memory at the 8 Kb mark
so that the smallest address format could be used, for speed; that
design was done at a time when IRIX only supported 4 Kb virtual pages.)
--
"law -- it's a commodity"
-- Andrew Ryan (The Globe and Mail, 2005/11/26)
Oct 3 '06 #47

P: n/a
Walter Roberson wrote:
In article <45***********************@news.orange.fr>,
jacob navia <ja***@jacob.remcomp.frwrote:

>>The OP is running linux. Linux has memory protection, as far
as I remember.


Does Linux promise memory protection on every implementation?
If a system that Linux is ported to cannot do the kind of memory
protection you are thinking of, then is it prohibitted from calling
itself Linux? ucLinux has been ported to a number of embedded
environments: is it Linux on those environments or is it not?

Does Linux promise that the kind of memory protection you are thinking
of is active on -every- page of memory? What if there happens to be
writable memory within the first "page" of process memory?
SGI IRIX "has memory protection" too, but on IRIX 6.4 and later on
"big" systems that run with 16 Kb virtual pages, virtual address 0 is
*not* write protected for reasons having to do with the graphics
subsystems (which were designed to expect memory at the 8 Kb mark
so that the smallest address format could be used, for speed; that
design was done at a time when IRIX only supported 4 Kb virtual pages.)
The OP said:

"I am working on MontaVista Linux on a PPC board"

The PowerPC is a very modern chip with memory protection.
Linux with PPC chip is surely a combination where any NULL
access will crash, as it does in the x86 and in most
modern OSes/chips combinations.

There can be exceptions, of course, but they are that: exceptions,
and obviously you have to check for NULL in those implementations.

Oct 3 '06 #48

P: n/a
Keith Thompson posted:
>If malloc'ing less than a kilobyte, I wouldn't bother.

That is extraordinarily bad advice.
Of course, it depends on the requirements of the project and so forth, but
there are many circumstances in which I'd just assume that malloc succeeds.
At the very most, I might do something like:

#include <stddef.h>
#include <stdlib.h>

void *ExitiveMalloc(size_t const size)
{
void *const p = malloc(size);

if(!p) exit(EXIT_FAILURE);

return p;
}
Here's an example of where I'd be wreckless with malloc:

#include <stddef.h>
#include <stdlib.h>
#include <assert.h>
#include <string.h>
#include <ctype.h>

char *const TruncateAndMakeUppercase(char const *const arg,size_t const len)
{
int const assert_dummy = (assert(!!arg), 0);

char *const retval=ExitiveMalloc(len+1), *p=retval;

strncpy(retval,arg,len);

while( *p++ = toupper((char unsigned)*p) );

return (void)assert_dummy, retval;
}

(I'm not entirely sure if I violate a sequence point with the "*p++ = ").

--

Frederick Gotham
Oct 3 '06 #49

P: n/a
Frederick Gotham said:
Keith Thompson posted:
>>If malloc'ing less than a kilobyte, I wouldn't bother.

That is extraordinarily bad advice.

Of course, it depends on the requirements of the project and so forth, but
there are many circumstances in which I'd just assume that malloc
succeeds.
It's still a stupid assumption, no matter how many times you make it.
At the very most, I might do something like:

#include <stddef.h>
#include <stdlib.h>

void *ExitiveMalloc(size_t const size)
{
void *const p = malloc(size);

if(!p) exit(EXIT_FAILURE);
Bye-bye user's data. Who cares?
>
return p;
}
Here's an example of where I'd be wreckless with malloc:
We have no shortage of examples of stupid code. Why add to the mess? And
your code is far from wreckless. Spelling flames for the sake of it are
lame, but the difference in meaning between "reckless" and "wreckless" is
significant.

--
Richard Heathfield
"Usenet is a strange place" - dmr 29/7/1999
http://www.cpax.org.uk
email: rjh at above domain (but drop the www, obviously)
Oct 3 '06 #50

83 Replies

This discussion thread is closed

Replies have been disabled for this discussion.