컴퓨터구조 CPU·캐시·메모리 정리
명령어 실행, 캐시 지역성, 가상메모리 주소 변환을 중심으로 정리합니다.
CPU와 명령어
명령어 사이클은 인출·간접·실행·인터럽트 등의 단계로 설명할 수 있습니다. 프로그램 카운터는 다음 명령어 주소, 명령어 레지스터는 현재 명령어를 보관합니다.
- 파이프라이닝은 명령어 단계를 겹쳐 처리량을 높인다.
- 분기와 데이터 의존성은 파이프라인 해저드를 만든다.
- 인터럽트는 현재 상태를 보존하고 서비스 루틴으로 이동한다.
캐시와 지역성
시간 지역성은 최근 사용한 데이터의 재사용 가능성, 공간 지역성은 인접 데이터 사용 가능성을 뜻합니다. 캐시 적중률과 평균 접근시간 계산에서는 적중·실패 경로의 비용을 구분합니다.
- 직접 사상은 위치가 단순하지만 충돌이 많을 수 있다.
- 완전 연관 사상은 배치 자유도가 높지만 비교 비용이 크다.
- 쓰기 정책은 write-through와 write-back을 구분한다.
가상메모리
페이지는 가상 주소 공간, 프레임은 물리 메모리의 고정 크기 블록입니다. 페이지 테이블이 변환을 담당하고 TLB는 최근 변환 결과를 캐시합니다.
- 유효한 비상주 페이지에 접근하면 페이지 부재를 처리한다. 저장장치에서 읽는 경우뿐 아니라 0으로 채운 새 페이지를 할당하는 등 I/O가 필요 없는 경우도 있다.
- TLB 실패는 변환 캐시에 정보가 없다는 뜻이며 페이지 부재와 같지 않다.
- 스래싱은 과도한 페이지 교체로 실제 작업이 줄어드는 현상이다.
- 내부 단편화와 외부 단편화의 발생 조건을 구분한다.
주소 변환과 캐시 수치를 단계별로 계산하기
메모리 계산은 CPU가 만든 가상주소를 페이지 번호와 변위로 나누고, 페이지 테이블 또는 TLB로 프레임 번호를 찾은 뒤 물리주소를 구성하는 순서로 풉니다. 캐시는 주소를 태그·인덱스·블록 오프셋으로 나눠 매핑 방식과 적중 여부를 판단합니다.
- 페이지 크기가 2^k 바이트라면 변위는 k비트다.
- 유효 접근시간은 적중·실패 확률과 각 경로의 시간을 가중 평균한다.
- 쓰기 정책은 write-through/write-back과 write-allocate/no-write-allocate를 별도로 구분한다.
입출력·RAID·데이터 표현
입출력 방식은 CPU가 장치를 계속 확인하는지, 인터럽트로 완료를 알리는지, DMA가 메모리 전송을 맡는지로 구분합니다. 저장장치 문제에서는 RAID별 데이터 분산과 중복 정보의 위치를 확인하고 장애 허용 개수를 판단합니다.
- DMA는 블록 전송을 담당해 CPU의 반복적인 입출력 개입을 줄인다.
- RAID 0은 스트라이핑만 제공해 성능은 높지만 장애 복구용 중복 정보가 없다.
- RAID 1은 미러링, RAID 5는 분산 패리티를 사용한다.
- 빅엔디언은 상위 바이트를 낮은 주소에, 리틀엔디언은 하위 바이트를 낮은 주소에 저장한다.
데이터 표현·논리회로·명령어 형식
컴퓨터구조 계산은 진법과 보수, 부호 표현, 논리식 간소화에서 시작해 명령어의 연산코드·주소 필드와 주소지정 방식으로 이어집니다. 같은 비트열도 부호 있는 정수·부호 없는 정수·부동소수점 중 해석 방식에 따라 값이 달라집니다.
- 2의 보수 n비트 정수 범위는 -2^(n-1)부터 2^(n-1)-1까지이며 최상위 비트의 가중치를 음수로 해석할 수 있다.
- 부동소수점은 부호·지수·가수로 구성되고 정규화·반올림·오버플로·언더플로를 구분한다.
- 드모르간 법칙은 논리곱의 부정을 각 항의 부정의 논리합으로, 논리합의 부정을 각 항의 부정의 논리곱으로 바꾼다.
- 즉시 주소는 명령어 안의 값, 직접 주소는 유효주소, 간접 주소는 유효주소를 얻기 위한 주소, 인덱스 주소는 기준 주소와 인덱스를 결합한다.
- RISC는 단순·규칙적 명령과 레지스터 중심 실행, CISC는 복잡하고 다양한 명령 형식을 대표 특성으로 비교한다.
파이프라인·캐시·성능 계산
파이프라인은 여러 명령의 단계를 겹쳐 처리량을 높이지만 구조·데이터·제어 해저드로 지연될 수 있습니다. 성능 문제는 클럭 주기, 명령 수, CPI의 단위를 맞추고 캐시·메모리의 각 접근 경로를 확률 가중 평균합니다.
- CPU 실행시간은 명령 수×CPI×클럭 주기이며 클럭률을 쓸 때는 명령 수×CPI/클럭률로 계산한다.
- 데이터 해저드는 포워딩·스톨, 제어 해저드는 분기 예측·지연 분기 등으로 영향을 줄인다.
- 직접 사상은 한 블록의 위치가 하나이고 집합 연관은 정해진 세트 안 여러 라인, 완전 연관은 어느 라인에도 배치 가능하다.
- AMAT는 적중시간과 실패율×실패 페널티를 구분하며 문제에서 실패 페널티에 적중시간이 이미 포함됐는지 확인한다.
- Amdahl 법칙은 개선되지 않는 부분이 전체 성능 향상의 상한을 만든다는 점을 계산한다.
직접 풀어보는 예제와 단계별 해설
캐시와 가상메모리는 서로 다른 주소 변환을 다룹니다. 같은 숫자라도 블록 번호·캐시 라인·가상 페이지·물리 프레임 중 무엇인지 표시하며 계산합니다.
연속 주소는 적중하는데 다시 읽은 주소는 왜 실패할까?
8비트 바이트 주소를 사용하는 직접 사상 캐시입니다. 데이터 용량은 32byte, 블록 크기는 8byte이고 처음에는 모든 라인이 무효입니다. 읽기 주소 0, 7, 32, 0, 8, 15를 순서대로 접근합니다. 실패하면 해당 블록 전체를 적재하며 선행 인출은 없습니다. 각 접근의 적중 여부를 구하세요.
Python 3
lines = [None] * 4
for address in (0, 7, 32, 0, 8, 15):
block = address // 8
index = block % 4
tag = block // 4
hit = lines[index] == tag
print(address, index, tag, 'HIT' if hit else 'MISS')
lines[index] = tag넓은 표는 좌우로 밀어 나머지 열을 볼 수 있습니다.
| 주소 | 블록 / 라인 / 태그 | 판정 | 이유 |
|---|---|---|---|
| 0 | 0 / 0 / 0 | 실패 | 라인 0에 첫 적재 |
| 7 | 0 / 0 / 0 | 적중 | 0과 같은 8byte 블록 |
| 32 | 4 / 0 / 1 | 실패 | 라인 0의 태그를 1로 교체 |
| 0 | 0 / 0 / 0 | 실패 | 라인 0에 태그 1이 남아 있음 |
| 8 | 1 / 1 / 0 | 실패 | 라인 1에 첫 적재 |
| 15 | 1 / 1 / 0 | 적중 | 8과 같은 블록 |
풀이 순서
- 라인 수는 32/8=4개입니다. 블록 오프셋은 3비트, 라인 인덱스는 2비트, 태그는 나머지 3비트입니다. 블록 번호는 주소÷8의 몫, 라인은 블록 번호 mod 4로 구합니다.
- 주소 0과 32는 서로 다른 블록이지만 같은 라인 0으로만 들어갑니다. 다른 라인이 비어 있어도 그쪽으로 옮길 수 없어 교체가 발생합니다. 네 번째 접근 0의 실패는 이 충돌 때문입니다.
- 적중은 7과 15에서 두 번이므로 적중률은 2/6=1/3입니다. 적중시간이 2ns이고 실패 시 추가 비용이 30ns라면 평균 접근시간은 2+(4/6)×30=22ns입니다. 실패 접근의 총시간을 30ns로 준 문제라면 같은 식을 그대로 쓰지 않습니다.
확인 결과
0 0 0 MISS
7 0 0 HIT
32 0 1 MISS
0 0 0 MISS
8 1 0 MISS
15 1 0 HIT틀리기 쉬운 지점: 인덱스가 같다고 적중이 아닙니다. 유효 비트와 태그까지 맞아야 합니다. 공간 지역성이 있어도 직접 사상 충돌은 별도로 발생할 수 있습니다.
TLB에 없다는 것과 메모리에 없다는 것은 다르다
가상주소는 16비트, 페이지 크기는 1KiB입니다. 단일 단계 페이지 테이블에서 가상 페이지 11은 present=1·프레임 6, 가상 페이지 12는 present=0입니다. 두 페이지는 모두 유효하게 할당된 읽기 가능 영역이고 TLB에는 없습니다. 주소 0x2D3A와 0x3010의 처리를 각각 판단하세요.
Python 3
page_size = 1024
page_table = {11: 6, 12: None}
for address in (0x2D3A, 0x3010):
page, offset = divmod(address, page_size)
frame = page_table[page]
if frame is None:
print(f'{address:#06x}: page={page} offset={offset} PAGE_FAULT')
else:
physical = frame * page_size + offset
print(f'{address:#06x}: page={page} offset={offset} physical={physical:#06x}')넓은 표는 좌우로 밀어 나머지 열을 볼 수 있습니다.
| 가상주소 | 페이지 / 변위 | 처리 |
|---|---|---|
| 0x2D3A | 11 / 0x13A | TLB 실패지만 메모리에 존재 → 물리주소 0x193A |
| 0x3010 | 12 / 0x010 | TLB 실패 후 present=0 확인 → 페이지 부재 처리 |
풀이 순서
- 1KiB=2^10byte이므로 변위는 하위 10비트이고 가상 페이지 번호는 상위 6비트입니다. 0x2D3A를 1024로 나누면 몫 11, 나머지 314입니다.
- 가상 페이지 11은 프레임 6에 있으므로 물리주소는 6×1024+314=6458, 즉 0x193A입니다. 변위 0x13A는 주소 변환 뒤에도 그대로 유지됩니다.
- TLB 실패는 변환 캐시에 정보가 없다는 뜻입니다. 페이지 11처럼 페이지 테이블에 유효한 상주 매핑이 있으면 디스크를 읽지 않고 계속 진행할 수 있습니다. 예제의 페이지 12는 메모리에 없으므로 먼저 페이지 부재를 처리해야 하며, 프레임을 정하기 전에는 물리주소를 확정할 수 없습니다.
- TLB 조회 1ns, 메모리 접근 50ns이고 병렬 조회·다단계 페이지 테이블·데이터 캐시를 무시하면, 상주 페이지의 TLB 적중은 51ns, 실패는 페이지 테이블과 데이터 두 번 접근으로 101ns입니다. 페이지 부재 시간은 이 101ns에 포함되지 않습니다.
확인 결과
0x2d3a: page=11 offset=314 physical=0x193a
0x3010: page=12 offset=16 PAGE_FAULT틀리기 쉬운 지점: 페이지 부재를 모두 디스크 읽기로 계산하지 마세요. 새 익명 페이지를 0으로 채우거나 이미 메모리에 있는 페이지를 연결하는 경우처럼 저장장치 I/O 없이 처리되는 경우도 있습니다. 접근 권한 위반과 유효한 비상주 페이지도 구별해야 합니다.
검증 방법과 참고 문서
공개한 Python 예제를 실제 실행하고, 캐시 비트 분해와 페이지 변환을 별도 계산으로 대조했습니다. 시간 계산은 예제에서 명시한 단순 모델의 결과이며 실제 기기 성능 측정치가 아닙니다.
예제·데이터·풀이표: 정처LAB 자체 설계 · AI 보조 작성 및 로컬 검증 · 예제 수정일 2026-09-27
혼동하기 쉬운 지점
- 처리량과 단일 명령 지연시간을 동일시
- 시간 지역성과 공간 지역성을 반대로 암기
- 페이지와 프레임을 같은 주소 공간의 용어로 해석
개념을 확인했다면 관련 문제에 적용해보세요.
첫 관련 문제 풀기