What Is a Segmentation Fault?
A segmentation fault, or segfault, is a crash that happens when a program tries to read or write memory it is not allowed to access, such as address 0 through a null pointer. The operating system stops the program with the SIGSEGV signal.
Updated September 24, 2026
A C program prints its first line and then stops with a message nobody wrote:
#include <stdio.h>
int main(void) {
int *score = NULL;
printf("About to read the score\n");
printf("Score: %d\n", *score);
return 0;
}
About to read the score
bash: line 1: 64030 Segmentation fault: 11 ./seg
That output is from bash on macOS, where 64030 is the process ID and 11 is the signal number. On Linux the same crash usually reads Segmentation fault (core dumped). Either way, the program never printed the score. score holds address 0, and *score asks the processor to read the memory at that address, which no program is allowed to do.
How a segmentation fault happens
Every program runs in its own virtual address space, a huge range of addresses that the operating system fills in piece by piece. It maps the program's code, its global variables, its stack and its heap into that range, in blocks called pages (4 KB on most x86 Linux systems, 16 KB on Macs with Apple silicon). Most addresses are left unmapped, and address 0 is always among them so that null pointer bugs are caught.
- The program executes an instruction that reads or writes an address. Here it is the read of
*score, address 0. - The processor's memory management unit looks the address up in the page table. The page is not mapped, or the program is trying to write to a page that is read-only.
- The processor stops the instruction and hands control to the kernel with a page fault.
- The kernel checks whether the access could be legal, for example a stack that needs to grow. It is not, so the kernel sends the process signal 11,
SIGSEGV. - The default action for
SIGSEGVis to end the process and, when the system allows it, save a core dump. The shell then prints the message and sets the exit status to 139, which is 128 plus the signal number.
So a segmentation fault is not reported by the compiler, and it is not an exception the language raises. It is the hardware and the kernel protecting memory, which makes it a runtime error of the most abrupt kind. Windows handles the same event as an access violation, exception code 0xC0000005.
Common causes of segmentation faults
C and C++ let a program compute any address and use it, so the causes come down to using an address that is not valid.
- Dereferencing a null pointer.
int *p = NULL; *p = 5;A function that returnsNULLon failure, such asmallocorfopen, leads here when its result is not checked. - An index far past the end of an array. C does not check bounds, so
arr[1000000]is simply an address a million elements further on. - Using memory after
free. The pointer still holds the old address, but the memory no longer belongs to you. - An uninitialized pointer.
int *p; *p = 5;writes through whatever garbage valuephappens to hold. - Stack overflow. A recursive function with no stopping case keeps adding stack frames until it runs off the end of the stack. The example below crashed on macOS with
Segmentation fault: 11and exit status 139. - Writing to a string literal.
char *name = "coddy"; name[0] = 'C';tries to change read-only memory. On Linux that is a segfault. On macOS the same program stopped withBus error: 10, a related signal.
#include <stdio.h>
int depth(int n) {
return depth(n + 1) + 1; /* never stops calling itself */
}
int main(void) {
printf("%d\n", depth(0));
return 0;
}
A small mistake often does not crash at all, which makes it more dangerous. This loop reads one element past the end of a three-element array:
#include <stdio.h>
int main(void) {
int scores[3] = {72, 88, 95};
int total = 0;
for (int i = 0; i <= 3; i++) { /* <= reads scores[3] */
total += scores[i];
}
printf("Total: %d\n", total);
return 0;
}
Compiled with Clang on a Mac, it printed Total: 256. The correct total is 255. scores[3] was the next 4 bytes of the stack, which belonged to the program, so no fault occurred and the garbage value was added silently. The operating system only stops accesses to memory the program does not own at all.
The fix for both mistakes is the same habit: know how many elements there are, and check a pointer before you follow it.
Best: 95
No scores, nothing to read
What "core dumped" means
A core dump is a file that holds a copy of the program's memory at the moment it crashed. A debugger can open it later and show exactly where the program was and what its variables held: gdb ./app core. On many Linux distributions, systemd-coredump collects these files, and coredumpctl list shows them. When core dumps are turned off, for example with ulimit -c 0, the message is just Segmentation fault, without the words in parentheses.
How to find the line that crashed
The line where the program crashes is often not the line with the bug. A pointer can become invalid in one function and be used in another much later. These tools show both.
A debugger. Compile with debug information and run the program inside the debugger. When it stops, bt (backtrace) prints the chain of function calls with file names and line numbers. On Linux the debugger is usually gdb; on macOS it is lldb, where bt works the same way.
gcc -g app.c -o app
gdb ./app
(gdb) run
(gdb) bt
AddressSanitizer. Compile with -fsanitize=address (GCC and Clang both support it) and run the program normally. Instead of a bare segfault, it prints a report that names the kind of mistake, such as heap-use-after-free or stack-buffer-overflow, with the line that made the access and the line that allocated the memory. It also catches the quiet one-past-the-end read above, which never crashes on its own.
Valgrind. On Linux, valgrind ./app runs an unmodified program and reports every invalid read or write, such as Invalid read of size 4.
Segmentation faults in other languages
Python, Java and JavaScript check every index and every reference before using it, so the same mistakes become exceptions with clear messages: IndexError or AttributeError in Python, ArrayIndexOutOfBoundsException or NullPointerException in Java, TypeError in JavaScript. Those can be caught with exception handling. A segfault cannot be handled that way: it is a signal, and a C++ catch block does not see it.
Python programs can still segfault when C code fails underneath them. This line asks ctypes to read address 0:
import ctypes
ctypes.string_at(0)
Run with python3 -X faulthandler, Python 3.12 printed Fatal Python error: Segmentation fault, followed by the Python lines that were running. The same crash happens when a C extension or a native library has a memory bug. Rust takes a different approach: its compiler rejects most code that could access invalid memory before the program is built.
Where to go next
The C guide to segmentation faults walks through each cause with a minimal program and its fix. To avoid the mistakes in the first place, read about pointers, null pointers and the stack and the heap, then practice them in the C course. For how errors are reported in languages that check memory for you, see the runtime error page.
Frequently Asked Questions
How do you fix a segmentation fault?
-g and run the program under gdb or lldb, then type bt after the crash, or compile with -fsanitize=address for a detailed report. Then fix the pointer or index that line uses: check pointers for NULL, keep array indexes below the length, stop using memory after free, and make sure recursion ends.Is a segmentation fault a memory leak?
free, such as using a pointer after freeing it, can cause segfaults, while forgetting free causes leaks.Why is it called a segmentation fault?
SIGSEGV, stayed. Windows calls the same event an access violation.Can Python have a segmentation fault?
ctypes. Running python -X faulthandler script.py prints the Python lines that were running when it crashed.What does exit code 139 mean?
SIGSEGV, a segmentation fault. Shells report a death by signal as 128 plus the signal number, and 128 + 11 = 139. In Docker and Kubernetes, a container that exits with 139 had its main process segfault.