////
Search

메모리관리

Created
2022/09/03 11:08
1 more property

메모리관리에 대해서

우리가 사용하는 메모리는 크게 논리적 주소물리적 주소로 나뉜다.
논리적 주소
물리적 주소
주소 바인딩
상징적 주소 → 논리적 주소 → 물리적 주소
프로그래밍을 할때 우리는 상징적(Symbolic) 주소를 이용하여 프로그래밍을 진행한다.
우리는 변수를 이용하지 직접 메모리 주소를 작성하지 않음

주소 바인딩

주소를 실제 메모리에 연결하는 방법은 크게 3가지로 나뉜다.
Compile time binding
컴파일시 물리적 주소가 정해지는 방식
시작 위치 변경시 재컴파일
컴파일러는 절대 코드(absolute code) 생성
Load time Binding
Loader의 책임하에 물리적 메모리 주소 부여
컴파일러가 재배치가능코드를 생성한 경우 가능
Run time Binding
수행이 시작된 이후에도 프로세스의 메모리 상 위치를 옮길 수 있음
CPU가 주소를 참조할 때마다 binding을 점검
하드웨어적인 지원필요 (MMU)

MMU (Memory Management Unit)

Run time Binding을 지원하기 위한 하드웨어 장치로 2개의 레지스터를 가지고 있다.
Relocation Register
프로세스 메모리의 시작 주소를 가르킨다.
Limit Register
프로세스 메모리의 길이를 나타낸다.
Dynamic Relocation
논리 주소를 물리적 메모리에 재배치 해주는 방식
Hardware Support for Address Translation
자신의 메모리 범위를 벗어난 접근을 하려고 하면 에러발생

Dynamic Loading

프로세스 전체를 메모리에 미리 다 올리는 것이 아니라 해당 루틴이 불려질 때 메모리에 Load 하는 것
메모리 활용성의 향상
가끔씩 사용되는 많은 양의 코드의 경우 유용
운영체제의 특별한 지원 없이 프로그램 자체에서 구현 가능 (OS는 라이브러리를 통해 지원)
프로그래머가 직접 동적 로딩을 하도록 만드는 것

Overlay

메모리에 프로세스의 부분 중 필요한 정보만을 올림
작은 공간의 메모리를 사용하던 초창기 시스템에서 수 작업으로 프로그래머가 구현
Menual Overlay
프로그래밍이 매우 복잡
OS 지원 없이 사용자가 모든것을 직접 구현해야한다.

Swapping

스와핑(Swapping)이란? 프로세스를 일시적으로 메모리에서 Backing store로 쫓아내는 것
Backing store (=swap area)
디스크) 많은 사용자의 프로세스 이미지를 담을 만큼 충분히 빠르고 큰 저장 공간
Swap in / Swap out
일반적으로 중기 스케줄러에 의해 Swap out 시킬 프로세스 선정
priority-based CPU scheduling algorithm
Compile time or Load time binding에서는 원래 메모리 위치로 swap in 해야 함
Run time Binding에서는 추후 빈 메모리 영역 아무 곳에서나 올릴 수 있음
swap time은 대부분 transfer time(swap되는 양에 비례하는 시간)임

Linking

링킹이란 여러 군데 존재하는 목적 파일들을 묶어서 하나의 실행 파일을 만드는 과정을 뜻한다.

Static Linking

라이브러리가 프로그램 실행 파일 코드에 포함
실행 파일의 크기가 커짐
동일한 라이브러리를 각각의 프로세스가 메모리에 올리므로 메모리 낭비

Dynamic Linking

링킹을 실행시간 까지 미루는 기법
라이브러리가 실행 시 연결 됨
라이브러리 호출 부분에 라이브러리 루틴의 위치를 찾기위한 stub이라는 작은 코드를 둠
라이브러리가 이미 메모리에 있으면 그 루틴의 주소로 가고 없으면 디스크에서 읽어옴
운영체제의 도움이 필요함
다이나믹 링킹을 해주는 라이브러리를 Shared Library라고 한다
리눅스의 경우 shared object, 윈도우의 경우 dll

물리 메모리 관리 (Allocation of Physical Memory)

