Înainte de a afla despre gestionarea memoriei în Windows, trebuie mai întâi să înțelegeți ce este un proces. Programul este un fișier EXE care poate fi rulat din Windows în mai multe moduri. După pornire, programul devine un proces. Procesul are propria sa memorie, descriptori de fișiere și alte resurse de sistem. Dacă executați același program de două ori la rând, veți obține două procese separate.
Dispozitiv de memorie
- fișierul EXE al programului;
- toate DLL-urile non-sistem încărcate de programul dvs. (inclusiv MFC DLL-uri)
- datele globale ale programelor (disponibile atât în citire și scriere, cât și în lectură);
- stack-ul programului;
- memorie alocată dinamic, inclusiv biblioteca Windows heap și runtime C;
- fișiere proiectate în memorie;
- blocuri de memorie partajate de mai multe procese;
- o memorie locală pentru un fir executabil dat;
- blocuri speciale de memorie de sistem, inclusiv tabele de memorie virtuală;
- kernel și DLL componente ale Windows.
Cum este gestionată memoria virtuală
Momentul citirii și scrierii paginii (pentru a atinge performanța maximă) determină managerul de memorie virtuală Windows. Dacă un proces nu utilizează pagina pentru o anumită perioadă de timp și este nevoie de această memorie de un alt proces, această pagină este descărcată din memorie, iar pagina este încărcată în locul noului proces.
Toate procesele au o singură mare nivel de sistem de fișiere de paginare (swap file), care sunt plasate (dacă este cazul), toate tipurile de date „scrie și să citească“ și un fel de date este „doar pentru citire.“ (Windows NT sprijină funcționarea simultană a mai multor fișiere de paginare.) Windows determină dimensiunea fișierului de swap, în funcție de dimensiunea spațiului RAM și pe disc, dar există modalități pentru a ajusta dimensiunea și locația fizică a fișierului.
Funcția VirtualAlloc: memorie transferată și rezervată
Dacă programul are nevoie de memorie alocată dinamic, atunci mai devreme sau mai târziu va trebui să apeleze funcția VirtualAlloc. Cel mai probabil, nu-l numiți un programator, ci o funcție Windows sau o bibliotecă runtime C care alocă memoria din heap. Știind cum funcționează VirtualAlloc, poți înțelege mai bine funcțiile care se referă la el.
Funcții de gestionare a memoriei
O grămadă de vânturi și familia de funcții GlobalAlloc
O grămadă este o piscină de memorie pentru orice proces. Atunci când un program are nevoie de un bloc de memorie onavyzyvaet funcția alocă memorie din heap și de a elibera memoria alocată anterior, ¥ funcție, prima pereche. Alinierea la granițe, un multiplu de 4 KB, în acest caz nu este efectuată; Managerul heap folosește spațiu în paginile alocate anterior sau accesează VirtualAlloc. pentru a obține pagini suplimentare. Una dintre cele două grămezi cu care funcționează programul este grămada de Windows. Pentru a aloca memorie de la ea, utilizați funcția HeapAlloc. și să elibereze funcția HeapFree. HeapAlloc este util în special pentru alocarea blocurilor de memorie "mari".
O grămadă de bibliotecă De la perioada de execuție, hehemin și C ++ sunt operatorii noi și eliminați
Cu toate acestea, Windows ciorchine (și funcția HeapAlloc) ¯ nu este un morman, care va lucra cea mai mare parte a cererii. Există un alt heap "este condus de biblioteca runtime C (cu bibliotecă RunTime, CRT). Accesul la CRT-heap implementat funcțiile malloc și libere, apelanții directe C ++ noi și șterge. Această grămadă este optimizată pentru a aloca blocuri de dimensiuni mici.
Desigur, funcția malloc numește VirtualAlloc, dar o face foarte inteligent. Când numit mai întâi rezervă o dimensiune regiune de 1 Mb (în versiunile viitoare ale Visual C ++, aceste valori pot varia) și transmite un bloc de memorie, a cărui dimensiune este un multiplu de 64 KB (dacă malloc cauzată de a aloca dimensiunea memoriei de 64K sau mai puțin, un 64-Kbyte alocate bloc de apeluri consecutive în memoria este alocată, în măsura în care este posibil din acest bloc ;. în caz contrar managerul heap determină VirtualAlloc să transmită mai multă memorie După ce regiunea de 1 Mb este consumată, malloc alocă o altă zonă de dimensiunea de 2 MB, apoi celălalt, dar .. deja dimensionate 4 MB de memorie, și așa cum este necesar trecerea prin.
Dacă procesul alocă o mulțime de memorie din halda CRT și apoi eliberează cea mai mare parte a acelei memorii, toate paginile rămân angajate. Deși este posibil ca RAM să nu fie alocată, procesul face pagini din fișierul swap care rămân indisponibile altor procese. Atunci când apelați o altă funcție CRT, _heapmin. managerul heap returnă toate paginile gratuite și, în plus, eliberează toate regiunile returnate complet.
Fișiere mapate în memorie și memorie partajată
Puteți crea o mapare a fișierelor utilizând funcția CreateFileMapping. Pentru a deschide un afișaj existent cu un anumit nume, aplicațiile pot utiliza funcția OpenFileMapping. Funcția MapViewOfFile afișează o porțiune a fișierului într-un bloc de memorie virtuală.
O caracteristică a fișierelor afișate în memorie este utilizarea în comun a acestora de către diferite aplicații, adică dacă două aplicații au deschis o mapare a fișierelor cu același nume, atunci au creat, de fapt, un bloc de memorie partajată.
Nu este necesar să utilizați un fișier de disc dacă trebuie doar să transferați câteva octeți între aplicații? De fapt, nu este nevoie să deschideți și să utilizați în mod explicit un fișier disc pentru a obține un afișaj în memorie. Aplicațiile pot transmite o semnificație specială în descriptor funcția 0hFFFFFFFF CreateFileMapping pentru afișare direct în fișierul de sistem de paginare. Aceasta, de fapt, creează un bloc de memorie partajată.
Câteva sfaturi pentru a lucra cu memorie dinamică
Cu cât este mai intensă mormanul, cu atât este mai fragmentată și cu cât programul funcționează mai lent. Dacă se presupune că timpul de funcționare continuă a programului va fi calculat în ore sau zile, atunci trebuie făcută prudență. Este mai bine să alocați toată memoria necesară la pornirea programului și să îl eliberați atunci când acesta este închis, dar acest lucru nu este întotdeauna posibil. Acest lucru poate fi împiedicat de clasa CString, care alocă în mod constant și eliberează mici porțiuni de memorie. Cu toate acestea, dezvoltatorii MFC au făcut recent o serie de îmbunătățiri.
În cazul în care programul este excretat în principal în blocuri mici, dar necesită uneori blocuri 6olshih (luându-le pentru un timp, diferit de cel pe care este nevoie de blocuri mici), atunci ar trebui să se gândească la alocarea de blocuri mari funcția HeapAlloc. dar nu noi. Acest lucru va reduce într-o oarecare măsură gradul de fragmentare a haldei CRT. Nu uitați să faceți ocazional. Ar trebui să aibă mare grijă a fost primit sau că blocul de aplicare memorie ¯ nu trece o problemă gravă în cazul în care, de exemplu, va provoca HeapFree pentru indicatorul obținut de noi.
Trebuie remarcat faptul că mărimea stivei poate fi așa cum ar trebui să fie. Pentru că acum nu există nici o limită la 64 KB, stiva poate fi plasat obiecte de dimensiuni mari, ceea ce reduce nevoia de alocare de memorie din heap.