LibAFL - Framework di Fuzzing Modulare Cheatsheet
LibAFL è un framework di fuzzing, non un fuzzer. Scritto in Rust dal team AFL++, fornisce blocchi costruttivi componibili — observer, feedback, mutatori, scheduler, stage, executor — che assembli in un fuzzer adatto al tuo target. La motivazione è che i fuzzer monolitici funzionano bene su target convenzionali e male su quelli insoliti (protocolli custom, firmware emulato, kernel, grammatiche), dove finisci per combattere il tool. Con LibAFL costruisci esattamente il fuzzer di cui il target ha bisogno, e ottieni scaling multi-core gratuitamente.
Costruire un fuzzer è più lavoro che eseguirne uno. Ricorri a LibAFL quando i tool out-of-the-box genuinamente non si adattano.
Setup
| Passo | Comando |
|---|
| Nuovo progetto | cargo new my_fuzzer && cd my_fuzzer |
| Aggiungi LibAFL | cargo add libafl libafl_bolts |
| Strumentazione del target | cargo add libafl_targets (o libafl_qemu, libafl_frida) |
| Costruisci | cargo build --release |
Concetti Principali
| Componente | Ruolo |
|---|
| Input | Quello che viene fuzzato (byte, albero di grammatica, syscall) |
| Observer | Registra dati durante un”esecuzione (mappa di copertura, timing) |
| Feedback | Decide se un”esecuzione è stata “interessante” |
| Objective | Decide se un”esecuzione è una soluzione (un crash) |
| Corpus | Archiviazione per input interessanti |
| Mutator | Trasforma gli input |
| Scheduler | Sceglie il prossimo input da eseguire |
| Stage | Una fase applicata per input (muta, taglia, calibra) |
| Executor | Esegue il target con un input |
// Struttura concettuale — vedi esempi di LibAFL per codice completo
let mut feedback = MaxMapFeedback::new(&edges_observer);
let mut objective = CrashFeedback::new();
let mut state = StdState::new(
StdRand::with_seed(current_nanos()),
InMemoryCorpus::new(),
OnDiskCorpus::new("./crashes")?,
&mut feedback,
&mut objective,
)?;
let scheduler = QueueScheduler::new();
let mut fuzzer = StdFuzzer::new(scheduler, feedback, objective);
let mut executor = InProcessExecutor::new(
&mut harness, tuple_list!(edges_observer), &mut fuzzer, &mut state, &mut mgr,
)?;
let mutator = StdScheduledMutator::new(havoc_mutations());
let mut stages = tuple_list!(StdMutationalStage::new(mutator));
fuzzer.fuzz_loop(&mut stages, &mut executor, &mut state, &mut mgr)?;
Executor (Come il Target Viene Eseguito)
| Executor | Usa |
|---|
InProcessExecutor | Più veloce; harness nello stesso processo |
ForkserverExecutor | Stile AFL forkserver per binari esterni |
CommandExecutor | Esegui un comando esterno per input |
libafl_qemu | Target emulati / fuzzing binary-only |
libafl_frida | Strumentazione dinamica (binary-only) |
libafl_nyx | Fuzzing di VM basato su snapshot |
Feedback
| Feedback | Interessante quando |
|---|
MaxMapFeedback | Nuovi edge di copertura colpiti |
TimeFeedback | Il tempo di esecuzione cambia |
CrashFeedback | Il target è crashato (objective) |
TimeoutFeedback | Il target si è bloccato (objective) |
NewHashFeedback | Nuovo hash di stack di crash unico |
| Combinatori | feedback_or!, feedback_and! per comporre |
Mutatori
| Mutator | Fa |
|---|
havoc_mutations() | Mutazioni random standard di stile AFL |
tokens_mutations() | Inserimento di dictionary/token |
| Mutatori di grammatica | Generazione consapevole di struttura |
| Custom | Implementa il trait Mutator per il tuo tipo di input |
I tipi di input custom più i mutatori custom sono la ragione principale per scegliere LibAFL — fuzzare un protocollo o un AST intelligentemente piuttosto che capovolgere byte.
Scaling Multi-Core
| Meccanismo | Nota |
|---|
LlmpRestartingEventManager | Passaggio di messaggi a basso overhead tra core |
Launcher | Genera un fuzzer per core con corpus condiviso |
| Sincronizzazione corpus | Gli input interessanti si propagano tra istanze |
| Riavvio | Sopravvive ai crash del processo fuzzer |
LibAFL vs Fuzzer Pronti
| Aspetto | LibAFL | AFL++ | honggfuzz |
|---|
| Modello | Costruisci il tuo | Pronto per eseguire | Pronto per eseguire |
| Sforzo | Alto | Basso | Basso |
| Flessibilità | Totale | Configurabile | Configurabile |
| Migliore per | Target insoliti, ricerca | Binari standard | Inizio veloce, feedback hardware |
Inizia con AFL++ o honggfuzz; passa a LibAFL quando lo scopo di input o il modello di esecuzione li sconfigge.
Risorse