In Java il vecchio modo di memorizzare un segreto, come ad esempio una password, era usare char[]
in quanto si poteva sovrascrivere i propri dati quando si era finito con esso. Tuttavia, da allora è stato dimostrato che non è sicuro poiché il garbage collector copierà le cose mentre riorganizza l'heap. Su alcune architetture è possibile che una pagina venga liberata e il segreto rimarrà quando qualche altro programma assegna quella stessa pagina.È possibile archiviare segreti nello stack in java?
Questo è orribilmente brutto, ma cosa succede se il segreto è stato memorizzato nella pila del metodo run
di Thread? Sarebbe comunque necessario fare attenzione a terminare il thread con garbo, in modo che potesse azzerare i suoi dati, ma questo problema era presente anche nel vecchio modo.
Uno dei problemi principali che vedo subito è che non riesco a pensare a un modo sicuro per ottenere dati dentro e fuori dal container. È possibile ridurre al minimo la probabilità di un segreto trapelato utilizzando flussi con buffer interni molto piccoli, ma alla fine si finisce con lo stesso problema di char[]
. [Modifica: un singolo membro private static byte
e una bandiera funzionano? Sebbene ciò ti limiti a un segreto per ClassLoader. Questo aggiunge più bruttezza, ma potrebbe essere abbastanza facile nascondersi dietro un'interfaccia ben scritta.]
Quindi ho un sacco di domande, davvero.
Lo stack è più sicuro da questi tipi di attacchi rispetto all'heap? Esistono meccanismi Java puri per eseguire una copia da stack a stack tra due diversi stack frame in un modo che sarebbe utile a questo problema? In caso contrario, la JVM supporta anche questo tipo di operazione in bytecode?
[Modifica: Prima che le persone si preoccupino troppo, questo è più di un esperimento mentale che altro. Non ho assolutamente intenzione di "provare in produzione" o di usarlo in qualsiasi progetto corrente. Mi rendo conto che quello di cui sto parlando è davvero brutto, probabilmente orribilmente ingombrante e funziona contro l'intera struttura JVM. Mi interessa sapere se è possibile, se effettivamente raggiunge i miei obiettivi e che tipo di eroismo ci vorrebbe per realizzarlo.]
Se sei legittimamente preoccupato per un utente malintenzionato che ottiene l'accesso a dati come questo, è probabile che tu sia fottuto comunque, perché ogni attaccante abbastanza sofisticato da essere preoccupato a questo livello è abbastanza sofisticato da infrangere la maggior parte qualsiasi cosa tu possa lanciarli contro di loro –
In linea di massima sono d'accordo, ma questo è un argomento molto povero per chiudere una minaccia. In ogni caso, ho iniziato questo percorso quando esaminavo un elenco di requisiti di sicurezza forniti dal mio cliente. Uno è che abbiamo sempre a zero i segreti in memoria. In caso contrario, verrà preso dal cliente in revisione. Il client è abbastanza intelligente da capire che 'char []' non funzionerà, tuttavia impongono anche l'uso di Java. Fortunatamente sono persone ragionevoli, riconoscono il conflitto e non è una preoccupazione troppo grande. Ma mi ha fatto pensare ... –
argomento molto povero contro la chiusura di una minaccia * - scusate, modifica il periodo di tempo scaduto. –