물리적 메모리 관리를 어떻게 관리할 것인가?
메모리는 일반적으로 두 영역으로 나뉘어 사용
OS 상중 영역 = Interrupt vector와 함께 낮은 주소 영역 사용
사용자 프로세스 영역 = 높은 주소 영역 사용

메모리 단편화

외부 조각 (External fragmentation)
프로그램의 크기보다 분할의 크기가 작아서 다른 분할로 들어가야하는 문제
내부 조각 (Internal fragmentation)
프로그램의 크기보다 분할의 크기가 큰 문제

연속 할당 방식(Configuous allocaion)

고정 분할 방식
물리적 메모리를 몇 개의 영구적 분할로 나누어 사용하는 방식
분할의 크기가 모두 동일한 방식과 서로 다른 방식이 존재
분할당 하나의 프로그램 적재
융통성이 없음
동시에 메모리에 로드되는 프로그램수가 고정, 최대 수행 가능 프로그램 제한
Internal fragmentation 발생 (External fragmentation도 발생)
가변 분할 방식
프로그램의 크기를 고려해서 할당
분할의 크기 개수가 동적으로 변함
기술적 관리 기법 필요
External fragmentation 발생
Hole
가용 메모리 공간을 의미한다.
다양한 크기의 Hole들이 메모리 곳곳에 흩어져 있다.
프로세스가 도착하면 수용 가능한 Hole을 할당한다.
Dynamic Storage-Allocation Problem
First-fit
size가 n이상인 것 중에 최초로 찾아지는 hole에 할당
Best-fit
size가 n이상인 가장 작은 hole을 찾아서 할당
hole들의 리스트가 크기순으로 정렬되지 않을 경우 모든 hole의 리스트를 탐색
많은 수의 아주 작은 hole들이 생성
Worst-fit
가장 큰 hole에 할당, 모든 리스트를 탐색, 상대적으로 아주 큰 hole들이 생성
first-fit과 best-fit이 worst-fit보다 속도와 공간 측면에서 효과적이다.
Compaction
메모리 단편화 문제를 해결하는 방법
사용중인 메모리 영역을 한군데로 몰고, hole들을 다른 한곳으로 몰아서 큰 block을 만든다.
매우 비용이 많이 든다 → 바인딩을 다 관리해야되서
최소한의 메모리 이동으로 compaction을 하는 방법 → 매우 복잡한 문제
compaction은 프로세스의 주소가 실행 시간에 동적으로 재배치 가능한 경우에만 수행될 수 있다.

비연속 할당 방식(Conconfiguous allocaion)

비연속 할당방식은 연속 할당방식의 단편화 문제에서 비교적 자유로울 수 있는 현대적인 방법이다.

Paging

