lists.openwall.net   lists  /  announce  owl-users  owl-dev  john-users  john-dev  passwdqc-users  yescrypt  popa3d-users  /  oss-security  kernel-hardening  musl  sabotage  tlsify  passwords  /  crypt-dev  xvendor  /  Bugtraq  Full-Disclosure  linux-kernel  linux-netdev  linux-ext4  linux-hardening  linux-cve-announce  PHC 
Open Source and information security mailing list archives
 
Hash Suite: Windows password security audit tool. GUI, reports in PDF.
[<prev] [next>] [thread-next>] [day] [month] [year] [list]
Message-Id: <20230102183716.9698-1-federico.vaga@vaga.pv.it>
Date:   Mon,  2 Jan 2023 19:37:16 +0100
From:   Federico Vaga <federico.vaga@...a.pv.it>
To:     Jonathan Corbet <corbet@....net>
Cc:     Federico Vaga <federico.vaga@...a.pv.it>,
        linux-doc@...r.kernel.org, linux-kernel@...r.kernel.org
Subject: [PATCH V2] doc:it_IT: add translation for botching-up-ioctl.rst

This patch adds the translation for the botching up ioctl document.

Signed-off-by: Federico Vaga <federico.vaga@...a.pv.it>
---
V1 -> V2 use the kernel-doc mecanism to link functions in documents

 .../it_IT/process/botching-up-ioctls.rst      | 249 ++++++++++++++++++
 .../translations/it_IT/process/index.rst      |   1 +
 2 files changed, 250 insertions(+)
 create mode 100644 Documentation/translations/it_IT/process/botching-up-ioctls.rst

