Analisi della sequenza temporale · Lezione 3 di 5
Creazione di una super timeline con Plaso
12 min di lettura
Un singolo artefatto raramente consente di stabilire che cosa sia accaduto. È la sequenza di più artefatti a farlo: un programma è stato eseguito, un file è stato aperto, un'unità è stata collegata, una copia è comparsa su quell'unità. Una super timeline riunisce gli eventi provenienti da file system, hive del registro, registri eventi, cronologie dei browser e altre fonti in un unico elenco ordinato cronologicamente. Questa lezione ne costruisce una con The Sleuth Kit e con Plaso, riduce milioni di eventi ai minuti rilevanti e spiega l'errore più comune nel triage: trattare gli orari di copia dei file raccolti come elementi probatori.
Timeline del file system e super timeline
Una timeline del file system elenca soltanto i timestamp contenuti nei metadati del file system: per NTFS, i timestamp $STANDARD_INFORMATION e $FILE_NAME trattati nella lezione 3.2; per FAT, ext4 e altri, i rispettivi campi temporali. È rapida da creare, ma non indica perché un timestamp sia cambiato.
Una super timeline aggiunge i timestamp memorizzati all'interno dei file: orari di esecuzione di Prefetch, timestamp LastWrite delle chiavi del registro, record dei registri eventi, dati di LNK e Jump List, visite del browser. Ogni riga assume quindi un significato, come "ultima visita" o "ultima esecuzione". Il costo è il volume: l'immagine completa di un sistema Windows produce comunemente milioni di eventi.
| Aspetto | Timeline del file system | Super timeline |
|---|---|---|
| Fonti | Solo metadati del file system | File system e artefatti all'interno dei file |
| Strumenti tipici | fls + mactime (The Sleuth Kit) | Plaso (log2timeline.py, psort.py) |
| Significato degli eventi | Indicatori MACB | Testo di timestamp_desc per ciascun evento |
| Dimensioni | Da migliaia a centinaia di migliaia di righe | Spesso milioni di righe |
| Impiego ottimale | Rapida panoramica dell'attività sui file di un volume | Ricostruzione dell'attività dell'utente e del sistema |
Il metodo classico: bodyfile e mactime
The Sleuth Kit costruisce una timeline del file system in due passaggi. Per prima cosa, fls -r -m E: -z America/Sao_Paulo -o 2048 usb.E01 > usb.body percorre ricorsivamente il file system (-r) e scrive un bodyfile (-m, con E: come prefisso inserito prima di ogni percorso); -z specifica il fuso orario del sistema originale, necessario a fls per convertire gli orari locali FAT. -o 2048 indica il settore iniziale della partizione. In secondo luogo, mactime -b usb.body -d -z UTC > usb.csv ordina il bodyfile e lo restituisce come testo delimitato da virgole (-d) in UTC (-z).
Il bodyfile (formato TSK 3.x) contiene 11 campi separati da barre verticali: MD5|name|inode|mode_as_string|UID|GID|size|atime|mtime|ctime|crtime. I quattro timestamp sono espressi in secondi dall'epoca Unix. Su NTFS, fls scrive una seconda riga per ogni file, aggiungendo ($FILE_NAME) al nome, contenente i timestamp $FN.
Le colonne dell'output di mactime sono Date, Size, Type, Mode, UID, GID, Meta e File Name. Type è la stringa MACB: m modificato, a accesso effettuato, c metadati modificati, b nato (creato). Una riga con m.cb indica che tre dei quattro timestamp coincidono nello stesso secondo.
Esempio svolto: lettura di un timestamp del bodyfile
Una riga del bodyfile per E:/Plans/agenda.docx presenta crtime = 1773479721.
- 1773479721 ÷ 86.400 = 20.526 giorni, con un resto di 33.321 secondi.
- 20.526 giorni dopo il 1970-01-01 corrispondono al 2026-03-14.
- 33.321 s = 9 h (32.400 s) + 921 s = 9 h 15 min 21 s.
- Risultato: 2026-03-14T09:15:21Z.
mactime -z UTClo restituisce comeSat Mar 14 2026 09:15:21;-yrestituisce invece il formato ISO 8601 in UTC.
Architettura di Plaso
Plaso ("Plaso Langar Að Safna Öllu") suddivide il lavoro in estrazione e produzione dell'output, collegate da un file di archiviazione.
log2timeline.pyapre la fonte tramite dfVFS, il livello di file system virtuale di Plaso (che legge immagini E01 e raw, partizioni, snapshot VSS e normali directory). Esegue i parser su ogni file e scrive ciascun evento in un file di archiviazione Plaso (.plaso), basato su SQLite.pinfo.pyriporta il contenuto di un file di archiviazione: la versione di Plaso, ogni sessione di estrazione e la relativa riga di comando, il numero di eventi per parser e gli avvisi di estrazione.psort.pylegge il file di archiviazione, ordina cronologicamente, rimuove i duplicati, applica filtri e scrive l'output.psteal.pyesegue l'estrazione e la produzione dell'output in un unico passaggio, ad esempiopsteal.py --source usb.E01 -o dynamic -w usb.csv. Gli strumenti separati sono più adatti alle indagini: il file di archiviazione può essere nuovamente filtrato senza ripetere l'estrazione.
Parser e preset. --parsers accetta un elenco di preset, parser e plugin separati da virgole. Il prefisso ! esclude un elemento. log2timeline.py --info li elenca tutti. Tra i preset utili figurano win7 (Windows Vista e versioni successive, che include l'insieme generale win_gen), webhist (cronologie dei browser) e linux; winreg è il parser del registro con tutti i relativi plugin. Il parser mft legge direttamente un file NTFS $MFT e produce sia i timestamp $SI sia quelli $FN; aggiungerlo per nome affinché il file $MFT raccolto venga analizzato indipendentemente dal contenuto di un preset nella versione di Plaso in uso. Se si omette --parsers, Plaso sceglie un preset in base al sistema operativo rilevato; in una cartella di triage parziale tale rilevamento può fallire, pertanto occorre specificare esplicitamente i parser.
Fonti. Una fonte può essere un'immagine (--partitions all o --partitions 1,3 seleziona le partizioni; --volumes all seleziona i volumi APFS o LVM; --vss_stores controlla le copie shadow), una directory, ad esempio una raccolta di triage, oppure un singolo file. Eseguire nuovamente log2timeline.py con lo stesso --storage-file (e la stessa versione di Plaso) aggiunge una nuova sessione, consentendo a più fonti di condividere un unico file di archiviazione. pinfo.py elenca ciascuna sessione separatamente.
Formati e colonne dell'output
psort.py -o dynamic scrive un CSV con queste colonne predefinite (è possibile sceglierne altre con --fields):
| Colonna | Contenuto |
|---|---|
datetime | Orario dell'evento in formato ISO 8601, nel fuso orario dell'output |
timestamp_desc | Significato di questo timestamp |
source / source_long | Tipo di fonte in forma breve e lunga, ad esempio FILE o WEBHIST e una descrizione più estesa |
message | Descrizione dell'evento leggibile dall'utente |
parser | Catena di parser, come mft o sqlite/chrome_27_history |
display_name | File da cui proviene l'evento, così come rilevato da Plaso |
tag | Etichette aggiunte dai plugin di analisi o dall'analista |
timestamp_desc è la colonna chiave. Lo stesso file può produrre eventi "Ora di creazione", "Ora di modifica del contenuto", "Ora dell'ultimo accesso" e "Ora di modifica dei metadati". La cronologia di un browser produce "Ora dell'ultima visita"; un file Prefetch produce "Ora dell'ultima esecuzione". Leggere sempre questa colonna prima di dichiarare che cosa dimostri un orario.
-o l2tcsv è il formato storico di log2timeline con 17 campi fissi (date,time,timezone,MACB,source,sourcetype,type,user,host,short,desc,version,filename,inode,notes,format,extra). -o json_line scrive un oggetto JSON per evento, adatto a script e piattaforme di ricerca.
Fuso orario. Plaso memorizza gli orari in UTC. Per impostazione predefinita, l'output è in UTC; --output_time_zone UTC lo rende esplicito nelle annotazioni. Alcune fonti memorizzano l'ora locale senza fuso orario, come i timestamp FAT; log2timeline.py --timezone indica a Plaso quale fuso orario assumere durante l'estrazione. La lezione 3.5 tratta in dettaglio gli errori relativi ai fusi orari.
Dimensioni e rumore: definire prima il quesito
Non è possibile leggere milioni di righe e un foglio di lavoro Excel si ferma a 1.048.576 righe. Procedere in questo ordine:
- Definire il quesito e l'intervallo temporale prima di eseguire
psort.py, ad esempio "che cosa è accaduto nelle due ore intorno al collegamento USB?" Ricavare l'orario di riferimento da un artefatto preciso (lezione 2.6). - Filtrare per orario con un filtro sugli eventi:
"date > DATETIME('2026-03-14T08:30:00') AND date < DATETIME('2026-03-14T10:30:00')". Scrivere gli orari del filtro in UTC. - Filtrare per fonte con
data_type, ad esempio"data_type contains 'chrome'", oppure estrarre soltanto con i parser necessari. - Cercare parole chiave, come un nome di file o un numero di serie.
- Esaminare i risultati in un visualizzatore CSV come Timeline Explorer, in un foglio di calcolo per intervalli temporali ridotti oppure in una piattaforma collaborativa come Timesketch, che importa direttamente i file
.plaso.
I duplicati, ad esempio un evento rilevato in un volume e nella relativa copia shadow, vengono uniti per impostazione predefinita; -a (--include_all) li mantiene.
Raccolte di triage: gli orari di copia non sono elementi probatori
Questa è l'avvertenza più importante della lezione. Una raccolta di triage è un insieme di file copiati dal sistema in esecuzione in una cartella (o in un contenitore), mantenendone i percorsi originali. Quando Plaso elabora tale cartella, il parser filestat legge i timestamp attuali del file system delle copie sul disco dell'analista. A meno che lo strumento di triage non abbia preservato i timestamp originali, questi valori registrano il momento in cui i file sono stati raccolti o estratti, non quello in cui l'utente li ha creati o modificati. Anche gli strumenti che ripristinano i timestamp non possono ripristinare quelli $FN.
I timestamp NTFS originali rimangono nel file $MFT raccolto. Analizzarlo con il parser mft ed escludere filestat per la cartella di triage: --parsers 'win7,mft,!filestat'. Utilizzare apici singoli, poiché molte shell trattano ! all'interno di virgolette doppie come un comando della cronologia. Inoltre, display_name mostra il percorso all'interno della raccolta, come /data/triage/C/Users/ana/...; nella relazione, ricondurlo al percorso originale C:\.
Esempio svolto: una timeline, due fonti
La cartella del caso /cases/c042 contiene triage/ (la raccolta Windows, incluso C/$MFT) e usb.E01 (una partizione FAT32). Il fuso orario del sistema, letto dal registro nella lezione 2.2, è E. South America Standard Time (America/Sao_Paulo, UTC−3). Plaso viene eseguito nell'immagine Docker ufficiale, con la cartella del caso montata in /data.
| Passaggio | Comando |
|---|---|
| Registrare la versione | docker run --rm log2timeline/plaso log2timeline.py --version |
| Estrarre la cartella di triage | docker run --rm -v /cases/c042:/data log2timeline/plaso log2timeline.py --parsers 'win7,mft,!filestat' --storage-file /data/case.plaso /data/triage |
| Aggiungere l'immagine USB | docker run --rm -v /cases/c042:/data log2timeline/plaso log2timeline.py --partitions all --timezone Europe/Lisbon --storage-file /data/case.plaso /data/usb.E01 |
| Verificare il risultato | docker run --rm -v /cases/c042:/data log2timeline/plaso pinfo.py -v /data/case.plaso |
| Produrre l'output dell'intervallo temporale | docker run --rm -v /cases/c042:/data log2timeline/plaso psort.py --output_time_zone UTC -o dynamic -w /data/window.csv /data/case.plaso "date > '2026-03-14 08:30:00' AND date < '2026-03-14 10:30:00'" |
pinfo.py mostra due sessioni, conteggi diversi da zero per mft, prefetch, chrome_27_history e filestat (solo dalla sessione USB), oltre a eventuali avvisi. Sei righe di window.csv tra le 09:15 e le 09:25Z si presentano come segue (messaggi abbreviati; datetime ridotto ai secondi e il relativo +00:00 scritto come Z):
| datetime | timestamp_desc | source | parser | message |
|---|---|---|---|---|
| 2026-03-14T09:15:21Z | Ora dell'ultima esecuzione | LOG | prefetch | EXCEL.EXE è stato eseguito |
| 2026-03-14T09:15:58Z | Ora di creazione | FILE | mft | \Users\ana\AppData\Roaming\Microsoft\Windows\Recent\budget.xlsx.lnk ($SI) |
| 2026-03-14T09:18:40Z | Ora di modifica del contenuto | FILE | mft | \Users\ana\Documents\budget.xlsx ($SI) |
| 2026-03-14T09:18:40Z | Ora di modifica del contenuto | FILE | filestat | FAT:/Plans/budget.xlsx (usb.E01) |
| 2026-03-14T09:21:12Z | Ora di creazione | FILE | filestat | FAT:/Plans/budget.xlsx (usb.E01) |
| 2026-03-14T09:23:05Z | Ora dell'ultima visita | WEBHIST | sqlite/chrome_27_history | bing.com/search?q=clear+recent+files |
Interpretazione: Excel è stato eseguito alle 09:15:21Z. Il file LNK creato alle 09:15:58Z indica la prima apertura di budget.xlsx da quel percorso (lezione 2.4). Il documento è stato salvato alle 09:18:40Z. Sull'unità USB, la copia presenta lo stesso orario di modifica ma un orario di creazione successivo, 09:21:12Z: lo schema classico di un file copiato su un nuovo supporto, poiché la copia mantiene l'orario di modifica e imposta un nuovo orario di creazione. Alle 09:23:05Z l'utente ha cercato come cancellare l'elenco dei file recenti. Prima di riportare le 09:21:12Z, corroborare tale orario con un collegamento del dispositivo che comprenda quel momento (eventi Partition/Diagnostic 1006, setupapi.dev.log o orari di collegamento USBSTOR) e con il numero di serie del volume (lezione 2.6); la lezione 3.4 tratta questa correlazione tra fonti.
Documentazione per la ripetibilità
Registrare come è stata creata la timeline: la versione di Plaso (e il tag o il digest dell'immagine Docker), ogni riga di comando, l'elenco dei parser, le impostazioni dei fusi orari, l'hash di ciascuna fonte e l'output di pinfo.py. Il file di archiviazione conserva ogni riga di comando di estrazione, ma le annotazioni devono comprendere anche i filtri di psort. ISO/IEC 27041 richiede di dimostrare che un metodo sia adatto al quesito e validato. ISO/IEC 27042 richiede che l'analisi sia ripetibile e riproducibile. Un'immagine del contenitore fissata a una versione specifica consente a un altro esaminatore di rieseguire gli stessi comandi e ottenere le stesse righe.
Focus sull'esame: Occorre saper indicare un orario UTC ricavato da una riga della timeline; leggere quinditimestamp_desce il parser prima di decidere che cosa dimostri l'orario. È necessario sapere che i timestamp del file system dei file presenti in una raccolta di triage riflettono la raccolta e che i timestamp NTFS originali provengono dal file$MFTraccolto. Occorre saper convertire un valore di epoca di un bodyfile e riconoscere lo schema di copia caratterizzato da un orario di creazione successivo a quello di modifica.
Punti chiave
- Una timeline del file system contiene soltanto i timestamp dei metadati; una super timeline aggiunge timestamp dall'interno degli artefatti e raggiunge milioni di eventi.
fls -r -mscrive un bodyfile con timestamp espressi in secondi dall'epoca;mactime -b body -d -z UTClo ordina in righe MACB.log2timeline.pyanalizza le fonti e le inserisce in un file.plasobasato su SQLite;pinfo.pylo verifica;psort.pyfiltra, elimina i duplicati e scrive nei formatidynamic,l2tcsvojson_line.- In una cartella di triage, escludere
filestate analizzare il file$MFTraccolto con il parsermft. - Definire prima il quesito e l'intervallo temporale, filtrare in UTC e corroborare le righe chiave con altre fonti.
- Registrare versioni, righe di comando, filtri e hash affinché un altro esaminatore possa riprodurre la timeline.
Domande di esercitazione
Verifica la tua comprensione. Queste domande non contano per l’esame.
Accedi per salvare i tuoi progressi e riprendere da dove hai lasciato. È gratuito. Accedi