Back to C Programming
2026-07-155 min read

C - Memory Layout

Learn C - Memory Layout step by step with clear examples and exercises.

Why This Matters

Welcome to this full guide on C Memory Layout! In this lesson, we will delve into how memory is organized and managed in the C programming language. This knowledge is essential for understanding various aspects of C programming, from debugging complex programs to optimizing memory usage.

Why This Matters

Understanding memory layout in C is crucial for several reasons:

  1. Debugging: Knowing how variables are stored in memory can help you identify and fix bugs more efficiently.
  2. Optimization: By understanding memory allocation, you can write more efficient code that uses resources effectively.
  3. Interviews: Familiarity with C memory layout is often a requirement for advanced programming positions, especially those involving system programming or low-level development.
  4. Real-world bugs: Memory-related issues are common in C programs, and being able to diagnose and fix them is an essential skill for any C programmer.

Prerequisites

To fully appreciate this lesson, you should have a good understanding of the following topics:

  1. Basic C syntax, including variables, data types, and operators
  2. Control structures (if-else, loops)
  3. Functions and function calls
  4. Pointers and arrays

Core Concept

In C, memory is a continuous sequence of bytes that can be used to store data. The memory space is divided into several sections:

  1. Stack: Used for storing local variables, function call frames, and other temporary data. The stack grows towards lower addresses (downwards).
  2. Heap: A region of memory where dynamically allocated memory resides. You can allocate and deallocate memory from the heap using functions like malloc(), calloc(), free(), etc.
  3. Global/Static variables: Variables declared outside of any function are stored in the data segment, which is part of the global memory space. These variables persist for the lifetime of the program.
  4. Text segment (Code Segment): Contains the executable code of the program.

Stack and Local Variables

When a function is called, a new stack frame is created on the stack. This frame contains information about the function's local variables, parameters, and return address. The memory allocated for each variable in the stack frame is deallocated when the function returns.

void exampleFunction() {
int x = 10; // x is stored on the stack
}

Heap Allocation

The heap is used to dynamically allocate memory during runtime. When you call malloc(), it allocates a block of memory from the heap and returns a pointer to that block. To free the allocated memory, you can use free().

int main() {
int *ptr = (int *) malloc(sizeof(int)); // Allocate memory for an integer on the heap
*ptr = 20; // Store a value in the allocated memory
free(ptr); // Deallocate the memory when it's no longer needed
}

Global and Static Variables

Global variables are stored in the data segment, which is part of the global memory space. These variables persist for the lifetime of the program. When multiple functions access a global variable, they all share the same memory location.

Static variables behave similarly to global variables but have a more limited scope. They are initialized only once during the first call of their containing function and retain their values between function calls.

int global_var = 10; // Global variable

void exampleFunction() {
static int x = 20; // Static variable
}

Worked Example

Let's consider a simple C program with local and global variables, as well as heap allocation.

#include <stdio.h>
#include <stdlib.h>

int global_var = 10; // Global variable

void exampleFunction() {
int x = 20; // Local variable on the stack
printf("Local var: %d\n", x);
}

int main() {
int *ptr = (int *) malloc(sizeof(int)); // Allocate memory for an integer on the heap
*ptr = 30; // Store a value in the allocated memory
printf("Heap-allocated var: %d\n", *ptr);
exampleFunction(); // Call the function with a local variable
printf("Global var: %d\n", global_var);
free(ptr); // Deallocate the heap memory when it's no longer needed
}

Common Mistakes

  1. Stack overflow: When too much data is pushed onto the stack or a function recurses too deeply, the stack may run out of space, leading to a stack overflow error.
  2. Heap leaks: Failing to deallocate heap memory when it's no longer needed can result in a memory leak.
  3. Dangling pointers: Accessing memory after it has been freed or reallocated can lead to undefined behavior, known as a dangling pointer error.
  4. Misaligned pointers: Incorrectly aligning pointers can cause alignment errors and may affect performance.
  5. Memory fragmentation: Frequent allocation and deallocation of small memory blocks can result in memory fragmentation, reducing the efficiency of memory usage.

Practice Questions

  1. Write a C program that demonstrates stack overflow by recursively calling a function too many times.
  2. Implement a simple memory leak by allocating heap memory but not freeing it.
  3. Write a program that demonstrates dangling pointer behavior by accessing freed memory.
  4. Explain how you would use the calloc() function to allocate an array of integers on the heap.
  5. What is the difference between local, global, and static variables in C?

FAQ

  1. Why do I get a segmentation fault when accessing memory that should be valid?

A segmentation fault usually indicates that you are trying to access memory that has not been allocated or that has already been freed. Make sure to check your pointers for null values and verify that the memory is still in use before accessing it.

  1. What is the difference between stack and heap memory?

Stack memory is used for local variables, function call frames, and other temporary data. It grows towards lower addresses (downwards). Heap memory is a region of memory where dynamically allocated memory resides. You can allocate and deallocate memory from the heap using functions like malloc(), calloc(), free(), etc.

  1. What happens to global variables when a function returns?

Global variables persist for the lifetime of the program, so they are not affected by function calls or returns.

  1. Why can't I allocate an array of integers using malloc() directly?

When you use malloc() to allocate memory for an array, you should divide the total size of the array by the size of each element and pass that value as the argument. For example:

int *arr = (int *) malloc(sizeof(int) * 10); // Allocate memory for an array of 10 integers on the heap
  1. What is the purpose of the free() function in C?

The free() function is used to deallocate dynamically allocated memory from the heap, freeing up that memory for other uses. It's essential to call free() when you no longer need the allocated memory to avoid memory leaks.