diff --git a/Documentation/translations/it_IT/process/botching-up-ioctls.rst b/Documentation/translations/it_IT/process/botching-up-ioctls.rst
new file mode 100644
index 000000000000..91732cdf808a
--- /dev/null
+++ b/Documentation/translations/it_IT/process/botching-up-ioctls.rst
@@ -0,0 +1,249 @@
+.. include:: ../disclaimer-ita.rst
+
+:Original: Documentation/process/botching-up-ioctls.rst
+
+==========================================
+(Come evitare di) Raffazzonare delle ioctl
+==========================================
+
+Preso da: https://blog.ffwll.ch/2013/11/botching-up-ioctls.html
+
+Scritto da : Daniel Vetter, Copyright © 2013 Intel Corporation
+
+Una cosa che gli sviluppatori del sottosistema grafico del kernel Linux hanno
+imparato negli ultimi anni è l'inutilità di cercare di creare un'interfaccia
+unificata per gestire la memoria e le unità esecutive di diverse GPU. Dunque,
+oggigiorno ogni driver ha il suo insieme di ioctl per allocare memoria ed
+inviare dei programmi alla GPU. Il che è va bene dato che non c'è più un insano
+sistema che finge di essere generico, ma al suo posto ci sono interfacce
+dedicate. Ma al tempo stesso è più facile incasinare le cose.
+
+Per evitare di ripetere gli stessi errori ho preso nota delle lezioni imparate
+mentre raffazzonavo il driver drm/i915. La maggior parte di queste lezioni si
+focalizzano sui tecnicismi e non sulla visione d'insieme, come le discussioni
+riguardo al modo migliore per implementare una ioctl per inviare compiti alla
+GPU. Probabilmente, ogni sviluppatore di driver per GPU dovrebbe imparare queste
+lezioni in autonomia.
+
+
+Prerequisiti
+------------
+
+Prima i prerequisiti. Seguite i seguenti suggerimenti se non volete fallire in
+partenza e ritrovarvi ad aggiungere un livello di compatibilità a 32-bit.
+
+* Usate solamente interi a lunghezza fissa. Per evitare i conflitti coi tipi
+  definiti nello spazio utente, il kernel definisce alcuni tipi speciali, come:
+  ``__u32``, ``__s64``. Usateli.
+
+* Allineate tutto alla lunghezza naturale delle piattaforma in uso e riempite
+  esplicitamente i vuoti. Non necessariamente le piattaforme a 32-bit allineano
+  i valori a 64-bit rispettandone l'allineamento, ma le piattaforme a 64-bit lo
+  fanno. Dunque, per farlo correttamente in entrambe i casi dobbiamo sempre
+  riempire i vuoti.
+
+* Se una struttura dati contiene valori a 64-bit, allora fate si che la sua
+  dimensione sia allineata a 64-bit, altrimenti la sua dimensione varierà su
+  sistemi a 32-bit e 64-bit. Avere una dimensione differente causa problemi
+  quando si passano vettori di strutture dati al kernel, o quando il kernel
+  effettua verifiche sulla dimensione (per esempio il sistema drm lo fa).
+
+* I puntatori sono di tipo ``__u64``, con un *cast* da/a ``uintptr_t`` da lato
+  spazio utente e da/a ``void __user *`` nello spazio kernel. Sforzatevi il più
+  possibile per non ritardare la conversione, o peggio maneggiare ``__u64`` nel
+  vostro codice perché questo riduce le verifiche che strumenti come sparse
+  possono effettuare. La macro u64_to_user_ptr() può essere usata nel kernel
+  per evitare avvisi riguardo interi e puntatori di dimensioni differenti.
+
+
+Le Basi
+-------
+
+Con la gioia d'aver evitato un livello di compatibilità, possiamo ora dare uno
+sguardo alle basi. Trascurare questi punti renderà difficile la gestione della
+compatibilità all'indietro ed in avanti. E dato che sbagliare al primo colpo è
+garantito, dovrete rivisitare il codice o estenderlo per ogni interfaccia.
+
+* Abbiate un modo chiaro per capire dallo spazio utente se una nuova ioctl, o
+  l'estensione di una esistente, sia supportata dal kernel in esecuzione. Se non
+  potete fidarvi del fatto che un vecchio kernel possa rifiutare correttamente
+  un nuovo *flag*, modalità, o ioctl, (probabilmente perché avevate raffazzonato
+  qualcosa nel passato) allora dovrete implementare nel driver un meccanismo per
+  notificare quali funzionalità sono supportate, o in alternativa un numero di
+  versione.
+
+* Abbiate un piano per estendere le ioctl con nuovi *flag* o campi alla fine di
+  una struttura dati. Il sistema drm verifica la dimensione di ogni ioctl in
+  arrivo, ed estende con zeri ogni incongruenza fra kernel e spazio utente.
+  Questo aiuta, ma non è una soluzione completa dato che uno spazio utente nuovo
+  su un kernel vecchio non noterebbe che i campi nuovi alla fine della struttura
+  vengono ignorati. Dunque, anche questo avrà bisogno di essere notificato dal
+  driver allo spazio utente.
+
+* Verificate tutti i campi e *flag* inutilizzati ed i riempimenti siano a 0,
+  altrimenti rifiutare la ioctl. Se non lo fate il vostro bel piano per
+  estendere le ioctl andrà a rotoli dato che qualcuno userà delle ioctl con
+  strutture dati con valori casuali dallo stack nei campi inutilizzati. Il che
+  si traduce nell'avere questi campi nell'ABI, e la cui unica utilità sarà
+  quella di contenere spazzatura. Per questo dovrete esplicitamente riempire i
+  vuoti di tutte le vostre strutture dati, anche se non le userete in un
+  vettore. Il riempimento fatto dal compilatore potrebbe contenere valori
+  casuali.
+
+* Abbiate un semplice codice di test per ognuno dei casi sopracitati.
+
+
+Divertirsi coi percorsi d'errore
+--------------------------------
+
+Oggigiorno non ci sono più scuse rimaste per permettere ai driver drm di essere
+sfruttati per diventare root. Questo significa che dobbiamo avere una completa
+validazione degli input e gestire in modo robusto i percorsi - tanto le GPU
+moriranno comunque nel più strano dei casi particolari:
+
+ * Le ioctl devono verificare l'overflow dei vettori. Inoltre, per i valori
+   interi si devono verificare *overflow*, *underflow*, e *clamping*. Il
+   classico esempio è l'inserimento direttamente nell'hardware di valori di
+   posizionamento di un'immagine *sprite* quando l'hardware supporta giusto 12
+   bit, o qualcosa del genere. Tutto funzionerà finché qualche strano *display
+   server* non decide di preoccuparsi lui stesso del *clamping* e il cursore
+   farà il giro dello schermo.
+
+ * Avere un test semplice per ogni possibile fallimento della vostra ioctl.
+   Verificate che il codice di errore rispetti le aspettative. Ed infine,
+   assicuratevi che verifichiate un solo percorso sbagliato per ogni sotto-test
+   inviando comunque dati corretti. Senza questo, verifiche precedenti
+   potrebbero rigettare la ioctl troppo presto, impedendo l'esecuzione del
+   codice che si voleva effettivamente verificare, rischiando quindi di
+   mascherare bachi e regressioni.
+
+ * Fate si che tutte le vostre ioctl siano rieseguibili. Prima di tutto X adora
+   i segnali; secondo questo vi permetterà di verificare il 90% dei percorsi
+   d'errore interrompendo i vostri test con dei segnali. Grazie all'amore di X
+   per i segnali, otterrete gratuitamente un eccellente copertura di base per
+   tutti i vostri percorsi d'errore. Inoltre, siate consistenti sul modo di
+   gestire la riesecuzione delle ioctl - per esempio, drm ha una piccola
+   funzione di supporto `drmIoctl` nella sua librerie in spazio utente. Il
+   driver i915 l'abbozza con l'ioctl `set_tiling`, ed ora siamo inchiodati per
+   sempre con una semantica arcana sia nel kernel che nello spazio utente.
+
+
+ * Se non potete rendere un pezzo di codice rieseguibile, almeno rendete
+   possibile la sua interruzione. Le GPU moriranno e i vostri utenti non vi
+   apprezzeranno affatto se tenete in ostaggio il loro scatolotto (mediante un
+   processo X insopprimibile). Se anche recuperare lo stato è troppo complicato,
+   allora implementate una scadenza oppure come ultima spiaggia una rete di
+   sicurezza per rilevare situazioni di stallo quando l'hardware da di matto.
+
+ * Preparate dei test riguardo ai casi particolarmente estremi nel codice di
+   recupero del sistema - è troppo facile create uno stallo fra il vostro codice
+   anti-stallo e un processo scrittore.
+
+
+Tempi, attese e mancate scadenze
+--------------------------------
+
+Le GPU fanno quasi tutto in modo asincrono, dunque dobbiamo regolare le
+operazioni ed attendere quelle in sospeso. Questo è davvero difficile; al
+momento nessuna delle ioctl supportante dal driver drm/i915 riesce a farlo
+perfettamente, il che significa che qui ci sono ancora una valanga di lezioni da
+apprendere.
+
+ * Per fare riferimento al tempo usate sempre ``CLOCK_MONOTONIC``. Oggigiorno
+   questo è quello che viene usato di base da alsa, drm, e v4l. Tuttavia,
+   lasciate allo spazio utente la possibilità di capire quali *timestamp*
+   derivano da domini temporali diversi come il vostro orologio di sistema
+   (fornito dal kernel) oppure un contatore hardware indipendente da qualche
+   parte. Gli orologi divergeranno, ma con questa informazione gli strumenti di
+   analisi delle prestazioni possono compensare il problema. Se il vostro spazio
+   utente può ottenere i valori grezzi degli orologi, allora considerate di
+   esporre anch'essi.
+
+ * Per descrivere il tempo, usate ``__s64`` per i secondi e ``__u64`` per i
+   nanosecondi. Non è il modo migliore per specificare il tempo, ma è
+   praticamente uno standard.
+
+ * Verificate che gli input di valori temporali siano normalizzati, e se non lo
+   sono scartateli. Fate attenzione perché la struttura dati ``struct ktime``
+   del kernel usa interi con segni sia per i secondi che per i nanosecondi.
+
+ * Per le scadenze (*timeout*) usate valori temporali assoluti. Se siete dei
+   bravi ragazzi e avete reso la vostra ioctl rieseguibile, allora i tempi
+   relativi tendono ad essere troppo grossolani e a causa degli arrotondamenti
+   potrebbero estendere in modo indefinito i tempi di attesa ad ogni
+   riesecuzione. Particolarmente vero se il vostro orologio di riferimento è
+   qualcosa di molto lento come il contatore di *frame*. Con la giacca da
+   avvocato delle specifiche diremmo che questo non è un baco perché tutte le
+   scadenze potrebbero essere estese - ma sicuramente gli utenti vi odieranno
+   quando le animazioni singhiozzano.
+
+ * Considerate l'idea di eliminare tutte le ioctl sincrone con scadenze, e di
+   sostituirle con una versione asincrona il cui stato può essere consultato
+   attraverso il descrittore di file mediante ``poll``. Questo approccio si
+   sposa meglio in un applicazione guidata dagli eventi.
+
+ * Sviluppate dei test per i casi estremi, specialmente verificate che i valori
+   di ritorno per gli eventi già completati, le attese terminate con successo, e
+   le attese scadute abbiano senso e servano ai vostri scopi.
+
+
+Non perdere risorse
+-------------------
+Nel suo piccolo il driver drm implementa un sistema operativo specializzato per
+certe GPU. Questo significa che il driver deve esporre verso lo spazio
+utente tonnellate di agganci per accedere ad oggetti e altre risorse. Farlo
+correttamente porterà con se alcune insidie:
+
+ * Collegate sempre la vita di una risorsa creata dinamicamente, a quella del
+   descrittore di file. Considerate una mappatura 1:1 se la vostra risorsa
+   dev'essere condivisa fra processi - passarsi descrittori di file sul socket
+   unix semplifica la gestione anche per lo spazio utente.
+
+ * Dev'esserci sempre Il supporto ``O_CLOEXEC``.
+
+ * Assicuratevi di avere abbastanza isolamento fra utenti diversi. Di base
+   impostate uno spazio dei nomi riservato per ogni descrittore di file, il che
+   forzerà ogni condivisione ad essere esplicita. Usate uno spazio più globale
+   per dispositivo solo se gli oggetti sono effettivamente unici per quel
+   dispositivo. Un controesempio viene dall'interfaccia drm modeset, dove
+   oggetti specifici di dispositivo, come i connettori, condividono uno spazio
+   dei nomi con oggetti per il *framebuffer*, ma questi non sono per niente
+   condivisi. Uno spazio separato, privato di base, per i *framebuffer* sarebbe
+   stato meglio.
+
+ * Pensate all'identificazione univoca degli agganci verso lo spazio utente. Per
+   esempio, per la maggior parte dei driver drm, si considera fallace la doppia
+   sottomissione di un oggetto allo stesso comando ioctl. Ma per evitarlo, se
+   gli oggetti sono condivisibili, lo spazio utente ha bisogno di sapere se il
+   driver ha importato un oggetto da un altro processo. Non l'ho ancora provato,
+   ma considerate l'idea di usare il numero di inode come identificatore per i
+   descrittori di file condivisi - che poi è come si distinguono i veri file.
+   Sfortunatamente, questo richiederebbe lo sviluppo di un vero e proprio
+   filesystem virtuale nel kernel.
+
+
+Ultimo, ma non meno importante
+------------------------------
+
+Non tutti i problemi si risolvono con una nuova ioctl:
+
+* Pensateci su due o tre volte prima di implementare un'interfaccia privata per
+  un driver. Ovviamente è molto più veloce seguire questa via piuttosto che
+  buttarsi in lunghe discussioni alla ricerca di una soluzione più generica. Ed
+  a volte un'interfaccia privata è quello che serve per sviluppare un nuovo
+  concetto. Ma alla fine, una volta che c'è un'interfaccia generica a
+  disposizione finirete per mantenere due interfacce. Per sempre.
+
+* Considerate interfacce alternative alle ioctl. Gli attributi sysfs sono molto
+  meglio per impostazioni che sono specifiche di un dispositivo, o per
+  sotto-oggetti con una vita piuttosto statica (come le uscite dei connettori in
+  drm con tutti gli attributi per la sovrascrittura delle rilevazioni). O magari
+  solo il vostro sistema di test ha bisogno di una certa interfaccia, e allora
+  debugfs (che non ha un'interfaccia stabile) sarà la soluzione migliore.
+
+Per concludere. Questo gioco consiste nel fare le cose giuste fin da subito,
+dato che se il vostro driver diventa popolare e la piattaforma hardware longeva
+finirete per mantenere le vostre ioctl per sempre. Potrete tentare di deprecare
+alcune orribili ioctl, ma ci vorranno anni per riuscirci effettivamente. E
+ancora, altri anni prima che sparisca l'ultimo utente capace di lamentarsi per
+una regressione.
diff --git a/Documentation/translations/it_IT/process/index.rst b/Documentation/translations/it_IT/process/index.rst
index 8d4e36a07ff4..25602c1a97d1 100644
--- a/Documentation/translations/it_IT/process/index.rst
+++ b/Documentation/translations/it_IT/process/index.rst
@@ -58,6 +58,7 @@ perché non si è trovato un posto migliore.
    adding-syscalls
    magic-number
    volatile-considered-harmful
+   botching-up-ioctls
    clang-format
    ../riscv/patch-acceptance
 
-- 
2.30.2

Powered by blists - more mailing lists

Powered by Openwall GNU/*/Linux Powered by OpenVZ