Processes and Threads

유병익·2022년 10월 18일
1

OS

목록 보기
1/1
post-thumbnail

1.1 The Process


1.1.1 Process란?


수행의 기본 단위

📝 정의

  • 수행 & 스케쥴링 의 기본 단위
  • 프로세스마다 유니크한 PID가 있음
  • Process control block(PCB) 에 프로세스의 여러 정보를 저장
  • job, task, sequential process 등으로 불리기도 함

1.1.2 Process 생성


  • UNIX에서 Process 생성

    1. fork() system call

      • 새로운PCB를 생성 & 초기화
      • 주소 공간도 새롭게 생성 (기본적으로 부모의 주소공간을 카피)
      • 여러 리소스들을 초기화 (경우에 따라 부모의 자원을 공유)
    2. exec() system call

      • 현재 프로세스를 중지
      • 특정 프로그램을 주소 공간에 로드
      • 하드웨어 컨텍스트, 새 프로그램에 대한 Argument 초기화
      • PCB를 Ready Queue에 배치 📝 새 프로세스를 생성하는 것은 아님 !!

1.1.3 Process Termination


  1. Normal exit
    • main()으로 부터 return
    • exit()호출
    • _exit()호출
  2. Abnormal termination
    • abort() 호출
    • 특정 신호가 올 때

📝 프로세스가 어떤 방식으로 종료되든, 커널에선 동일한 코드가 작동한다.

프로세스의 PCB와 할당된 Memory를 해제 등


1.1.4 Process Hierarchy


  • Parent-child relation
    • 부모 Process자식 Process를 생성
    • 자식 Process는 자신만의 Process를 생성할 수 있음
  • Forms a hierarchy
    • UNIX에선 이를프로세스 그룹이라고 부름
    • 신호를 프로세스 그룹으로 보낼 수 있음
  • 윈도우 운영체제는 이런 계층 구조 개념이 없음
    • 윈도우 운영체제의 모든 프로세스들은 동등하게 생성됨

1.1.5 Process states


각 프로세스에는 현재 수행 중인 작업을 나타내는 실행 상태가 있다.

  • ready
    • 실행 가능 But, 다른 프로세스가 CPU를 사용하는 중
  • running
    • 현재 프로세스가 CPU를 사용 중
  • blocked
    • 이벤트가 발생해서 프로세스가 진행될 수 없을 때

1.1.6 Process data structures


  • PCB(Process Control Block) == PT(Process Table)에 프로세스에 대한 모든 정보 저장

  • PCB는 운영체제가 관리한다.

  • Context switch가 발생 → Running 상태의 Process 정보를 PCB에 저장

    📝 Context switch : CPU를 점유하는 프로세스가 변경되는 것

  • Unschedule될 때의 상태를 저장하고 Ready 상태

  • 다시 Running 상태로 돌아갈 때 PCB를 토대로 정보를 복원

  • Process address space



1.2 Thread


1.2.1 Parallel Programs


  • Parallel Program을 수행하려면, 여러 프로세스를 생성해야 함
  • 각 Process에 주소 공간, OS 자원, 레지스터 정보 등 자원 할당
  • 이를 OS Scheduling을 통해 병렬 처리
⚠️ Process로 병렬 처리를 하는 것은 비효율적!
  • PCB,Page Table 등 주소 공간 낭비
  • OS 구조 생성, 주소 공간 Copy 등 시간 낭비
  • Parallel Program에서 각 프로세스들의 공통점
    • 동일한 코드와 데이터(주소 공간) 공유
    • 모두 같은 권한
    • 모두 동일한 Resource(파일, 소켓 등) 공유
  • Parallel Program에서 각 프로세스들의 다른점
    • Process 실행 상태



1.2.2 Thread


Thread

📌 정의

  • 특정 프로세스 안에서 실행되는 흐름의 단위
  • 특정 프로세스 안에 리소스를 할당하고 실행을 할당하는 단위
  • Thread Model
  • Address space with Threads

Thread의 특징

  • 프로그래밍 모델이 더 간단함
  • 주소 공간을 공유
  • 프로세스보다 가볍습니다.
  • 프로세스보다 생성 및 소멸 용이
  • 생성 및 관리 오버헤드가 Process보다 적음
  • 정보 교환이 유리

📌 참고

  • Thread를 만들고 관리하는 것이 Process를 만드는 것보다 오버헤드가 적다.
  • Process를 만들 때 사용되는 SystemCall오버헤드Thread를 만들 때 보다 큼
  • 프로세스 간의 정보 교환 → Interprocess Communication
    • 다른 프로세스로의 접근
    • SystemCall을 통해 운영체제 담당
    • 오버헤드가 크다.
  • Thread는 같은 주소 공간공유 → 정보 교환 과정 단순 + 오버헤드가 적음

