- Práce s pamětí uživatelských procesů (aplikací) se liší od OS
- Dva základní typy
- zásobník (stack)
- halda (heap)
- Obvykle řeší běhové prostředí (např. JVM) či standardní knihovna (např. dlmalloc)
Linux - ptmalloc
ptmalloc
(verze 3, Céčko)- rozhraní
malloc, free, realloc, ...
- od OS získá souvislý blok paměti (pomocí systémového volání
brk/sbrk
či mapování souborů do paměti/dev/zero
)
-
brk()
… argument je adresa “do které” má pamět rozšířit -
sbrk()
… argument je velikost o kterou má být paměť rozšířena -
uvolnění je jednoduché, ale způsobuje fragmentaci (do
size
se uvede záporná hodnota) -
bloky zaokrouhleny na dvojnásobek velikosti slova (32/64 bitů) → minimálně 8 B
-
každé vlákno může mít svůj alokátor
-
nejmenší alokovatelný blok jsou 4 slova
-
vždy začíná/vrací sudý násobek slova
-
malloc
nejdříve hledá volný blok, který byl již uvolněn, pokud nenajde → oblast se rozšíří- hledání pomocí 2 strategií - FIFO v seznamech, best fit ve stromech
-
alokátor si udržuje informaci o tom, které bloky byly uvolněny
- menší bloky v 32 frontách
- větší bloky v 16 trie
- ostatní (největší) mají speciální strom
-
zavolání
free
funguje na principu buddy systému pro následující a předchozí blok (slučování)
Windows
- API + frontend + backend
- každý objekt má hlavičku (8 B)
- frontend
- optimalizuje alokaci menších bloků
- 2 strategie
- LAL (look aside list) - 127 s objekty velikosti
n * 8 B
- LF (low fragmentation) - až pro objekty do 16 kB
- LAL (look aside list) - 127 s objekty velikosti
- backend
- podobný ptmalloc
- velké bloky přímo přes VM
- není k dispozici malý → rozdělí se větší
Garbage collector
- Automatická správa paměti
- zjednodušený vývoj aplikací na úkor režie počítače (a aplikace jsou pomalejší)
- escape analysis - analýza zda daný objekt může uniknout z daného kontextu (např. funkce)
- region/aréna = alokace velkého bloku paměti (předpoklad na společné uvolnění, menší režie než
malloc
afree
) - jak řešit automatickou správu?
- počítání odkazů - (ARC … automatic reference counting)
- kolik na něj odkazuje objektů ⇒ pokud 0, tak smažu
- např. PHP, Python
- problém cyklické závislosti
- řeší to překladač (Swift, ObjectiveC)
- objekty rozděleny do 3 množin
- bílé - kandidáti na uvolnění
- šedé - odkazované z kořenu (musí se prověřit)
- černé - mají odkazy na bílé objekty
- algoritmus
- jeden šedý objekt se přebarví na černo
- z něj odkazovné bílé objekty se barví na šedo
- opakuje se dokud existují šedé
Varianty GC
- přesunující vs nepřesunující
- přeskupení objektů, aby vytvořily souvislý blok
- generační
- předpoklad: krátce žijící objekty budou žít krátce
- u starších objektů nemusí probíhat sběr příliš často
- přesné vs konzervatinví
- v Javě, .NET
- odhadují zda je daná část objektu ukazatel
- finalizace: fronta objektů ke zrušení (
finalize()
, není zaručeno zda bude vůbec zavolána a kdy, spíše NEPOUŽÍVAT)
- inkrementální vs stop the world
- inkrementální uvolňuje objekty po menších částech
- stop the world vše uvolní najednou (musí se zastavit)
- vylepšení paralelním zpracováním
- mark and sweep
- každý objekt má příznak zda-li se používá
- při úklidu se objekty podle potřeby označí a ty neoznačené se uvolní
- nevýhody: špatná cache, vnější fragmentace
- kopírující GC
- přesouvá objekty mezi aktivní a neaktivní částí (kopírovaných objektů je značně méně - jsou to ty aktivní)
- řeší problémy “mark and sweep”
- následující vizualizace je animace (gif)