C Error Handling
Error Handling in C
Error handling lets you detect and respond to problems in your program, like a file that can't be opened or memory that can't be allocated, so your program doesn't crash or behave unexpectedly.
Unlike some languages, C does not have built-in exception handling (like try/catch). Instead, C uses return values, global error codes, and helper functions like perror()
and strerror()
.
Using Return Values
In the previous chapter, you learned that functions like fopen()
return NULL
when something goes wrong.
You can check for NULL
using an if
statement to detect and handle errors before your program crashes.
In the example below, we try to open a file that does not exist. Since fopen()
fails, it returns NULL
and we print an error message:
Example: fopen() fails
#include <stdio.h>
int main() {
FILE *fptr = fopen("nothing.txt", "r");
if (fptr == NULL) {
printf("Error opening file.\\n");
return 1;
}
fclose(fptr);
return 0;
}
Result:
Error opening file.
Get More Details
If you want more details about what went wrong, you can use the perror()
function.
It prints a custom error message followed by a description of the last error that occurred:
Example: perror() with fopen()
#include <stdio.h>
int main() {
FILE *f = fopen("nothing.txt", "r");
if (f == NULL) {
perror("Error opening file");
return 1;
}
fclose(f);
return 0;
}
Result:
Error opening file: No such file or directory
Using strerror() and errno
errno
is a global variable that stores the error code from the last failed operation. You can include <errno.h>
to access it, and strerror(errno)
will convert the error code into a readable message:
Example: strerror()
#include <stdio.h>
#include <errno.h>
#include <string.h>
int main() {
FILE *f = fopen("nothing.txt", "r");
if (f == NULL) {
printf("Error: %s\n", strerror(errno));
return 1;
}
fclose(f);
return 0;
}
Result:
Error: No such file or directory
Common Error Codes
Error constants are defined in <errno.h>
. You can compare errno
to them to detect specific issues:
Error Code | Meaning |
---|---|
ENOENT | No such file or directory |
EACCES | Permission denied |
ENOMEM | Not enough memory |
EINVAL | Invalid argument |
Example: Custom message for ENOENT
#include <stdio.h>
#include <errno.h>
int main() {
FILE *f = fopen("nothing.txt", "r");
if (f == NULL) {
if (errno == ENOENT) {
printf("The file was not found.\n");
} else {
printf("Some other file error occurred.\n");
}
return 1;
}
fclose(f);
return 0;
}
Result:
The file was not found.
Using exit() to Stop the Program
If you want to stop the program immediately when an error occurs, you can use exit()
.
It lets you return a status code to the operating system.
Exit codes help signal whether the program finished successfully or with an error, like:
0
means success- Non-zero values (like
1
orEXIT_FAILURE
) indicate errors
Example: Using exit() on error
#include <stdio.h>
#include <stdlib.h>
int main() {
FILE *f = fopen("nothing.txt", "r");
if (f == NULL) {
printf("Failed to open file.\n");
exit(1);
}
fclose(f);
return 0;
}
Result:
Failed to open file.
Common Exit Status Codes
Code | Meaning |
---|---|
0 | Success - the program completed normally |
1 | Error - something went wrong |
EXIT_SUCCESS | Same as 0 (defined in <stdlib.h> ) |
EXIT_FAILURE | Same as a non-zero error code (also in <stdlib.h> ) |
Tip: You can use EXIT_SUCCESS
and EXIT_FAILURE
instead of numbers to make your code more readable.
Example: Using EXIT_FAILURE and EXIT_SUCCESS
#include <stdio.h>
#include <stdlib.h>
int main() {
FILE *f = fopen("nothing.txt", "r");
if (f == NULL) {
perror("Could not open nothing.txt");
exit(EXIT_FAILURE); // More readable than exit(1)
}
fclose(f);
return EXIT_SUCCESS;
}
Result:
Could not open nothing.txt: No such file or directory
Summary
- Many C functions return
NULL
when something goes wrong - Use
perror()
to print a message about the error - Use
strerror(errno)
to get the error message as a string errno
stores the error code from the last failed action- You can compare
errno
to values likeENOENT
(file not found) orENOMEM
(not enough memory) - Use
exit()
to stop the program early if there's an error
Tip: Always check for errors after file operations, memory allocation, and system calls. Ignoring errors can lead to unexpected behavior or crashes.