Professional Documents
Culture Documents
UE20CS501 Computer Systems For Programmers: Unit-05: Virtual Memory
UE20CS501 Computer Systems For Programmers: Unit-05: Virtual Memory
UE20CS501 Computer Systems For Programmers: Unit-05: Virtual Memory
Santhosh Kumar V
Department of Computer Science & Engineering
Computer Systems for Programmers
Unit-05: Virtual Memory
Topic:
Dynamic Memory Allocation,
Garbage Collection, Memory bugs.
Santhosh Kumar V
Department of Computer Science & Engineering
05/28/2024 UE20CS501 2
Overview
CS:APP 9.9.1
Memory / RAM
• Heap management is an important
component that affects program
0xfffffffc
-
User stack 0x80000000
}
– Memory utilization (reduce Heap
wasted areas)
Uninitialized Data
(.bss)
I n i t i a l i z e d Data
programmer Code ( . t e x t )
0x00400000
-
Dynamic Memory Allocation
int x, y[10]; Memory
Application invisible to
main() Kernel virtual memory
user code
Dynamic Memory Allocator {
User stack
int a, b[10]; (created at runtime)
Heap int *c; %rsp
c = malloc(10); (stack
• Programmers use dynamic func(); pointer)
• void
block* c a l l o c ( s i z e _ t nmemb, s i z e _ t s i z e ) User stack 0x80000000
– Allocates nmemb*size bytes, sets the memory to 0,
returns a pointer to the block
-
• void f re e ( v o id * p t r ) function
Memory-mapped
– Frees the block at address ptr (returned by malloc/calloc), Regions f o r shared
libraries
returns it to the system for re-use by subsequent malloc calls
... malloc
i n t main() { Heap allocates:
i n t num; scores[3] 0x0006de4c
printf("How many s t u d e n t s ? \ n " ); scores[2]
scanf("%d", &num); scores[1] 0x0006de48
scores[0]
Uninitialized Data 0x0006de44
/ / cast “ ( i n t * ) ” from vo id * not necessary i n C
(.bss)
i n t *scores = malloc(num * s i z e o f ( i n t ) ) ; 0x0006de40
I n i t i a l i z e d Data
(.data) 0x10000000
/ / can now access scores[0] . . scores[num-1];
free(scores); / / deallocate -
return 0; Code ( . t e x t )
}
0x00400000
-
OS & the Heap
• The OS kernel maintains the brk
pointer Memory / RAM
– Virtual address of the top of the heap -
0xfffffffc
-
0x10000000
0x00400000
intptr_t is a signed integer type that will match the size of pointers (32- or
64-bits) -
Dynamic Memory Allocation
• Allocator maintains heap as collection of variable sized
blocks, which are either allocated or free
• Types of allocators
– Explicit allocator: application allocates and frees space
• E.g., malloc and free in C
Memory-mapped
= sbrk( 1 << 20) ; / / 1 MB Regions f o r shared
– h e a p _ in i t libraries
– void *heap_init;
- new brk
o r i g brk
Uninitialized Data
(.bss)
I n i t i a l i z e d Data
(.data) 0x10000000
-
Code ( . t e x t )
0x00400000
-
10.11
memory areas -
brk
Heap
allocated
free allocated
free
allocated alloc
free Hea allocated
p
Uninitialized Data
(.bss)
I n i t i a l i z e d Data
(.data) 0x10000000
-
Code ( . t e x t )
0x00400000
-
A First Look at malloc (3)
• The C-library implementation will provide Memory / RAM
0xfffffffc
an implementation to manage the heap -
0x80000000
• At startup, the C-Library will allocate an
User stack
-
new brk
• Calls to free or delete will reclaim those Heap
o ld brk
memory areas
Heap
allocated
free allocated
free
allocated alloc
Hea
• If there is not enough contiguous free heap
free allocated
p
Uninitialized Data
(.bss)
memory to satisfy a call to malloc/new I n i t i a l i z e d Data
(.data)
then the library will use sbrk to increase
0x10000000
-
• Types:
-
– Explicit Allocator: Requires the Memory-mapped
Heap
allocated
free allocated
garbage collection) -
Code ( . t e x t )
Heap
allocated
free allocated
– Allocated blocks must be aligned to any type of free
allocated
Hea
alloc
free allocated
data p
Uninitialized Data
(.bss)
• Previously allocated blocks may not be I n i t i a l i z e d Data
(.data)
moved -
0x10000000
p1 = malloc(4*SIZ)
p2 = malloc(5*SIZ)
p3 = malloc(6*SIZ)
free(p2)
p4 = malloc(2*SIZ)
Allocator Goals
• Maximize throughput (i.e., fast allocation / deallocation)
• Maximize memory utilization
– Take as little memory as possible from the OS with sbrk
The .g., ays
– We need a formal definition of peak memory utilization
•
se no n allo
E
Hk
alw
(Monotonically non-decreasing.)
t o p tra block
to e new
k (~time)
dds ck s w
(co of fr ith s
nfli ee
ctin bloc r
g)wit
he
ks
b
Fragmentation
• Poor memory utilization is caused by fragmentation
• Sections of memory (that are free) but can’t be used to store data, and
cannot be used to satisfy allocation requests.
• Two kinds
– External: Many small fragments of free space between allocated blocks
– Internal: When payload of is smaller than the block size allocated
• Often used when fixed size "chunks" are allocated
• Notice: There may be enough total free memory for a request but not
contiguous free memory
External Fragmentation
allocated free
Internal Fragmentation
Block
Internal Internal
Payload
fragmentation fragmentation
• Caused by
– Overhead of maintaining heap data structures
– Padding for alignment purposes
– Explicit policy decisions
(e.g., to return a big block to satisfy a small request)
• Depends only on the pattern of previous requests
– Thus, easy to measure
External Fragmentation #define SIZ sizeof(size_t)
• Occurs when there is enough aggregate heap memory, but no single free block is large
enough
• Caused due to alloc/free pattern leaving “holes(free mem)” between allocated blocks
p1 = malloc(4*SIZ)
p2 = malloc(5*SIZ)
p3 = malloc(6*SIZ)
free(p2)
– Requires an extra word for every allocated block size Payload Padding
(aligned) (for alignme
block free(p0)
Keeping Track of Free Blocks
• Method 1: Implicit list using length—links all blocks
Need to tag
Unused each block as
32 48 32 16 allocated/free
Need space
32 48 32 16 for pointers
pointer
explicitly Payload
returned from
heap_start
to make new allocations Padding/Footer
End
Unused Block
Start
of 16/0 32/1 64/0 32/1 8/1
heap
heap_start heap_end
1 word
Need space
32 48 32 16 for pointers
Size a Size a
slide) Empty
Empty
Padding/Footer
Padding/Footer
Implicit Memory Management: Garbage Collection
Not-reachable
(garbage)
A node (block) is reachable if there is a path from any root to that node.
Non-reachable nodes are garbage (cannot be needed by the application)
Mark and Sweep Collecting
• Can build on top of malloc/free package
– Allocate using malloc until you “run out of space”
• When out of space:
– Use extra mark bit in the head of each block
– Mark: Start at roots and set mark bit on each reachable block
– Sweep: Scan all blocks and free blocks that are not marked
root Note: arrows
here denote
Before mark memory refs, not
free list ptrs.
• Application
– new(n): returns pointer to new block with all locations cleared
– read(b,i): read location i of block b into register
– write(b,i,v): write v into location i of block b
• ->, (), and [] have high precedence, with * and & just below
•Unary +, -, and * have higher precedence than binary forms
...
scanf(“%d”, val);
Reading Uninitialized Memory
• Assuming that heap data is initialized to zero
/* return y = Ax */
int *matvec(int **A, int *x) {
int *y = malloc(N*sizeof(int));
int i, j;
int **p;
p = malloc(N*sizeof(int));
int **p;
p = malloc(N*sizeof(int *));
/* reads “123456789”
from stdin */
gets(s);
return p;
}
Overwriting Memory
• Referencing a pointer instead of the object
it points to
int *BinheapDelete(int **binheap, int *size) {
int *packet;
packet = binheap[0];
binheap[0] = binheap[*size - 1];
*size--;
Heapify(binheap, *size, 0);
return(packet);
}
Referencing Nonexistent Variables
• Forgetting that local variables disappear
when a function returns
int *foo () {
int val;
return &val;
}
Freeing Blocks Multiple Times
• Nasty!
x = malloc(N*sizeof(int));
<manipulate x>
free(x);
y = malloc(M*sizeof(int));
<manipulate y>
free(x);
Referencing Freed Blocks
• Evil!
x = malloc(N*sizeof(int));
<manipulate x>
free(x);
...
y = malloc(M*sizeof(int));
for (i=0; i<M; i++)
y[i] = x[i]++;
Failing to Free Blocks (Memory Leaks)
• Slow, long-term killer!
foo() {
int *x = malloc(N*sizeof(int));
...
return;
}
Failing to Free Blocks (Memory Leaks)
• Freeing only part of a data structure
struct list {
int val;
struct list *next;
};
foo() {
struct list *head = malloc(sizeof(struct list));
head->val = 0;
head->next = NULL;
<create and manipulate the rest of the list>
...
free(head);
return;
}
05/28/2024 UE20CS501 51
Dealing With Memory Bugs
• Debugger: gdb
– Good for finding bad pointer dereferences
– Hard to detect the other memory bugs
• Data structure consistency checker
– Runs silently, prints message only on error
– Use as a probe to zero in on error
• Binary translator: valgrind
• allocating the wrong size, using an uninitialized pointer,
accessing memory after it was freed, overrunning a buffer, and
so on.
– Powerful debugging and analysis technique
– Rewrites text section of executable object file
– Checks each individual reference at runtime
• Bad pointers, overwrites, refs outside of allocated block
• glibc malloc contains checking code
– setenv MALLOC_CHECK_ 3
THANK YOU
Santhosh Kumar V.
Department of Computer Science & Engineering
05/28/2024 UE20CS501 53