Re: Learning C



On 2006-03-12, Nick Keighley <nick_keighley_nospam@xxxxxxxxxxx> wrote:

no. Put an assert() in. A modified variable is just for today. An
approriate
assert() lasts forever. Next year when someone casts doubt on the same
function, you simply look at the func() source code and say "nope,
can't
be a divide by zero because there's an assert() to check for that". Fix
it
once, never touch it again.

Thats not the example I gave. I gave the example to force the divide
by zero error : with no added code which changes the footprint between
runtime and debug models. To expand a bit, I might want to check a
deeply embedded function can handle an integer limit or a null
pointer. One very important issue
here is that I dont do this all the time - only when its deep in a
system where a quick glance cant quarentee the absence of such
"limits". I might want to call "convertBitmap()" with option 3 for GIF
since the test data framework didnt incude that option. Or 6 which is
not yet implemented.

Bottom line is that also, some systems dont want to exit : they want
to handle the assert condition more generously. assert is one up from
printf mind you. At least you can compile it out without running
around changing all your source. Not that I agree with code footprint
which is different between "real" and "development".

Also, how many times have we found

assert(a++);

as opposed to "assert(a);a++" in some remote rarely called routine?

Bad? Yes. But *** happens.

If what you want is required then yes, an assert is useful.


a debugger war is much more fun...


It can be.. (ps this is far from OT : it is about using C language mechanisms
for debugging aid which overrule the need for a HW/SW debugger). If it
was in the std group then yes.


<snip>

Maybe I'll even get my debugger out and step through a program
sometime to see if it brings me any insights. Maybe you should try
a "debugger free day" and try and see what you have to do to manage
without. Try reasoning about the program. Consider invariants and
post/pre conditions. Try adding asserts etc.

If you recall I did mention that a home brew logging system is
prefential to printf :

where did the words "homebrew logging system" appear in the paragraph
above? I did write a fairly blunt paragraph here. And then thought
better of it. Do you know what an invarient is? Design by contract?

I used those words. Its when you wrap whatever underlying logging system is
convenient to you in a fairly generic calling interface : so you could
log to files, text consoles, window systems whatever without changing
the calling code.

I note you didn't say if you knew what "Design by Contract" meant.


It has nothing to do with what I am advocating here. And so I wont get
dragged into a terminology war. I'm not talking about designing
anything here. And if I wanted to bluff, google is a mere keypress away
:-;

Remember that the crux of this is that I'm saying it can be
advantageous for someone wanting to familiarise themself with a system
to see it runing under a good debugger. You claimed this as "bizarre".

<snip>

A debugger isnt the only tool : and I never said it was. What it
can do is allow you to see the flow of an application while watching
live data, allow you to modify that data

never felt the need. Not since compilers got fast enough to run during
the day.

I really dont understand this. What has that got to do with a debugger?

I've modified variables using the debugger (the "debugger" actually had

toggle switches...) when the run time of the compiler was significant.
If it
took hours to recompile your code then machine code patches and
register
hacking was acceptable. It is no longer necessary (well, sometimes).


You must work on very small systems. I would never counter someone
modifying code here there and everywhere to *find* a bug when you can
get the same effect in less time without modifying the code.

What are toggle switches? What is a machine code patch in this
context? I would rarely advocate register hacking : the whole point of
a debugger is that it gives symbolic access to your system variables
and messing with registers is not required.

<snip>

and to examine and ensure
data typing is consistant from skillful use of register/pointer/memory
examinations : it is why they exist.

you examine registers? On a deeply embedded system, ok. But a
server?

I also mentioned memory and pointers. And yes I do. Very useful in
debugging big C systems.

wow. Culture Shockville. To my shame I couldn't even tell you what
registers
my platform has without STFWing. Ok that's a project for today.

<snip>

The whole crux here is you doubting
that stepping an existing app can help a user understand it : after
many, many and varied projects on various platforms in various
languages I find it incredulous how you could doubt this would be
beneficial. In order to even put in these printfs() you need some
understanding of whats going :

<snip>

I'd say the same went (in spades) for stepping. You've got to know
where
to step. There's source code, case tools, source browsers, source code.
I've even resorted to grep to find callers of functions.

grep is ok : if I dont have a decent IDE I use something like emacs
tags. I have used grep in about 15 years :)

ok it's a tool of desparation. You * never* use grep?!


I used it today to find where a certain daemon was in a boot hierarchy
: nice.

OK, lets call it a day.

<snip>


--
Nick Keighley

Testing can show the presense of bugs, but not their absence.
-- Dijkstra

.


Quantcast