A systems programming project in C that simulates a simplified operating system memory management environment with multiple processes, an MMU, a simulated hard disk, page faults, eviction, and synchronized memory snapshots.
This project demonstrates how core virtual memory concepts can be modeled using processes, threads, inter-process communication, and synchronization primitives.
- Language: C
- Concurrency: processes, threads, mutexes, condition variables
- System Concepts: memory management, page faults, eviction, MMU behavior, disk access simulation, synchronization
The simulator models a simplified memory-management system made of:
- two CPU processes that generate memory access requests
- a Memory Management Unit (MMU) that handles hits, misses, and page replacement
- a simulated Hard Disk (HD) that serves read/write requests
- periodic memory snapshots that show the current state of memory
The goal of the project is to simulate how a memory subsystem behaves under concurrent access and limited memory capacity. :contentReference[oaicite:1]{index=1}
- multi-process simulation of CPU memory access
- MMU logic for handling hits and misses
- simulated hard-disk read/write operations
- page eviction when memory becomes full
- FIFO clock-style eviction policy
- printer thread for consistent memory snapshots
- synchronization using mutexes and condition variables
- configurable timing and workload parameters
The simulation includes four main components:
The first CPU process runs in a loop and periodically generates memory access requests.
Its behavior includes:
- waiting for a configured time interval
- choosing between read and write access
- sending a request to the MMU
- waiting for acknowledgment
- repeating continuously during the simulation window
The second CPU process behaves the same way as the first one.
Using two CPU processes makes it possible to simulate concurrent memory access and contention between multiple request sources. :contentReference[oaicite:2]{index=2}
The MMU is the central component of the system.
It manages a memory array of pages and is responsible for:
- handling incoming memory access requests
- determining whether each access is a hit or a miss
- triggering disk access when needed
- marking pages as valid, invalid, clean, or dirty
- invoking page eviction when memory pressure becomes too high
The MMU includes three internal threads:
- Main Thread – processes incoming access requests
- Evicter Thread – frees memory using a FIFO clock-style policy
- Printer Thread – periodically captures consistent snapshots of memory state :contentReference[oaicite:3]{index=3}
The hard disk module simulates secondary storage.
It handles page read/write requests from the MMU and responds after a configured access delay, representing the slower behavior of disk compared to memory. :contentReference[oaicite:4]{index=4}
A typical simulation flow looks like this:
- CPU processes generate read/write requests
- requests are sent to the MMU
- the MMU checks whether the target page is already in memory
- on a hit, the MMU responds directly
- on a miss, the MMU interacts with the simulated hard disk
- if memory is full, the evicter thread removes pages according to the policy
- the printer thread periodically prints a memory snapshot
- the simulation ends after the configured runtime
The simulator models memory as an array of pages.
Each page may have a status such as:
- valid or invalid
- clean or dirty
This allows the simulation to represent key memory-management events such as:
- page insertion
- page replacement
- dirty-page write-back
- memory pressure and eviction behavior :contentReference[oaicite:5]{index=5}
When the number of used slots grows too high, the evicter thread begins reclaiming memory.
The project uses a FIFO clock-style eviction policy, which balances simplicity with realistic page replacement behavior in the simulation. :contentReference[oaicite:6]{index=6}
This project focused on simulating operating-systems behavior rather than building an end-user application.
Key implementation areas included:
- concurrent CPU request generation
- MMU request handling logic
- hit/miss processing
- simulated hard-disk interaction
- eviction control under memory pressure
- printer thread synchronization for safe snapshots
- process/thread coordination and cleanup
- careful synchronization to avoid race conditions and deadlocks
This project demonstrates practical understanding of:
- virtual memory concepts
- page faults and eviction
- concurrency with processes and threads
- synchronization in systems programming
- coordination between compute and storage components
- simulation of operating-systems behavior in C
It is a strong systems project because it combines multiple low-level concepts in one design: memory management, concurrency, synchronization, and inter-component communication.
Clone the repository:
git clone https://github.com/your-username/memory-management-simulation.git
cd memory-management-simulationCompile the project:
makeRun the simulation:
./simulateModify simulation parameters in config.h, including values such as:
INTER_MEM_ACCS_TWR_RATEMEM_WR_THIT_RATEHD_ACCS_TSIM_TIMEUSED_SLOTS_TH:contentReference[oaicite:7]{index=7}
- memory management
- MMU simulation
- page faults
- page replacement
- dirty vs. clean pages
- processes and threads
- mutexes and condition variables
- synchronization
- systems programming in C
Through this project, I strengthened my understanding of:
- how memory subsystems behave under concurrent access
- how MMU-style logic handles hits, misses, and disk access
- how eviction policies affect system behavior
- how to coordinate processes and threads safely
- how to design systems simulations that reflect operating-system concepts
Possible next steps for the project:
- add more eviction policies for comparison
- collect and visualize hit/miss statistics
- log page-fault and eviction events in more detail
- extend the simulator to model virtual addresses more explicitly
- add performance measurements across different parameter settings
- document the internal message flow between components more clearly