Come posso allocare memoria su Linux senza eseguire l'overcommit
Questa è una domanda carica, o almeno errata. La domanda si basa su un presupposto errato, che rende la risposta alla domanda dichiarata irrilevante nella migliore delle ipotesi, fuorviante nella peggiore.
L'overcommit della memoria è una politica a livello di sistema, perché determina la quantità di memoria virtuale resa disponibile ai processi, e non qualcosa che un processo può decidere da solo.
Spetta all'amministratore di sistema determinare se la memoria è sottoposta a overcommit o meno. In Linux, la politica è abbastanza regolabile (vedi ad esempio /proc/sys/vm/overcommit_memory
nell'uomo 5 proc. Non c'è nulla che un processo possa fare durante l'allocazione che influisca sulla policy di overcommit della memoria .
OP sembra anche interessato a rendere i propri processi immuni al killer di memoria insufficiente (OOM killer) in Linux. (OOM killer in Linux è una tecnica utilizzata per alleviare la pressione della memoria, uccidendo i processi e quindi rilasciando le loro risorse nel sistema.)
Anche questo è un approccio scorretto, perché l'OOM killer è un processo euristico, il cui scopo non è "punire o uccidere i processi che si comportano male", ma mantenere il sistema operativo. Questa funzione è anche abbastanza regolabile in Linux e l'amministratore di sistema può persino regolare la probabilità che ogni processo venga interrotto in situazioni di elevata pressione della memoria. A parte la quantità di memoria utilizzata da un processo, non spetta al processo determinare se il killer OOM lo interromperà durante situazioni di memoria insufficiente; anch'esso è un problema di politica gestito dall'amministratore di sistema e non dai processi stessi.
Ho pensato che la vera domanda che l'OP sta cercando di risolvere sia come scrivere applicazioni o servizi Linux in grado di rispondere dinamicamente alla pressione della memoria, oltre a morire (a causa di SIGSEGV o del killer OOM). La risposta è non lo fai -- lasci che l'amministratore di sistema si preoccupi di ciò che è importante per loro, nel carico di lavoro che hanno, invece --, a meno che la tua applicazione o servizio non sia uno che utilizza molta, molta memoria, ed è quindi probabile che venga ucciso ingiustamente durante la memoria alta pressione. (Soprattutto se il set di dati è sufficientemente grande da richiedere l'abilitazione di una quantità di swap molto maggiore di quella che sarebbe altrimenti abilitata, causando un rischio maggiore di tempesta di swap e OOM killer tardivo ma troppo forte.)
La soluzione, o almeno l'approccio che funziona, è bloccare in memoria le parti critiche (o anche l'intera applicazione/servizio, se funziona su dati sensibili che non dovrebbero essere scambiati su disco), o utilizzare una mappa di memoria con un file di supporto dedicato. (Per quest'ultimo, ecco un esempio che ho scritto nel 2011, che manipola un set di dati delle dimensioni di un terabyte.)
Il killer OOM può ancora interrompere il processo e si verifica ancora un SIGSEGV (a causa, ad esempio, di un'allocazione interna da parte di una funzione di libreria a cui il kernel non riesce a fornire il supporto della RAM), a meno che tutta l'applicazione non sia bloccata sulla RAM, ma almeno il servizio/processo non è più ingiustamente mirato, solo perché utilizza molta memoria.
È possibile catturare il segnale SIGSEGV (che si verifica quando non c'è memoria disponibile per supportare la memoria virtuale), ma finora non ho visto un caso d'uso che giustifichi la complessità del codice e lo sforzo di manutenzione richiesto.
In sintesi, la risposta corretta alla domanda posta è no, non farlo .