
SunnyDayBPF: ricerca sulla deception di telemetria dei buffer utente post-syscall basata su eBPF di Azizcan Daştan
SunnyDayBPF è una tecnica di ricerca eBPF basata su decezione della telemetria del buffer utente post-syscall originariamente proposta e studiata da Azizcan Dastan.
La tecnica indaga se i dati osservati da agenti di sicurezza, logging o telemetria nello spazio utente possano essere alterati dopo che una syscall di tipo read è stata completata, ma prima che l'agente analizzi, interpreti o inoltri quei dati a una pipeline di sicurezza a valle.
L'idea centrale è:
L'evento accade comunque.
L'agente di monitoraggio legge comunque i dati.
Ma i dati osservati dall'agente potrebbero non rappresentare più completamente l'evento originale.
SunnyDayBPF si concentra sul divario tra ground truth e telemetria osservata.
SunnyDayBPF Hook Points
========================
Telemetry Agent Process +---------------------------------------------------------+ | | | read() pread64() recvfrom() | | | | | | +-----|----------------|------------------|---------------+ | | | ======|================|==================|======= KERNEL BOUNDARY | | | kprobe:ksys_read kprobe:_x64_sys kprobe:_sys (save buf ptr) pread64 recvfrom | (nested pt_regs) (save buf ptr) | (save buf ptr) | v v v [syscall executes — data enters user buffer] | | | kretprobe kretprobe kretprobe | | | +--------+-------+---------+--------+ | | read buffer into initialize BPF scratch space scan_state | v +------------------+ | TAIL CALL CHAIN | | | | scan_g0: SECURITY (4 rules, scan=177 bytes) | scan_g1: SECURITY (4 rules, scan=173 bytes) | scan_g2: SEVERITY (4 rules, scan=177 bytes) | scan_g3: SEVERITY (1 rule, scan=251 bytes) | scan_g4: PATH (4 rules, scan=132 bytes) | scan_g5: AUTH (4 rules, scan=190 bytes) | scan_g6: AUTH (1 rule, scan=249 bytes) | scan_g7: NETWORK (3 rules, scan=249 bytes) | scan_g8: PROCESS (4 rules, scan=173 bytes) | scan_g9: CUSTOM (2 rules, scan=243 bytes) | | | emit_event: | | perf event | | + stats | +------------------+ | v bpf_probe_write_user() (modify agent's buffer) | v read-back verification (confirm write succeeded) | v Agent continues with modified data
### Copertura delle Syscall
| Syscall | Hook del Kernel | Estrazione Arg | Copertura |
|---------|----------------|----------------|----------|
| `read()` | `ksys_read` | `PT_REGS_PARM2` (diretta) | Letture di file, pipe, `/proc`, file di log |
| `pread64()` | `__x64_sys_pread64` | `pt_regs` annidati tramite `bpf_probe_read_kernel` (offset 104/RSI) | Letture di file ad accesso casuale, journald |
| `recvfrom()` | `__sys_recvfrom` | `PT_REGS_PARM2` (diretta) | Socket di rete, inoltro syslog |
### Vincoli del Verificatore BPF
Il verificatore BPF impone un limite di sequenza di salti di 8.192 rami condizionali per programma. SunnyDayBPF aggira questo limite utilizzando:
- **Chiamate coda BPF** (`BPF_PROG_ARRAY`): 31 regole suddivise in 10 programmi indipendenti, ciascuno con il proprio budget del verificatore
- **Ottimizzazione case-insensitive**: `(d[i]|32)==lower` riduce i salti per byte da 2 a 1 per i caratteri alfabetici
- **Limiti di scansione dinamici**: La finestra di scansione di ciascun gruppo è calcolata come `min(BUF_SIZE - max_pat, 7800 / jumps_per_iter)` per rimanere entro i limiti del verificatore
- **Array per-CPU**: `BPF_PERCPU_ARRAY` per buffer temporaneo e stato di scansione, condivisi tra programmi chiamati in coda
---
## Panoramica
I moderni sistemi di sicurezza Linux si basano spesso su agenti nello spazio utente che raccolgono telemetria da file, socket, pipe, API, interfacce del kernel o flussi di eventi.
Questi agenti possono inoltrare la telemetria a:
- piattaforme SIEM
- backend EDR/XDR
- pipeline di audit
- collettori di log
- motori di sicurezza runtime
- sistemi di ingegneria della detection
- piattaforme di osservabilità
Un presupposto comune è:```text
actual system behavior == collected telemetry == observed security data
SunnyDayBPF mette in discussione tale presupposto.
La ricerca esplora un modello di inganno post-syscall dove un processo di monitoraggio riceve i dati normalmente, ma il buffer contenente tali dati viene modificato prima che il processo li consumi.```text actual system behavior != observed telemetry
## Definizione tecnica
SunnyDayBPF è una tecnica di inganno della telemetria post-syscall che studia la manipolazione dei buffer dello spazio utente appartenenti a processi selezionati consumatori di telemetria.
A livello generale, la tecnica segue questo modello:```text
sys_enter_*:
identify a target telemetry-consuming process
record the user-space buffer pointer involved in the read-like operation
sys_exit_*:
verify that the read-like operation completed successfully
inspect the returned user-space buffer
selectively alter telemetry-relevant content
verify write success via read-back
allow the target process to continue execution normally
Questo crea una discrepanza tra:```text what happened on the system
e:```text
what the monitoring agent later observes, parses, and forwards
SunnyDayBPF identifica i processi target tramite corrispondenza del prefisso del nome del comando di 5 caratteri.
| Agente | Prefisso | Metodo di lettura | Efficace? |
|---|---|---|---|
| Wazuh | wazuh | read() su file di log, syslog, log di audit | Sì |
| OSSEC | ossec | read() su file di log | Sì |
| Splunk UF | splun | read() su file monitorati | Sì |
| Elastic Agent | elast | read() su sorgenti log | Sì |
| Datadog Agent | datad | read() su log e metriche | Sì |
| Cribl | cribl | read() per routing log | Sì |
| Agente | Prefisso | Metodo di lettura | Efficace? |
|---|---|---|---|
| rsyslog | rsysl | read() / recvfrom() su syslog | Sì |
| syslog-ng | syslo | read() / recvfrom() su syslog | Sì |
| Filebeat | fileb | read() su file di log | Sì |
| Fluent-bit | fluen | read() / recvfrom() su input | Sì |
| Fluentd | fluen | read() / recvfrom() su input | Sì |
| Logstash | logst | read() / recvfrom() su pipeline | Sì |
| Promtail | promt | read() su file di log (Loki) | Sì |
| Vector | vecto | read() su sorgenti log | Sì |
| Agente | Prefisso | Metodo di lettura | Efficace? |
|---|---|---|---|
| Falco | falco | eventi eBPF raccolti tramite read() su buffer perf | Sì |
| osquery | osque | read() su /proc, file di log, tabelle di sistema | Sì |
| Agente | Prefisso | Metodo di lettura | Efficace? |
|---|---|---|---|
| Snort | snort | recvfrom() su cattura pacchetti | Sì |
| Suricata | suric | recvfrom() su cattura pacchetti | Sì |
| Zeek | zeek_ | recvfrom() su cattura pacchetti | Sì |