web-dev-qa-db-fra.com

Qu'est-ce qu'un «coup de mémoire»?

Je viens de venir à travers ce billet de blog qui mentionne "stomping memory":

un programme C++ qui est facilement capable de piétiner la mémoire (quelque chose dont vous n'avez probablement jamais entendu parler si vous étiez né dans un monde de code managé.)

Et en fait je n'en ai jamais entendu parler!

Alors, qu'est-ce que c'est, une mémoire stomping, stomping memory? Quand cela se produit-il?

90
scravy

La mémoire est "écrasée" lorsqu'un morceau de code manipule la mémoire sans se rendre compte qu'un autre morceau de code utilise cette mémoire d'une manière conflictuelle. Il existe plusieurs façons courantes de mémoriser la mémoire.

L'un alloue, disons, 100 octets de mémoire, mais stocke ensuite quelque chose au-delà de la 100e adresse. Cette mémoire peut être utilisée pour contenir quelque chose de complètement différent. Cela est particulièrement difficile à déboguer car le problème apparaîtra lorsque quelque chose tente d'accéder à la victime qui a été piétinée et le code qui l'a piétiné peut être totalement indépendant.

Un autre accède à la mémoire après sa libération. La mémoire peut être allouée à un autre objet. Encore une fois, le code qui montre le problème peut être lié à l'objet nouvellement alloué qui a obtenu la même adresse et sans rapport avec le code à l'origine du problème.

113
David Schwartz

Très souvent, il s'agit d'un dépassement de tampon; à titre d'exemple, ce code:

char buffer[8];
buffer[8] = 'a';

"piétinera" tout ce qui se trouvera dans la prochaine chose en mémoire après buffer. D'une manière générale, "piétiner", c'est quand la mémoire est écrite involontairement.

32
IronMensan

Les autres réponses sont fondamentalement correctes, mais je voudrais donner un exemple.

int a[10], i;       
for (i = 0; i < 11 ; i++)
    a[i] = 0;

int i, a[10];     
for (i = 0; i < 11 ; i++)
    a[i] = 0;

Ces échantillons peuvent conduire à une boucle infinie (ou ne pas conduire), car il s'agit d'un comportement non défini.

La variable i très probablement en mémoire est stockée juste après le tableau. Donc, accéder à a[10] pourrait en fait accéder à i en d'autres termes, il pourrait réinitialiser le compteur de boucles.

Je pense que c'est un bon exemple qui démontre que la mémoire "piétine".

8
ST3