2010-09-24 13 views
8

Sto scrivendo un programma (un proverbio del teorema come accade) il cui requisito di memoria è "il più possibile, per favore"; cioè, può sempre fare meglio usando più memoria, per scopi pratici senza limite superiore, quindi quello che in realtà deve fare è usare solo la quantità di memoria disponibile, né più né meno. Posso capire come dare la priorità ai dati per cancellare il valore più basso quando la memoria è breve; il problema che sto cercando di risolvere è come capire quando questo sta accadendo.Mantenere l'utilizzo della memoria entro l'importo disponibile

Idealmente mi piacerebbe una chiamata di sistema che restituisca "quanta memoria è rimasta" o "siamo ancora fuori memoria?"; per quanto posso dire, nessuna cosa del genere esiste?

Ovviamente, malloc può segnalare l'esaurimento della memoria restituendo 0 e il nuovo può chiamare un gestore; questi non sono segnali ideali, ma sarebbero meglio di niente. Un problema, tuttavia, è che voglio veramente sapere quando la memoria fisica sta per scadere, quindi posso evitare di andare in profondità nello swap e quindi fermare tutto; Suppongo che non ci sia modo di chiedere "dobbiamo ancora scambiare?" o dire al sistema operativo "non scambiare sul mio account, semplicemente fallire le mie richieste se si tratta di questo"?

Un altro approccio sarebbe quello di scoprire quanta RAM è nella macchina e monitorare la quantità di memoria che il programma sta utilizzando al momento. Per quanto ne so, non c'è generalmente modo di dire al primo? Ho anche l'impressione che non ci sia un modo affidabile per dire a quest'ultimo se non avvolgendo malloc/free con una funzione di bookkeeper (che è poi più problematica in C++).

Ci sono approcci che mi mancano?

L'ideale sarebbe una soluzione portatile, ma sospetto che ciò non accadrà. In caso contrario, una soluzione che funziona su Windows e un'altra che funziona su Unix sarebbe buona. In caso contrario, potrei cavarmela con una soluzione che funziona su Windows e un'altra che funziona su Linux.

+0

Bene, tutto quello che posso dire con certezza è che non troverete una soluzione portatile. Oh, e questo non è il compito più facile. – sbi

+1

Su Linux: http://linux.die.net/man/2/getrusage forse? Su Windows: GetProcessMemoryInfo forse? –

risposta

6

Penso che il modo più utile e flessibile per utilizzare tutta la memoria disponibile sia consentire all'utente di specificare la quantità di memoria da utilizzare.

Lascia che l'utente lo scriva in un file di configurazione o tramite un'interfaccia, quindi crea un allocatore (o qualcosa di simile) che non fornirà più di questa memoria.

In questo modo, non è necessario trovare le statistiche sul computer corrente in quanto ciò sarà sempre influenzato dal fatto che il sistema operativo potrebbe anche eseguire altri programmi. Non parliamo nemmeno del modo in cui il sistema operativo gestirà la cache, le differenze tra 32 e 64 bit che rendono lo spazio degli indirizzi limitano le allocazioni, ecc.

Alla fine, l'intelligenza umana (presupponendo che l'utente sia a conoscenza del contesto di utilizzo) è meno costosa da implementare se fornita dall'utente.

+0

Questa è la strada giusta da percorrere: la pressione della memoria potrebbe essere causata comunque da altre applicazioni in esecuzione. – caf

1

La soluzione migliore che posso pensare potrebbe essere quella di interrogare quanti errori di pagina si sono verificati all'interno, ad esempio, nell'ultimo secondo. Se ci sono molti scambi in corso, probabilmente dovresti rilasciare un po 'di memoria, e se no, puoi provare ad allocare più memoria.

Su Windows, WMI può probabilmente darvi alcune statistiche che è possibile utilizzare.

Ma è un problema difficile, dal momento che non vi è alcun limite rigido che è possibile chiedere al sistema operativo e quindi rimanere sotto. Puoi continuare ad allocare la memoria ben oltre il punto in cui hai esaurito la memoria fisica, il che significa solo che paralizzerai il tuo processo con uno swap eccessivo.

Quindi il meglio che puoi fare è una sorta di approssimazione.

0

È possibile mantenere l'allocazione della memoria oltre il punto in cui è utile farlo, ovvero ciò che richiede il sistema operativo per lo scambio o la pagina delle cose importanti. Il problema è che non è necessariamente facile dire dove si trova.

Inoltre, se l'attività esegue qualsiasi IO (significativo), sarà necessario lasciarne alcuni per i buffer del sistema operativo.

Suggerisco solo di esaminare quanto c'è nella macchina, quindi di assegnare una quantità in funzione di quella (proporzione, o lasciare alcuni liberi ecc.).

2

Fare affidamento su malloc per restituire 0 quando nessuna memoria è disponibile potrebbe causare problemi su Linux, perché Linux overcommits memory allocations. malloc di solito restituirà un puntatore valido (a meno che il processo non sia fuori dallo spazio di indirizzi virtuale), ma l'accesso alla memoria a cui punta potrebbe attivare lo "OOM killer", un meccanismo che uccide il processo o un altro processo sul sistema. L'amministratore di sistema può tune this behavior.

Problemi correlati