컴퓨터 메모리&레지스터 구조
시스템이 초기화 되기 시작하면 시스템은 커널을 메모리에 적재시키고 가용 메모리 영역을 확인하게 된다.
시스템은 운영에 필요한 기본적인 명령어 집합을 커널에서 찾는다.
커널이란?
컴퓨터의 운영체제의 핵심이 되는 컴퓨터 프로그램의 하나로, 시스템의 모든 것을 완전히 통제한다.
운영체제의 다른 부분 및 응용 프로그램 수행에 필요한 여러 가지 서비스를 제공한다.
Process & Segment
우리가 알아야 할 것은 하나의 프로그램이 실행되기 위한 메모리 구조이다.
운영체제는 하나의 프로세스를 실행시키면 이 프로세스를 segment라는 단위로 묶어서
가용 메모리 영역에 저장시킨다.
하나의 segment는 위 그림처럼 오른편에 나와있는 구조를 갖고 있다. 각각을
code segment, stack segment, data segment라고 한다.
Code segment
code segment에는 시스템이 알아들을 수 있는 명령어 즉 instruction들이 들어 있다.
이것은 기계어 코드로써 컴파일러가 만들어낸 코드이다.
data segment
프로그램이 실행시에 사용되는 데이터가 여기에 들어간다. 여기서 말하는 데이터는 전역 변수이다.
프로그램 내에서 전역 변수를 선언하면 그 변수가 data segment에 자리 잡게 된다.
data segment는 다시 네 개의 data segment로 나뉘는데 각각 현재 모듈의 data sturct,
상위 레벨로부터 받아들이는 데이터 모듈, 동적 생성 데이터, 다른 프로그램과 공유하는 공유 데이터 부분이다.
stack segment
현재 수행되고 있는 handler, taskm, program이 저장하는 데이터 영역으로
우리가 사용하는 버퍼가 바로 이 stack segment에 자리 잡게 된다. 또한 프로그램이 사용하는
multiple 스텍을 생성할 수 있고 각 스텍들간의 switch가 가능하다. 지역 변수들이 자리 잡는 공간이다.
스텍은 처음 생성될 때 그 필요한 크기만큼 만들어지고 프로세스의 명령에 의해 데이터를 저장해 나가는
과정을 거치게 되는데 이것은 stack pointer(SP)라고 하는 레지스터가 스텍의 맨 꼭대기를 가리키고 있다.
스텍에 데이터를 저장하고 읽어 들이는 과정은 PUSH와 POP instruction에 의해서 수행된다.
8086 CPU 레지스터 구조
cpu는 데이터를 재빨리 읽고 쓰기를 해야 하는 데이터들이므로 CPU 내부에 존재하는 메모리를 사용한다.
이러한 저장 공간을 레지스터(register)라고 한다.
레지스터는 다시 그 목적에 따라서 범용 레지스터(General-purpose register), 세그먼트 레지스터(segment register)
, 플래그 레지스터(program status and control register), 그리고 인스터럭션 포인터(instruction pointer)로 구성된다.
범용레지스터는 논리 연산, 수리 연산에 사용되는 피연산자, 주소를 계산하는데 사용되는 피연산자, 그리고 메모리
포인터가 저장되는 레지스터다. 또한, 컴퓨터 장치들을 제어한다.
세그먼트 레지스터는 code segment, data segment, stack segment를 가리키는 주소가 들어있는 레지스터이다.
세그먼트 레지스터는 크기가 16비트이며,
세그먼트 레지스터는 SS, DS, CS, ES(extra segment), 80386과 그 이후 프로세서에서는
FS와 GS 레지스터가 제공된다.
이렇게 세그먼트 레지스터가 가리키는 위치를 바탕으로 우리는 우리가 원하는 segment 안의
특정 데이터, 명령어를 정확하게 끄집어 낼 수가 있게 된다.
플래그 레지스터는 프로그램의 현재 상태나 조건 등을 검사하는데 사용되는 플래그들이 있는 레지스터이다.
인스트럭션 포인터는 다음에 수행해야 하는 명령(instruction)이 있는 메모리 상의 주소가 들어가 있는 레지스터이다.
범용 레지스터(General-purpose register)
범용 레지스터는 프로그래머가 임의로 조작할 수 있게 허용되어 있는 레지스터다. 일종의
4개의 32bit 변수라고 생각하면 된다. 예전의 16bit 시절에는 각 레지스터를 AX. BX, CX, DX... 등으로 불렀지만
32bit 시스템으로 전환되면서 E(Extended)가 앞에 붙어 EAX, EBX, ECX, EDX... 등으로 불린다. AX 레지스터의
EAX, EBX, ECX, EDX 레지스터들은 프로그래머의 필요에 따라 아무렇게나 사용해도 되지만 최초 태생은
자신들의 목적을 가지고 대어났고 나중에 기계어 코드를 읽고 이해하기 편하게 하기 위해서
그 목적대로 사용해 주는 것이 좋다. 또한 컴파일러도 이러한 목적에 맞게 사용하고 있다.
범용 레지스터엔 총 8가지 종류(EAX, EBX, ECX, EDX, ESI, EDI, ESP, EBP )가 있다.
모든 범용 레지스터는 각각 32BIT를 가진다.
각 레지스터의 목적을 살펴보자.
EAX- 피연산자와 연산 결과의 저장소
EBX- DS segment()안의 데이터를 가리키는 포인터
ECX- 문자열이나 루프를 위한 카운터
EDX - I/O 포인터
ESI - DS 레지스터가 가리키는 data segment 내의 어느 데이터를 가리키고 있는 포인터.
문자열 처리에서 source를 가리킴.
EDI - ES 레지스터가 가리키고 있는 data segment 내의 어느 데이터를 가리키고 있는 포인터.
ESP - SS 레지스터가 가리키는 stack segment의 맨 꼭대기를 가리키는 포인터
EBP - SS 레지스터가 가리키는 스텍상의 한 데이터를 가리키는 포인터
플래그 레지스터와 명령어레지스터도 다루어야 하지만 아직 필요 없음으로
나는 범용 레지스터만 다루게ㅆ다.