프로세스가 구성하는 주소 공간을 같은 크기의 Page로 잘라서 관리하는 기법
Paging 기법은 Logical address를 Page 단위로, Physical address를 같은 크기인 Frame 단위로 나누어 올리고 접근
Page Table
왜 Page Table이 필요한가?
프로세스를 일정한 크기의 페이지로 쪼갰기 때문에 이를 접근하기 위해서는 메모리 변환과정이 필요하기 때문에 페이지의 위치를 저장해두는 테이블이 필요하다.
페이지테이블은 각각의 프로세스마다 존재
Page기법 이용시의 MMU 레지스터는 무슨 역할을 하는가?
page-table base register(PTBR)가 page table을 가리킨다
page-table length register(PTLR)이 테이블의 크기를 보관
Page Table은 어디에 위치해 있는가?
Page Table은 물리 메모리에 존재한다.
이유인 즉슨, 관리해야하는 엔트리의 수가 많아서 레지스터로는 감당이 안된다.
때문에 메모리 변환과정에서 물리메모리 접근 → 물리메모리 접근이라는 오버헤드가 발생한다!
TLB(Translation Look-aside Buffer)이란 무엇인가?
Page 고속 접근을 위한 일종 Cache - 변환의 오버헤드가 존재하기 때문에 이용한다.
병렬탐색 레지스터인 Associative register를 통해서 보다 빠르게 이용이 가능하다.
TLB는 context switch 때 flush(오래된 엔트리를 비운다)
Two-Level Page Table
참고이미지
현대의 컴퓨터는 매우 큰 주소체계를 가진다. (32, 64 Bit)
Page Table은 모든 프로세스가 하나씩 가지지만 사용하는 Page는 일부에 불과하다. 결과적으로 사용하지 않는 Page Table은 메모리의 낭비로 이어지게 된다.
32Bit 시스템 기준으로 4G의 주소 공간 표현이 가능하다.
이 시스템에서 Page size가 4KB라면 1MB 개의 페이지 엔트리가 필요하고, 한개의 엔트리는 4Byte 정도기 때문에 프로세스마다 4MB의 Page Table이 필요함.
때문에 이런 메모리 낭비를 막아보고자 등장한것이 이중 페이지 테이블이다.
메모리 낭비를 막는 이론
32bit 중 12bit는 offset을 표현하는 데 사용함
남은 20bit로 페이지를 접근하면 4Byte로 프로세스마다 4MB의 페이지 테이블이 필요한데 사실 다쓰는것도 아니고 미리 할당하기에는 너무 낭비가 많음
여기서 앞서 20Bit를 다시 10Bit 씩 나누어 두 계층으로 테이블 구조를 사용하게 됨
Outer 페이지 테이블이 Inner 페이지 테이블을 Null 값으로 설정해서 메모리 낭비를 막을 수 있음
단, 변환 과정을 2번 거치는 만큼 오버헤드가 크다.
Valid / Invalid Bit
페이지 테이블이 사용되고 있다면 V(Valid)
페이지 테이블이 사용되고 있지 않다면 I(Invalid)
Inverted Page Table
메모리 구조의 역전
시스템 내에 페이지 테이블이 하나만 존재하게 됨
프로세스 기준이 아닌 물리 메모리의 frame 갯수만큼 존재하게 된다.
따라서 어떤 프로세스의 페이지인지 알기 위해서 PID가 함께 저장되어야 한다.
CPU는 논리 주소의 pid와 p와 맞는 entry를 찾기 위해 page table을 모두 서치한다.
공간적 이득은 큼 하지만 모든 엔트리에 접근하기 때문에 병렬적으로 서치해야한다. (오버헤드 발생 가능성이 크다)
Shared Page
공유 페이지가 되기 위한 조건 2가지
ReadOnly 여야만 한다.
Logical Memory의 위치가 동일해야만 한다.
Memory Protection
보호비트를 통해서 메모리의 연산 접근에 대해서 제한을 둘수 있다.
Read / Write / ReadOnly

Segmentation

참고이미지
의미가 있는 블록으로 메모리를 나누는 기법(정적 변수, 메소드, 심볼 등등)
페이징과는 달리 각 세그먼트의 크기가 다르다.
Segmentation Table에 접근하는 S 값에 대해서 먼저 Limit를 초과하는지 검사 를 통해 잘못된 주소 접근을 막는다.
Segmentation 기법에서 MMU의 레지스터는 뭘로 이용될까?
Segment-table base register (STBR)
세그먼트 테이블의 시작위치를 담고있다.
Segment-table length register(STLR)
프로그램이 사용하는 세그먼트의 수를 담고 있다.
Page 기법에 비해서 얻을 수 있는 장점은 뭘까?
논리적 단위로 나뉘기 때문에 보안, 메모리 상태, 쉐어링 등의 장점을 얻을 수 있음
메모리 배치
First-fit or Best-fit을 이용한다
외부조각 발생 가능성이 있다.

Paged-Segmentation

논리적 단위인 세그먼트로 먼저 메모리를 나누고 한번더 페이지로 나누어 관리하는 기술
세그먼트 하나당 페이지 테이블이 하나 존재함
때문에 세그먼트를 얻어오면 페이지 테이블의 시작주소를 가져올 수 있음
세그먼트 길이가 페이지 테이블의 길이기 때문에 세그먼트 길이를 통해서 Trap 발생 가능
세그먼트 길이보다 Offset 길이가 크다면 잘못된 메모리 접근으로 Trap
세그먼트 Offset을 잘라서 앞부분은 페이지 번호로, 뒷부분은 페이지 오프셋으로 사용한다.