⚠️ 단점

  • 하나의 Thread에서 오류나 Fault 발생 → 해당 프로세스의 모든 Thread 종료
  • 안정성이 낮아진다.
<

1.2.3 Kernel Threads & User-level Threads


  • 누가 Thread를 생성하고 관리하는지?

    • OS가 Thread 생성 및 관리 → Kernel Threads
    • Libarary가 Thread 생성 및 관리 → User-level Threads
  • Example

User-level Threads


  • User-level Threads는 일반적으로 라이브러리의 함수 호출을 통해 생성
  • Library는 Thread TableUser-level에서 생성 및 관리
👍 장점
  • 생성Switch이 빠르다.
  • Kernel System Call 필요 없음 → Kernel Threads보다 빠름
⚠️ 단점
  • Blocking System Call 사용 → Process 전체 Block
  • Page Fault 발생 → Process 전체 Block
  • User-level에서 Libarary Call을 하지 못하고 무한 Loop → 특정 Thread가 계속 사용 (User-level Threads는 Clock interrupt X)
  • OS는 해당 Process에 Thread가 있는지 없는지 알 수 없음

    결국 CPU할당은 OS가 담당한다.
    User-level Threads는 OS 입장에서 하나의 Process로 보이기 때문에 여러 개의 CPU가 IDLE하더라도, 하나의 CPU밖에 할당 할 수 없다.

Kernel Threads


  • Kernel ThreadsOS가 Threads를 관리
  • Kernel Threads는 Threads의 수가 제한됨
  • 오버헤드가 크다.
    • But, Process로만 관리하는 것보단 낫다.



1.3 Synchronization (Interprocess Communication)


  • Multithreaded Programs에서 각 Thread들은 협력해야 함
  • 자원 공유 & 공유 데이터 접근 & 협력을 위해 Synchronization을 통한 Thread 제어 필요
  • Thread뿐만 아니라 Processes에도 적용된다.


1.3.1 Race Condition


Race Condition

  • Output을 예상할 수 없는 경우
  • 타이밍에 따라 결과가 다르게 나올 수 있는 상황
  • Example

  1. A와 B가 계좌 공유
  2. 각자 동시에 10$ 출금
  3. 순서 & 타이밍에 따라 다른 결과가 출력

📌 공유된 자원에 Synchronization없이 접근 → Race Condition 발생할 수 있음

모든 공유된 자원에 대해 Synchronization는 필수적이다.



1.3.2 Critical Section (Critical Regions)


Critical Section (Critical Regions)

공유된 자원에 Access하는 Code

Mutual exclusion (Mutex)

상호 배타적으로 수행하는 방식

동시에 수행할 수 없도록 하는 방식

📌 Mutual exclusion을 통해 Critical Region의 실행을 동기화하자!

Critical Section Problem (CSP)

  • Critical Section Problem를 해결하기 위해 몇 가지 조건이 필요하다.
    • Mutual exclusion
      • 전체 시스템에서 같은 자원에는 한번에 하나의 작업 수행
    • Bounded waiting(No starvation)
      • 무한정 기다리면 안됨
    • Progress
      • Critical region에서의 작업이 없는데, 진입하지 못하는 상황이 발생하면 안됨
    • 연산하는 CPU의 숫자, 속도 등을 가정하지 않는다.

CSP를 해결하는 여러 방법들

  • Disabling Interrupt
  • Locks
  • Semaphores
  • Monitors
  • Messages


1.3.3 Mutual Exclusion with Busy Waiting


Disabling Interrupt


  • Critical region에 진입하면 interrupt를 disable
  • CPU가 하나라면 OK, But 여러 개라면 Mutual exclusion 위배

Lock Variable


  • 전역 변수 Lock 선언
  • Critical Region에 진입할 때 Lock을 1로 바꾸고 Critical Region진입
  • 작업을 마친 Thread가 lock을 0으로 바꾸면 다른 Thread가 Critical Region에 진입 가능

⚠️ Context swtich가 일어나는 시점에 따라 Mutual exclusion 위배할 수 있음

  • ex) Lock 세팅할 때 Context switch가 발생하는 경우
  • Busy waiting
    • 계속해서 변수를 확인하면서 대기
    • CPU 낭비 → 짧은 대기 시간이 예상될 때 사용
  • Spin lock
    • Busy waiting을 사용하는 Lock
    • Mutual exclusion
    • Progress상황 발생 가능

