# Advanced Systems Lab - Spring 2026 This is the GitLab repository of **Group 70**. **Project topic:** Social Force Model for Pedestrian Dynamics The goal of this project was to implement and optimize Helbing's social force model for pedestrian dynamics. The final report includes the implementation details, performance analysis, and results of the work. This repository contains the C++ simulation code and Python visualization code used to generate and analyze the data. --- ## Results The logs of our benchmarks are stored inside the [`measurements`](./measurements/) folder. However, the log files contain incorrect flop counts since our benchmarking code assumed the same baseline flop count for all versions. Thus, we manually recalculated the flop count for each version and created helper functions for the correct flop counts inside the [`flopcounts`](./flopcounts/) folder. **The final, correct results are stored inside [`analysis/results_x86.csv`](./analysis/results_x86.csv).** [`variant_inlining_8.cpp`](./variants/variant_inlining_8.cpp) is our best non-vectorized version, while [`variant_float_inlining_SoA_AVX512_polyexp_moreavx_ilp_2_rsqrt_morersqrt_improved_moreilp.cpp`](./variants/variant_float_inlining_SoA_AVX512_polyexp_moreavx_ilp_2_rsqrt_morersqrt_improved_moreilp.cpp) is our best vectorized version. The measurements for the best non-vectorized version compiled with flags specifically disabling vectorization are stored at [`4.log`](./measurements/variant_inlining_8/x86/4.log), [`5.log`](./measurements/variant_inlining_8/x86/5.log), and [`6.log`](measurements/variant_inlining_8/x86/6.log). Additionally, the markdown files we have inside [`docs`](./docs/) are incomplete and outdated. Thus, **the final report [`70_report.pdf`](./70_report.pdf) should be used as the sole reference for all of our optimizations**. ## Requirements The project uses a `Makefile` to simplify building, running, benchmarking, testing, and visualization. Make sure `make` is installed: ```bash make --version ``` You also need a C++ compiler. The Makefile automatically uses `g++` if available, otherwise it falls back to `clang++`. Check your compiler with: ```bash g++ --version clang++ --version ``` The visualization script requires Python and the following packages: ```bash python3 -m pip install numpy pandas matplotlib ``` To generate MP4 videos, `ffmpeg` must also be installed. On Ubuntu/Debian: ```bash sudo apt update sudo apt install make g++ clang python3 python3-pip ffmpeg libgtest-dev python3 -m pip install numpy pandas matplotlib ``` On macOS: ```bash xcode-select --install brew install ffmpeg googletest python3 -m pip install numpy pandas matplotlib ``` --- ## Makefile commands The main commands are: ```bash make run ``` Runs the simulation and writes pedestrian states to a CSV file. ```bash make video ``` Runs the simulation and generates a visualization video. ```bash make run-bench ``` Compiles and runs benchmark measurements. All build commands accept a `VARIANT` parameter to select an optimization variant: ```bash make run-bench VARIANT=v1_cutoff N_P=100 N_ITER=10000 ``` The default is `VARIANT=baseline`. Each variant compiles its own binary (`main_baseline`, `main_v1_cutoff`, etc.). ```bash make bench-suite ``` Compiles once and runs benchmarks across multiple pedestrian counts (default: 50, 100, 200, 500, 1000, 2000, 5000, 10000 with 1000 iterations each). Redirect output to save results: ```bash make bench-suite > benchmarks/baseline.txt make bench-suite VARIANT=v1_cutoff > benchmarks/v1_cutoff.txt ``` Both `BENCH_SIZES` and `BENCH_ITER` can be overridden: ```bash make bench-suite BENCH_SIZES="100 500 1000" BENCH_ITER=500 ``` ```bash make test ``` Compiles and runs all unit tests. ```bash make verify ``` Runs the simulation with the reference parameters and compares the output to `reference/baseline_n60_i4000.csv` using `verify.py`. Useful to check that a variant gives the same result as the baseline: ```bash make verify VARIANT=v1_cutoff ``` ```bash make asm ``` Generates assembly files. ```bash make sizes ``` Compiles the helper executable used to inspect data-structure sizes. ```bash make clean ``` Deletes generated build files. ```bash make clean-all ``` Deletes generated build files and all `.csv` / `.mp4` outputs in the current directory. **Warning:** `make clean-all` removes all CSV and MP4 files in the directory. Move any output files you want to keep before running it. --- ## Default parameters The default simulation parameters are: ```text N_P=60 N_ITER=4000 CSV=positions.csv MP4=simulation.mp4 RANDOM_SEED=0 VARIANT=baseline ``` They can be overridden from the shell. Parameters can be provided selectively and in any order. Run the simulation with custom parameters: ```bash make run N_P=100 N_ITER=5000 CSV=my_positions.csv ``` Generate a video with custom output names: ```bash make video N_P=100 N_ITER=5000 CSV=my_positions.csv MP4=my_simulation.mp4 ``` Run benchmark measurements with custom parameters: ```bash make run-bench N_P=100 N_ITER=5000 ``` Use non-reproducible random initialization: ```bash make run RANDOM_SEED=1 ``` or: ```bash make video RANDOM_SEED=1 ``` By default, `RANDOM_SEED=0` uses a fixed seed for reproducible simulations and benchmarks. --- ## Building To compile the main executable: ```bash make main ``` This produces the executable: ```text main_baseline (or main_) ``` The Makefile uses the following compiler flags: ```text -O3 -march=native -std=c++23 -Wall -Wextra -flto ``` where: - `-O3` enables high-level optimization. - `-march=native` optimizes for the current machine. - `-std=c++23` uses the C++23 standard. - `-Wall -Wextra` enables useful compiler warnings. - `-flto` enables link-time optimization across `.cpp` files, allowing cross-file optimizations such as function inlining. --- ## Running the simulation The recommended way to run the simulation is: ```bash make run ``` This compiles the code and runs the simulation with the default parameters. It produces a CSV file containing pedestrian states at each saved time step. You can also run the executable manually after compiling: ```bash ./main_baseline [csv_output_path] ./main_ [csv_output_path] ``` Example: ```bash ./main_baseline 60 4000 positions.csv ./main_ 60 4000 positions.csv ``` The third argument is optional. If it is provided, simulation states are written to the given CSV file. --- ## CSV output The CSV file contains the pedestrian states used for visualization. The output columns are: ```text time,id,x,y,p.e.x,p.e.y,color ``` where: - `time` is the simulation time step. - `id` is the pedestrian index. - `x`, `y` are the pedestrian position coordinates. - `p.e.x`, `p.e.y` are the components of the desired direction. - `color` indicates the pedestrian group / walking direction. --- ## Visualization To run the simulation and directly generate a video: ```bash make video ``` This produces an MP4 file, by default: ```text simulation.mp4 ``` To visualize an existing CSV file manually: ```bash python3 visualization.py ``` Example: ```bash python3 visualization.py positions.csv simulation.mp4 ``` The generated video shows the pedestrian dynamics produced by the social force simulation. --- ## Benchmarking Run: ```bash make run-bench ``` This compiles the executable with benchmarking enabled and measures the simulation performance. On ARM/AArch64 machines, the Makefile automatically prepends `sudo` for benchmark compilation and execution because access to PMU performance counters may require elevated privileges. For reproducible benchmark results, keep: ```text RANDOM_SEED=0 ``` which is the default. Example: ```bash make run-bench N_P=100 N_ITER=5000 ``` The benchmark output includes estimated work, operational intensity, measured cycles, and estimated performance in flops per cycle. --- ## Optimization Variants The project supports multiple optimization variants through the `VARIANT` Makefile parameter. Each variant provides its own implementation of the force computations and simulation loop while sharing the same interface, benchmark harness, and test suite. The default variant is `baseline`: ```bash make run-bench # uses baseline make run-bench VARIANT=baseline # equivalent make run-bench VARIANT=v1_cutoff # uses a different variant ``` ### File naming convention Each variant consists of a single file in the project root: ```bash variant_.cpp # force computations and simulation loop ``` The file must implement the interfaces defined in `forces.hpp` and `social_force.hpp`. The baseline implementation is `variant_baseline.cpp`. ### Creating a new variant 1. Copy the baseline file: ```text cp variant_baseline.cpp variant_v1_cutoff.cpp ``` 2. Edit the new file with your optimization. 3. Build and test: ```bash make test VARIANT=v1_cutoff make run-bench VARIANT=v1_cutoff N_P=100 N_ITER=10000 ``` ### Verifying correctness A reference CSV is stored in `reference/baseline_n60_i4000.csv`. To check that a variant produces the same simulation output, run: ```bash make verify VARIANT=v1_cutoff ``` If the variant changes numerical results (e.g., distance cutoff skipping negligible forces), use a tolerance-based comparison (use the python script with a third argument (tolerance)) instead of exact diff and justify the deviation. --- ## Tests Run all unit tests with: ```bash make test ``` The tests use GoogleTest, so `libgtest-dev` or an equivalent GoogleTest installation must be available. The test target compiles and runs the unit tests for the simulation components. --- ## Assembly generation To generate assembly files for the currently selected VARIANT: ```bash make asm ``` This generates assembly output for the main source files, such as: ```text main.s forces.s social_force_baseline.s ``` This can be useful for inspecting compiler optimizations and generated instructions. --- ## Structure-size helper To compile the helper executable used to inspect data-structure sizes: ```bash make sizes ``` This produces: ```text sizes ``` Run it with: ```bash ./sizes ``` --- ## Cleaning generated files Remove generated build files: ```bash make clean ``` This deletes files such as: ```text main_* sizes run_tests *.o *.s ``` Remove build files and generated CSV/MP4 outputs: ```bash make clean-all ``` This deletes: ```text main_* sizes run_tests *.o *.s *.csv *.mp4 ``` **Warning:** `make clean-all` deletes all `.csv` and `.mp4` files in the current directory. Move any files you want to keep before running it. --- ## Notes on reproducibility By default, the simulation uses a fixed random seed: ```text SEED=42 ``` This makes simulation runs reproducible. To use non-reproducible initialization, run: ```bash make run RANDOM_SEED=1 ``` or: ```bash make video RANDOM_SEED=1 ``` For benchmarking, reproducible initialization is recommended, so the default `RANDOM_SEED=0` should normally be kept. --- ## Example workflow Compile and run the simulation: ```bash make run ``` Generate a video: ```bash make video ``` Run tests: ```bash make test ``` Run benchmark measurements: ```bash make run-bench ``` Clean generated build files: ```bash make clean ``` Clean everything generated, including CSV and MP4 outputs: ```bash make clean-all ```