Domanda

realloc viene utilizzato per riallocare la memoria in modo dinamico.

Supponiamo che abbia assegnato 7 byte utilizzando la funzione malloc e ora voglio estenderlo a 30 byte.

Che cosa accadrà in background se non c'è sequenziale (continuamente in una singola riga) spazio di 30 byte nella memoria?

È disponibile uno spazio errori o saranno assegnate in parti?

È stato utile?

Soluzione

realloc lavora dietro le quinte o meno in questo modo:

  • Se non v'è sufficiente spazio libero dietro il blocco corrente per soddisfare la richiesta, estendere il blocco corrente e restituisce un puntatore all'inizio del blocco.
  • Al contrario, se c'è un grande blocco libero abbastanza altrove, quindi allocare quel blocco, copiare i dati dal vecchio blocco sopra, liberare il vecchio blocco e restituisce un puntatore all'inizio del nuovo blocco
  • Else mancato rapporto con il ritorno NULL.

Quindi, è possibile verificare per il mancato testando per NULL, ma essere consapevoli che non sovrascrivere il vecchio puntatore troppo presto:

int* p = malloc(x);
/* ... */
p = realloc(p, y); /* WRONG: Old pointer lost if realloc fails: memory leak! */
/* Correct way: */
{
  int* temp = realloc(p, y);
  if (NULL == temp)
  {
    /* Handle error; p is still valid */
  }
  else
  {
    /* p now possibly points to deallocated memory. Overwrite it with the pointer
       to the new block, to start using that */
    p = temp;
  }
}

Altri suggerimenti

realloc avrà successo solo se si può restituire un contigua ( "sequenziale" nelle tue parole) blocco di memoria. In assenza di tale blocco esiste, ritornerà NULL.

pagina man :

  

realloc () restituisce un puntatore al   appena allocata memoria, che è   opportunamente allineata per qualsiasi tipo di   variabile e può essere diverso da   PTR, o NULL se la richiesta non riesce.

Quindi, in altre parole, per rilevare il fallimento, basta controllare se il risultato è nullo.

EDIT:. Come evidenziato nel commento, se la chiamata non riesce, la memoria originale non viene liberato

In generale, dipende dall'implementazione. Su x 86 (-64) di Linux, credo che lo standard Doug Lea malloc algoritmo sarà sempre allocare un minimo di una pagina standard x86 (4096 byte), in modo per lo scenario che hai descritto sopra, sarebbe solo ripristinare i confini per accogliere i byte in più. Quando si tratta di, per esempio, la riassegnazione di un buffer di 7bytes al PAGE_SIZE + 1 Credo che proverà a destinare alla successiva pagina contigui, se disponibile.

Da leggere quanto segue, se si sta sviluppando su Linux:

  

Per impostazione predefinita, Linux segue una strategia di allocazione della memoria ottimista. Ciò significa che quando malloc () restituisce non-NULL non v'è alcuna garanzia che la memoria è realmente disponibile. Questo è davvero un   Bad bug. Nel caso in cui si scopre che il sistema è fuori della memoria, uno o più processi saranno uccisi dal OOM assassino infame. Nel caso in cui Linux è impiegato in circostanze in cui sarebbe   meno desiderabile perdere improvvisamente alcuni processi selezionati a caso, ed inoltre la versione del kernel è sufficientemente recente, si può disattivare questo comportamento overcommitting usando un comando come:

# echo 2 > /proc/sys/vm/overcommit_memory
     

Si veda anche la directory kernel documentazione, file vm / overcommit-contabile e sysctl / vm.txt.

FreeBSD e Mac OS X hanno la funzione reallocf () che libererà il puntatore passato quando la memoria richiesta non può essere allocata (vedi uomo realloc).

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top