해결방법

  1. Peterson's Solution

    • 이해하기 어려움, 성능 문제 등
  1. TSL(Test and Set Lock) instruction

    • Atomic한 명령어를 지원하는 하드웨어의 도움
      • Atomic instructions : 중간에 끼어들 수 없는 명령어, 쪼갤 수 없음
    • 위 사진에서 Lock을 테스트하는 명령어와 Setting하는 명령어가 Atomic
    • Lock방식과 비슷하지만, Atomic이 보장 → Mutual exclusion

⚠️ 하지만 이 방식들은 Busy Waiting 방식 → CPU 낭비



1.3.4 Sleep and Wakeup


특징


  • sleep(), wakeup() System Call 사용

  • sleep()

    • Running → Blocked
  • wakeup()

    • Blocked → Ready
  • Example

    ![](https://velog.velcdn.com/images/quddlr96/post/3d807792-adde-4cf6-8afd-9426e190f0aa/image.png)
    
    
    - 파란색에서 빨간색으로 진행할 때, Context Switch가 발생 → 둘 다 Sleep하는 문제 발생
    - count와 buffer는 `전역변수(공유된 자원)`
    - Sleep & Wake-Up은 `Mutual exclusion X`
    - count와 buffer에 접근하는 명령어는 Mutual exclusive 해야 함



1.3.5 Semaphores


특징


  • 높은 수준의 Lock과 비슷한 개념
  • down ,up Operation이 있음
  • down(semaphore)
    • semaphore 값이 0보다 크면 semaphore값을 1만큼 감소

    • semaphore 값이 0이라면 wait

      if (semaphore >0) semaphore--; else wait();
  • up(semaphore)
    • semaphore 값을 1만큼 증가
    • wait 중인 semaphore가 있다면 그 중 하나를 wake up

📌 up(semaphore)에 의해 wait이던 Process or Thread가 깨워지면, down(semaphore)를 다시 수행해야 함

깨워졌다고 해서 semaphore값이 0이 아니라는 보장을 할 수 없다!

  • Semaphore를 활용한 Producer-Consumer Problem

Semaphore의 종류

  • Binary Semaphore
    • semaphore값이 0 or 1
  • Counting Semaphore
    • semaphore값이 0~N

📌 Thread는 같은 주소 공간을 공유하기 때문에 전역 변수에 접근하기 수월하다. 하지만

Process는 그렇지 않기 때문에, OS의 도움으로 주소 공간을 공유 또는 Semaphore를 공유하는 자료 구조로 Kernel이 제공하는 방식을 사용해 자원을 공유하게 해준다.



1.3.6 Mutexes



1.3.7 Monitors


특징


  • 프로그래밍 언어에서 제공

  • Semaphore보다 쉽게 사용 가능

  • Mutual Exlusion보장

  • Monitor안에서 선언된 함수에 특정 Thread or Process가 접근하면 다른 Thread or Process는 그 함수에 접근할 수 없음

  • wait(c)

    • Monitor에 진입한 Thread or Process가 Monitor 밖으로 나옴
    • 다른 Thread or Process가 모니터에 진입 가능해짐 (Monitor lock 해제)
  • signal(c)

    • wait상태인 Thread or Process중 하나를 깨운다.

그럼 signal보낸 쓰레드랑 wait에서 깬 쓰레드랑 어떤게 먼저 수행되어야하나 ?

❓ signal을 보낸 Thread or Process와 wait에서 깬 Thread or Process중 어떤 것 먼저 수행?

Monitor의 종류


  • hoare monitors
    • wait에서 깬 Thread or Process 먼저 수행
  • mesa monitors
    • signal을 보낸 Thread or Process 먼저 수행
    • signal 보낸 Thread or Process가 끝나고 wait에서 깬 Thread or Process가 수행될 때, wait에서 깬 Thread or Process가 wait 된 조건이 끝났다는 보장이 없음 → 다시 한번 체크하고 진행
  • hansen monitors
    • signal을 보내는 코드 라인을 무조건 그 함수의 마지막에 오도록 함
    • 조건이 붙는 대신 개념이 훨씬 간단하고 이해하기 쉬움

⚠️ 단점

  • Monitor 기능을 제공해주는 프로그래밍 언어가 아니면 사용할 수 없음
  • 분산 환경에서 적합하지 않음
    - 공유 메모리가 아닌 네트워크로 연결된 환경
    - Semaphore도 동일

1.3.8 Message Passing


  • 네트워크 같은 분산 환경에서 사용

  • send, receive System Call 사용

    • Consumer의 처리 속도가 Producer의 생산 속도보다 느림→consumer가 send를 보내지 않음→ Producer는 receive에서 대기
    • Consumer의 처리 속도가 Producer의 생산 속도보다 빠름→producer가 send를 보내지 않음 → Consumer는 receive에서 대기

1.3.9 Barriers

profile
Backend 개발자가 되고 싶은

0개의 댓글