Table of contents:
1. Look at your output:
If your output says
then you have probably interchanged some variables in your program. Your
program may also say something like
This was the result of having an integer (4 bytes in this case) and
a double precision floating-point variable (8 bytes) in the wrong
order as arguments to a
Incidentally, the two lines aboves were output from the C program
2. Always run your compiler with warning messages!
If you were using the MinGW C compiler, and compiled the C program above
as
and then ran
then you would get several warning messages about
A more insidious example is the C program
which had output
The reason for this curious output is that `xx' is initialized at 7
(so that xx=7 until it is changed), but the variable in the second
However, if you had compiled this program as
then you would have gotten a warning message that `xx' was given a value
but that value was never used. The latter suggests that you made an error
of exactly this sort.
there would have been absolutely no warning or error messages.
3. Signals and math exceptions.
Another type of error is illustrated in the C program
In C, text strings are handled as pointers to arrays of variables of type
Crashing program bugs:
The first two statements above are called range errors (for obvious
reasons). The third is an overflow error, since exp(500000) is too large
to store in a double-precision floating point number. The opposite
condition
does not generally cause any problem: The computer normally replaces
w by 0.0 and proceeds, although there may be problems later if
you say 1/w. (A command like exp(-500000) is called an underflow, in
contrast to exp(500000), which causes an overflow.)
Treatment of math exceptions: By convention, modern C
compilers handle math exceptions without program interruptions. The
resulting floating-point numbers is replaced by what are called Infs
(standarding for ``infinities'') or NaNs (standing for ``Not a Number'').
Any further numerical operation on an Inf or NaN produces another Inf or
NaN. When you try to display an Inf or NaN in a print statement, it shows
up in computer output as something like #INF or #IND (the latter for
Indefinite).
Redirecting signals: The problem remains of how to handle
serious signal errors such as segmentation faults. You can get rid of the
irritating drop-down windows for these signals, or for most of them, by
``installing your own signal handler''. An example of how to do this is
given in the following program.
The main() program above shows two apparent problems. The first print
statement has a division-by-zero error in computing miles per gallon.
However, in most modern C compilers, this generates a NaN instead of
an unhandled exception. The program displays #INF for miles per gallon
and proceeds. (The older Borland C Vs. 5.0 compiler generates an
FPE signal error at this point.)
NOTE If you include the file
in your program, in place of Step III. (Note this is
Last modified April 30, 2007printf
function (see below). The
program treated the first four bytes of the 8-byte floating-point as if
it were an integer and then took the remaining eight bytes --- the last
four bytes of the double plus the following integer --- as a
floating-point number, with the resulting disfunctional display.
c_what1
, you would get the output above with no
warning. However, if you had compiled the program using
printf
arguments not matching the variables in its format string. These would
have been a clue to fix the printf statements. (Incidentally, the
-W
in -Wall
stands for
Warning
and all
for All, so that
-Wall
is not a reference to a real wall.)
printf
statement is x, not xx. In this case, x was declared
but not initialized, and that location in memory happened to have the
value 2 when the program was run. This sort of error is hard to
detect and can occasionally cause believable but highly incorrect
results.
printf
statement) without being initialized
(which gcc
should also have said). However, either warning
message should be taken as a clue that something potentially serious is
wrong.
char
(usually one byte each) that end with a zero byte. In
this case, the compiler creates an array of 6 bytes that has Hello as its
first 5 characters and then 0 to end the text string. The program then
stores the address of this array in the variable str
.
printf
function sees %s
in its
format string and str
in its argument list, it fetches the
characters at that address and adds them to the printed output. The
output from this line will be
%s
in the second printf
statement also
tells the computer to look for an array of char
s for text,
but tells it to look at the literal address xx=17 in your computer instead
of at the address of a well-defined string.
float.h
that must be part of any
standard C installation.
signal.h
. The
switch statement in my_signal_handler() tells the program to jump to the
`case SIGSEGV' label and then execute code until the
break;
statement. At that point, it exits the switch
statement and takes the opportunity to nag you further in another print
statement.
exit(1);
at the end of the signal handler is
exactly equivalent to return 1;
at the end of the
main()
function. In particular, the program exits gracefully
with an error code of 1. A normal program exit (either at the end of
the main() function or in an exit(0) call) indicates that the program has
completed its tasks without any errors. Any exit()
call
guarantees that all print and file buffers are flushed and that all files
are properly closed.
exit(1);
command in my_signal_handler() is likely to be
compiler dependent, but it will probably be unpleasant.
statlib.c
on the
Math408 Web site in your program, as well as the header filestatlib.h
, then you can install essentially the same signal
handler in your program by putting the single command
set_newsignals();
set_newsignals()
, not set_mysignals()
.) Then
leave out Steps I, II, and IV above. (That is, you can leave out the
code for my_signal_handler()
and
set_mysignals()
.) The necessary prototypes are in
statlib.c
and statlib.h
, and the code for
set_newsignals()
and the signal handler itself are in
statlib.c
.