
Strumento di osservabilità dei segnali del kernel in tempo reale che utilizza eBPF tracepoint per trasmettere ogni segnale generato su un host Linux, mostrando in tempo reale mittente, destinatario, disposizione, latenza del gestore e interruzioni delle chiamate di sistema.
sigwire
tail -fper i segnali. Ogni segnale lanciato da qualsiasi processo sulla macchina — chi lo ha inviato, chi lo ha ricevuto, quale segnale, come è stato lanciato (kill(2), il kernel, un timer POSIX), se il destinatario lo ha catturato e per quanto tempo il suo handler è stato eseguito, se ha strappato una chiamata di sistema bloccata conEINTR— decodificato dai tracepoint dei segnali del kernel e trasmesso in diretta sul tuo terminale. Nientestrace -fsu un singolo pid, nienteptrace, nessuna cooperazione dai processi coinvolti.
sigwire trasforma il meccanismo dei segnali del kernel in un patchbay live: ogni riga è sender ──SIGNAL──▶ target, colorata per gravità, etichettata con come è stato lanciato, se il target lo ha catturato (e per quanto tempo il suo handler è stato eseguito), se ha interrotto una chiamata di sistema bloccata (↯ EINTR read), compresso in ×N quando qualcosa invia ripetutamente, e contrassegnato con ☠ quando è un vero colpo letale. Un pannello laterale conta cosa sta volando sul cavo; metti in pausa e scegli una riga per ispezionare il quadro completo — disposizione, indirizzo dell'handler, flag di sigaction e i segnali che il target stava bloccando in quell'istante.
Poiché si aggancia ai tracepoint del kernel, non a un singolo processo, una singola esecuzione osserva ogni segnale sull'host in una volta — la tua applicazione, un supervisore, il meccanismo di fault del kernel stesso — senza che nessuno di loro sappia di essere tracciato.
[!TIP] Due lati di ogni segnale. sigwire osserva sia
signal:signal_generate(la vista del mittente — chi ha lanciato cosa, la linea del centralino) siasignal:signal_deliver(la vista del destinatario — lo ha catturato, con quale handler e flag, cosa stava bloccando, e ha interrotto una chiamata di sistema). Altri due hook —rt_sigreturn(2)e il tracepoint di uscita dalla chiamata di sistema — misurano il tempo dell'handler e catturano EINTR. Tutto è correlato in una singola riga. Questa divisione è anche il motivo per cui il conteggio☠ fatalè deliberatamente conservativo (vedi Cosa viene considerato fatale): la generazione avviene prima della consegna, quindi il lato mittente non può conoscere il destino del segnale — solo il lato di consegna può, e solo per i casi che osserva.
curl -fsSL https://yeet.cx | sh # install the yeet daemon (one time) yeet run github:yeet-src/sigwire # run the dashboard (the daemon does the privileged BPF load)
[Guida all'installazione manuale](https://yeet.cx/docs/manual-installation) | Solo Linux
Niente da configurare — i segnali sono traffico di fondo costante su qualsiasi macchina, quindi le righe iniziano ad arrivare immediatamente in cima. Vuoi crearne qualcuno da solo? `kill -USR1 <pid>`, `Ctrl-C` su un job in foreground, o avvia un runtime gestito e guarda il suo GC/scheduler fare ping ai propri thread (`↯ EINTR futex` che scorrono).
## Controlli
Il feed segue il segnale più recente per impostazione predefinita; seleziona una riga o metti in pausa e rimane fermo mentre i dati continuano a fluire sotto.
| key | action |
| --- | ------ |
| `p` · `Space` | metti in pausa / riprendi il feed (congelalo per leggere) |
| `↑`/`↓`, `k`/`j` | metti in pausa e ispeziona una riga — apre il pannello dei dettagli |
| `/` | filtro fuzzy — corrisponde a processo, pid, segnale, sorgente e disposizione; i caratteri corrispondenti si evidenziano in tempo reale |
| `e` | filtra solo le **syscall interrotte** (`↯ EINTR` / `↺ riavviate`) |
| `s` | apri il **selettore di segnali** — silenzia o mostra qualsiasi segnale, in tempo reale |
| `Esc` | torna indietro di un livello — cancella il filtro / chiudi il selettore / abbandona la selezione, poi esci |
| `q` | esci |
## Cosa stai guardando
Ogni riga è un segnale generato, il più recente in cima:```
WHEN SENDER SIGNAL TARGET NOTE
now bash·4402──SIGINT───▶ node·8813 kill(2) ↯ EINTR read caught 41µs
1.2s systemd·1──────SIGTERM──▶ nginx·1291 kill(2) caught 1.2ms
3.4s kernel·8813──SIGSEGV──▶ chrome·8813 fault default ☠
4.1s postgres·507──SIGUSR1───▶ postgres·509 ×6 kill(2) caught 9µs
Ogni riga è un blocco: il mittente → destinatario sono comm·pid (il mittente è chi ha generato il segnale, current; il destinatario è a chi è rivolto), il cavo al centro porta il nome del segnale colorato per gravità, ×N comprime un burst dello stesso segnale in una riga, e la nota a destra fornisce la sorgente, poi eventuali interruzioni di syscall, poi la disposizione.
Ogni riga viene congelata nel momento in cui la sua consegna viene risolta e non muta mai più — quindi un burst scorre come un log stabile, non un aggregato tremolante.
Il cavo è colorato per gravità sulla stessa tavolozza a 256 colori del resto dell'interfaccia utente:
| gravità | segnali | colore |
|---|---|---|
| kill | SIGKILL | hot red |
| fatale (con core dump) | SEGV BUS ABRT ILL FPE TRAP SYS QUIT | red |
| terminazione | TERM INT HUP PIPE ALRM … | amber |
| controllo job | STOP TSTP TTIN TTOU | yellow |
| continua | CONT | green |
| utente | USR1 USR2 | cyan |
| tempo reale | SIGRTMIN+n | violet |
| manutenzione | CHLD URG WINCH … | grey |
La nota è la sorgente (kill(2), tgkill, sigqueue, timer, kernel, fault); poi, se ha interrotto una syscall bloccata, ↯ EINTR read (o ↺ restarted read quando SA_RESTART l'ha ripresa automaticamente); poi la disposizione — caught 41µs (un handler è stato eseguito, e per quanto tempo), default (nessun handler, azione predefinita applicata), o ⊘ ignored. Un ☠ segna un colpo letale reale (vedi Cosa conta come fatale).
[!NOTE]
↯ EINTRè ciò che si deve osservare. Un segnale che arriva mentre un thread è bloccato in una syscall lenta (read,poll,accept,futex,nanosleep, …) lo tira fuori: la syscall restituisce-1/EINTRe, a meno che l'handler non abbia impostatoSA_RESTART, non riprende — l'app deve riprovare. Dimenticarlo è un bug classico, frustrante e dipendente dal tempismo ("perché la miaread()ha fallito una volta?"). sigwire lo mostra mentre accade, in tempo reale, e quale syscall ha subito l'interruzione. Premieper nascondere tutto il resto e guardare solo le interruzioni.
La barra a destra è la vista aggregata: segnali principali per volume, una ripartizione per sorgente, e un conteggio di consegna — quanti segnali sono stati catturati vs. hanno raggiunto il default vs. ignorati.