The Problem
Mobile researchers need a reliable way to capture and analyse low‑level cellular traffic on iOS devices. Existing tools either require jail‑breaks or provide only raw packet dumps, leaving analysts to build their own parsers and visualisations.
What This Does
CellGuard bundles an iOS app, a kernel‑level tweak, and a Rust extension to collect baseband packets (QMI/ARI) and present them in a UI. The Swift front‑end lives in CellGuardAppSwift/ (258 files) and drives the user experience, while CellGuardAppRust/ (3 source files) implements high‑performance CSV parsing in src/lib.rs. The data‑export pipeline is exercised by the Python helper CellGuardAppSwift/generate_operators.py, which contacts the CellGuard backend to fetch operator metadata.
Key artefacts:
CellGuardAppSwift/CellGuard/CellGuardApp.swift– application entry point for iOS.CellGuardAppRust/src/lib.rs– public Rust library exposingparse_csvused by the Swift bridge.CapturePacketsTweak/– Objective‑C tweak that injectsCPTClient/CPTCollectorinto the baseband stack to capture raw packets.AnalyzeCells/analyze_cells2.py– offline script that processes exported CSV datasets.
How It Is Wired
Execution starts when iOS launches CellGuardAppSwift/CellGuard/CellGuardApp.swift. The app initialises the StudyClient (in API/StudyClient.swift) which contacts the remote API (see API/CellGuardURLs.swift). On first launch the client triggers generate_operators.py (invoked via a Swift Process call) to download operator lists; the script performs an HTTP request without a timeout (see Code Health finding).
Captured packets flow from the injected tweak (CapturePacketsTweak/CPTClient.swift) into the Swift parsers under CellGuard/Tweaks/Capture Cells/ (AriCellParser.swift, QmiCellParser.swift). Each parser hands parsed records to the Rust library through the Swift‑Rust bridge (CellGuardAppRust/src/lib.rs). The Rust code converts the structures into CSV files stored in the app’s sandbox (PersistenceCSVExporter.swift).
The UI layer (User Interface/…/*.swift) reads the persisted Core Data model (Core Data/Objects/Packet*.swift) and renders tables, maps, and verification views. No internal module imports were detected in the static import graph, and the four most‑connected modules (analyze_cells2, build_ipa, generate_ari_json, generate_operators) have zero inbound/outbound import edges, indicating a largely decoupled code base but also a lack of explicit module wiring.
How To Use It
# Clone the repository
git clone https://github.com/moses-y/CellGuard.git
cd CellGuard
# Build the Swift app (requires Xcode)
make -C CellGuardAppSwift # invokes the Makefile that runs xcodebuild
# Build the Rust extension
cargo build --manifest-path CellGuardAppRust/Cargo.toml
# Run the Python analysis script (requires Python 3.11+)
uv sync --project-dir AnalyzeCells # uses pyproject.toml / uv.lock
python AnalyzeCells/analyze_cells2.py <exported_csv>
No Dockerfile, no explicit environment‑variable list, and no secret files are present. The only required runtime artefact is an iOS device (or simulator) where the tweak can be installed via the provided .xcodeproj.
Real‑World Use
A security lab can install the tweak on a test iPhone, run the app to collect baseband traffic in a controlled cell‑tower environment, export the CSV via the UI, and feed the file to AnalyzeCells/analyze_cells2.py to generate a report of suspicious base‑station behaviour.
Code Health & Issues
- HIGH – Add a test suite – 211 source files, no test files.
- MEDIUM – Enable Dependabot/Renovate – three manifest files (
Cargo.toml,pyproject.toml) lack an update bot. - MEDIUM – Outbound request timeout missing –
CellGuardAppSwift/generate_operators.pymakes HTTP calls without atimeout=argument. - LOW – Add repository convention files – missing
.editorconfig,.gitattributes, and formatter config.
- HIGH – Deep nesting – 59 occurrences of indentation depth ≥ 10 in files such as
LogArchiveReader.swift,TweakClient.swift,OperatorDetailsView.swift. Refactor with early returns or guard clauses. - HIGH – Duplicated code blocks – ~99 repeated 6‑line blocks across 41 files (e.g.,
CGVerificationPipeline.swift,SNVerificationPipeline.swift,AriCellParser.swift,QmiCellParser.swift). Extract shared helpers to reduce duplication.
The Bottom Line
CellGuard delivers a full iOS‑centric pipeline for capturing and analysing cellular baseband traffic, but the code base suffers from excessive nesting, duplicated parsers, and a complete lack of automated tests. It is suitable for research teams comfortable navigating Swift‑Objective‑C‑Rust interop, yet would require substantial refactoring and test coverage before production‑grade deployment.