💡 컴퓨터의 구성
운영체제를 알기 전에, 컴퓨터가 기본적으로 어떻게 구성되어 있는지 짚고 넘어갈 필요가 있겠다. 나는 컴맹이기 때문에~~!🥸
하드웨어는 컴퓨터의 물리적인 구성요소이다. 하드웨어는 절대 스스로 일하는 법이 없다. 따라서 하드웨어의 설계를 바탕으로 일을 시켜야만 한다. 이 때 하드웨어한테 일을 시키는 주체가 운영체제다. 초창기의 컴퓨터는 사용자가 작성한 프로그램 명령을 하드웨어에서 바로 수행할 수 있었다. 하지만 프로그램이 복잡해지고 하드웨어가 다양해지면서 운영체제가 탄생하게 되었고, 운영체제를 거쳐 사용자의 명령을 하드웨어에 전달하게 되었다.
운영체제는 영어로 Operating System, 줄여서 OS라고 부른다. 우리가 알고있는 Window OS, Mac OS가 대표적인 운영체제다. 운영체제가 하는 일을 살펴보자.
시스템 자원은 하드웨어를 뜻한다. 위에서 언급했듯이, 하드웨어는 혼자서 아무것도 못하는 바보다. 때문에 하드웨어를 관리하기 위해서는 운영체제가 꼭 필요하다. 하드웨어 관리는 크게 세 가지로 나뉜다.
운영체제는 사용자와 컴퓨터 사이의 커뮤니케이션을 중재한다. 사용자가 입출력장치를 통해 명령을 내리면 운영체제가 하드웨어를 관리한다.
모든 응용 프로그램이 시스템의 자원을 마음대로 사용한다면, 해커에 의한 공격에 무방비한 상태가 된다. 따라서 응용 프로그램은 권한에 대한 관리가 필요하다. 운영체제는 응용 프로그램이 실행되고, 시스템 자원을 사용할 수 있도록 권한과 사용자를 관리한다.
💡 응용 프로그램이란?
응용 프로그램은 응용 프로그램 소프트웨어 또는 애플리케이션(Application)이라고도 부른다. 응용 프로그램은 운영체제를 통해 컴퓨터한테 일을 시킨다. 그러기 위해서는 컴퓨터를 조작할 수 있는 권한을 운영체제로부터 부여받아야만 한다. 아래는 사용자, 응용 프로그램, 운영체제, 하드웨어 간의 관계를 나타내는 그림이다.
운영체제는 대부분 2개의 모드를 가진다. 유저 모드(User Mode)와 커널 모드(Kernel Mode)인데, 유저 모드는 일반적인 사용자 애플리케이션이 실행되는 모드이고, 커널 모드는 모든 시스템 메모리와 CPU에 접근이 가능한 모드이다. 유저 모드 애플리케이션이 커널 모드로 모드를 변경한 상태에서 운영체제 서비스를 호출하는 것을 시스템 콜이라고 한다. 이 때 애플리케이션은 운영체제가 제공하는 API(Application Programming Interface)를 사용하여 서비스를 요청한다. 즉, 시스템 콜이란 응용 프로그램이 시스템 자원을 사용할 수 있도록, 운영체제 차원에서 다양한 함수를 제공하는 것이다.
💡 커널(kernel)이란?
커널은 운영체제(OS)의 핵심 구성요소로, 하드웨어와 응용 프로그램 간의 인터페이스 역할을 수행한다. 운영체제의 심장이라고도 부른다. 소프트웨어가 컴퓨터에서 실행되기 위해서는 메모리에 해당 프로그램이 올라가야한다. 운영체제 자체도 소프트웨어로서 같은 맥락을 가진다. 하지만 운영체제처럼 규모가 큰 프로그램이 모두 메모리에 올라가면 메모리 공간의 낭비가 심할 것이다. 따라서 운영체제 중 항상 필요한 부분만 메모리에 올려놓고 그러지 않은 부분은 필요할 때마다 메모리에 올려서 사용하는데, 이 때 메모리에 상주하는 부분이 커널이다.
커널은 인터페이스로써 응용 프로그램 수행에 필요한 여러가지 서비스를 제공하며, 메모리 주소 공간 등의 리소스를 관리한다. 다음은 리눅스 커널의 구조도이다.
커널이 수행하는 주요 작업들은 다음과 같다.
- 프로세스 관리(Process Management)
- 메모리 관리(Memory Management)
- 파일 시스템 관리(File System Management)
- 디바이스 관리(Device Management)
- 네트워크 관리(Network Management)
- 입출력 통신 관리(I/O Communication Management)
더 자세한 내용은 아래 페이지를 참고하자.
https://blog.naver.com/PostView.nhn?blogId=cjsksk3113&logNo=222238471338
https://kjvvv.kr/1766
프로세스란 운영체제에서 실행중인 하나의 애플리케이션이다. 사용자가 애플리케이션을 실행하면 애플리케이션은 운영체제로부터 실행에 필요한 메모리를 할당받아 코드를 실행한다. 이때 실행되는 애플리케이션을 프로세스라고 부른다. 하나의 애플리케이션은 여러 개의 프로세스를 실행시킬 수 있으며, 이를 다중 프로세스라고 부른다. 프로세스의 메모리 영역은 크게 아래의 네 가지로 나뉜다.
스레드는 한 가지 작업을 실행하기 위해 순차적으로 실행한 하나의 코드 흐름이다. 스레드는 프로세스 내에서 실행되는 흐름의 단위로, 각 스레드마다 콜 스택(Call Stack)이 존재하고, 독립적으로 동작한다는 특징이 있다.
💡 Call Stack이란?
호출 스택이라고도 부르며, 여러 함수들을 호출하는 스크립트에서 해당 위치를 추적하는 인터프리터를 위한 메커니즘이다. 현재 어떤 함수가 동작하고있는 지, 그 함수 내에서 어떤 함수가 동작하는 지, 다음에 어떤 함수가 호출되어야하는 지 등을 제어한다.
- 스크립트가 함수를 호출하면 인터프리터는 이를 호출 스택에 추가한 다음 함수를 수행한다.
- 해당 함수에 의해 호출되는 모든 함수는 호출 스택에 추가되고 호출이 도달하는 위치에서 실행한다.
- 메인 함수가 끝나면 인터프리터는 스택을 제거하고 메인 코드 목록에서 중단된 실행을 다시 시작한다.
- 스택이 할당된 공간보다 많은 공간을 차지하면 "stack overflow" 에러가 발생한다.
멀티 태스킹은 말 그대로 두 가지 이상의 작업을 동시에 처리하는 것이다. 운영체제는 멀티 태스킹을 위해 프로세스마다 CPU 및 메모리를 적절히 할당하고 병렬로 실행한다. 멀티 프로세스는 애플리케이션 단위의 멀티 태스킹이고, 멀티 스레드는 애플리케이션 내부의 멀티 태스킹이다.
멀티 스레딩의 가장 큰 장점은 메모리 공간과 시스템 자원의 소모가 줄어든다는 것이다. 스레드간의 통신이 필요한 경우 별도의 자원을 이용하는 것이 아니라 힙(Heap)영역을 이용한다. 때문에 프로세스 간의 통신 방법(IPC)보다 훨씬 간단하다. 시스템 처리량(Throughput)이 향상되고, 프로그램 응답 시간이 단축된다. 이런 장점 때문에 여러 프로세스로 할 수 있는 작업을 하나의 프로세스에서 스레드로 나눠 수행한다.
멀티 스레딩의 문제점은 프로세스간 공유하는 자원이 없다는 것이다. 서로 다른 스레드가 같은 데이터에 접근하고, 힙 영역을 공유하기 때문에 서로 다른 스레드가 서로 사용 중인 변수나 자료구조에 접근하여 엉뚱한 값을 읽어오거나 수정하는 일이 발생할 수 있다. 때문에 동기화 작업을 통해 작업 처리 순서를 제어하고 공유 자원에 대한 접근을 제어해야 한다.
💡 데드락(Deadlock, 교착 상태)
https://chanhuiseok.github.io/posts/cs-2/
💡 뮤텍스(Mutex), 세마포어(Semaphore)
https://worthpreading.tistory.com/90
동시에 돌릴 수 있는 스레드 수는 컴퓨터에 있는 코어 개수로 제한된다. 운영체제(또는 가상 머신)는 각 스레드를 시간에 따라 분할하여, 여러 스레드가 일정 시간마다 돌아가면서 실행되도록 한다. 이를 시분할이라고 한다. 이 때 다른 태스크가 시작할 수 있도록 이미 실행 중인 태스크를 멈추는 것을 Context Switching이라고 한다.