3-bo‘lim

Jarayon va uning holatlari

Jarayon nima, uning xotira tuzilishi, holatlari va holat almashinuvi, PCB, kontekst almashinuvi va jarayonlarni kuzatish.

🕑 15 daqiqa o‘qish 📄 1 137 so‘z 👁 1 marta ko‘rilgan
Ushbu bo‘lim mundarijasi
  1. Dastur va jarayon farqi
  2. Jarayonning xotira tuzilishi
  3. Jarayon holatlari
  4. Linux'da holatlarni ko'rish
  5. Jarayon identifikatori
  6. Jarayonlar daraxti
  7. Jarayon boshqaruv bloki (PCB)
  8. Kontekst almashinuvi
  9. Jarayonni kuzatish
  10. Jarayonga ta'sir qilish
  11. Xulosa

Jarayon (process) - ishga tushirilgan dastur. Dastur diskda yotgan fayl, jarayon esa xotirada yashaydigan jonli mavjudot.

Dastur va jarayon farqi #

Bitta dastur - ko'p jarayon Dastur Diskdagi fayl /usr/bin/firefox Passiv, o'zgarmas Bitta nusxa ishga tushirish Jarayon PID 1234 O'z xotirasi O'z holati 1-oyna Jarayon PID 1789 O'z xotirasi O'z holati 2-oyna Jarayon PID 2001 O'z xotirasi 3-oyna
Bir xil kod, lekin har birining o'z xotirasi va holati bor

Jarayonning xotira tuzilishi #

Jarayonning virtual manzil fazosi Stek (stack) mahalliy o'zgaruvchilar, funksiya chaqiruvlari pastga o'sadi ↓ bo'sh joy Uyum (heap) malloc bilan ajratilgan xotira yuqoriga o'sadi ↑ BSS nol bilan boshlangan global o'zgaruvchilar Data qiymat berilgan global o'zgaruvchilar Text (kod) mashina buyruqlari - faqat o'qish uchun yuqori past Stek va uyum bir-biriga qarab o'sadi - to'qnashsa xotira tugadi
C darsligidagi stek va uyum aynan shu yerda joylashgan
C
#include <stdio.h>
#include <stdlib.h>

int global_qiymatli = 42;      /* data */
int global_nol;                /* bss */

int main(void) {
    int mahalliy = 7;                  /* stek */
    int *uyumda = malloc(sizeof(int)); /* uyum */

    if (uyumda == NULL) {
        return 1;
    }

    *uyumda = 100;

    printf("Kod (main)     : %s\n", (void *) main != NULL ? "bor" : "yo'q");
    printf("Global (data)  : %d\n", global_qiymatli);
    printf("Global (bss)   : %d\n", global_nol);
    printf("Stek           : %d\n", mahalliy);
    printf("Uyum           : %d\n", *uyumda);

    /* manzillar tartibini tekshiramiz */
    printf("Uyum stekdan pastdami? : %s\n",
           (void *) uyumda < (void *) &mahalliy ? "ha" : "yo'q");

    free(uyumda);
    return 0;
}
Natija
Kod (main)     : bor
Global (data)  : 42
Global (bss)   : 0
Stek           : 7
Uyum           : 100
Uyum stekdan pastdami? : ha
bss nima?

bss - «Block Started by Symbol». Bu yerda nol bilan boshlanadigan global o'zgaruvchilar yotadi.

Ular fayl ichida joy egallamaydi - faylda faqat «shuncha bayt nol kerak» deb yoziladi. Dastur ishga tushganda yadro o'sha joyni nol bilan to'ldiradi.

Shuning uchun int katta_massiv[1000000]; deb e'lon qilingan dastur faylining hajmi 4 MB emas, balki bir necha kilobayt bo'ladi.

Jarayon holatlari #

Jarayonning holat almashinuvi Yangi Tayyor (ready) navbatda kutmoqda Ishlayotgan protsessorda Bloklangan I/O kutmoqda tanlandi vaqti tugadi I/O so'radi I/O tugadi - yana navbatga Tugagan
Bitta protsessorda faqat bitta jarayon «ishlayotgan» holatda bo'ladi
HolatMa'nosi
YangiYaratilmoqda, hali ishga tushmagan
TayyorIshlashga tayyor, protsessor navbatini kutmoqda
IshlayotganHozir protsessorda buyruqlar bajarilmoqda
BloklanganBiror narsani kutmoqda (disk, tarmoq, klaviatura)
TugaganIsh tugadi, resurslar qaytarilmoqda
Nima uchun «bloklangan» holat kerak?

Dastur diskdan ma'lumot so'raganida, javob millionlab protsessor tsikli davom etadi. Bu vaqt ichida protsessorni bo'sh turg'azish - katta isrof.

Shuning uchun yadro jarayonni bloklangan holatga o'tkazadi va protsessorni boshqasiga beradi. Ma'lumot kelganda jarayon yana tayyor navbatiga qaytadi.

Aynan shu mexanizm bir protsessorli kompyuterda ham o'nlab dastur bir vaqtda ishlayotgandek tuyulishiga sabab bo'ladi.

Linux'da holatlarni ko'rish #

Terminal
ps aux | head -5
Natija
USER  PID %CPU %MEM    VSZ   RSS TTY  STAT START   TIME COMMAND
root    1  0.0  0.1 168404 11928 ?    Ss   09:12   0:02 /sbin/init
root    2  0.0  0.0      0     0 ?    S    09:12   0:00 [kthreadd]
husan 842  1.2  2.4 985432 39812 ?    Sl   09:15   0:45 /usr/bin/firefox
husan 901  0.0  0.0  12456  3204 pts/0 R+  10:22   0:00 ps aux
STATMa'nosi
RIshlayotgan yoki tayyor (running / runnable)
SUxlayotgan - uzilishi mumkin (interruptible sleep)
DUxlayotgan - uzilmaydi (odatda disk kutmoqda)
ZZombi - tugagan, lekin otasi hali o'qimagan
TTo'xtatilgan (Ctrl+Z bilan)
sSessiya boshlig'i
+Old fonda (foreground)
lKo'p oqimli
D holati - diqqat belgisi

D holatidagi jarayonni o'ldirib bo'lmaydi - hatto kill -9 ham ta'sir qilmaydi.

U diskdan yoki tarmoqdan javob kutmoqda va uzilishga javob bermaydi. Odatda bu:

  • nosoz disk;
  • javob bermayotgan tarmoq fayl tizimi (NFS);
  • USB qurilma uzilib qolgani

haqida signal beradi. Uzoq vaqt D holatida turgan jarayon - tizimda apparat muammosi borligining alomati.

Jarayon identifikatori #

C
#include <stdio.h>
#include <unistd.h>

int main(void) {
    pid_t ozim = getpid();
    pid_t otam = getppid();

    printf("Mening PID     : %s\n", ozim > 0 ? "olindi" : "xato");
    printf("Otamning PID   : %s\n", otam > 0 ? "olindi" : "xato");
    printf("PID musbat son : %s\n", ozim > 0 ? "ha" : "yo'q");

    /* aniq raqamlarni ko'rish uchun: */
    /* printf("PID = %d, PPID = %d\n", ozim, otam); */

    return 0;
}
Natija
Mening PID     : olindi
Otamning PID   : olindi
PID musbat son : ha
PID har safar boshqacha

PID (Process ID) - jarayonning noyob raqami. U har safar dasturni ishga tushirganingizda boshqacha bo'ladi.

Linux'da PID lar ketma-ket beriladi va chegaraga yetganda yana boshdan boshlanadi:

Terminal
cat /proc/sys/kernel/pid_max

Odatda 4 194 304. PID 1 - init yoki systemd, u birinchi bo'lib ishga tushadi va boshqa hamma jarayonlarning ajdodi hisoblanadi.

Jarayonlar daraxti #

Terminal
pstree -p | head -12
Natija
systemd(1)─┬─ModemManager(892)─┬─{ModemManager}(915)
           │                   └─{ModemManager}(921)
           ├─NetworkManager(878)───{NetworkManager}(902)
           ├─bash(1204)───pstree(1567)
           ├─cron(864)
           ├─sshd(901)───sshd(1198)───bash(1204)
           └─systemd-journal(312)

Har bir jarayonning otasi bor. Daraxt ildizi - systemd (PID 1).

Jarayon boshqaruv bloki (PCB) #

Yadro har bir jarayon haqida ma'lumotni maxsus tuzilmada saqlaydi. Linux'da u task_struct deb ataladi.

PCB da nima saqlanadiNima uchun
PID va PPIDKimligini aniqlash
HolatTayyor, ishlayotgan, bloklangan
Registrlar nusxasiTo'xtatilgan joydan davom etish uchun
Xotira xaritasiQaysi sahifalar unga tegishli
Ochiq fayllar ro'yxatiFayl deskriptorlari
Foydalanuvchi (UID)Huquqlarni tekshirish
UstuvorlikRejalashtirish uchun
Ishlatilgan vaqtStatistika va adolatli taqsimot
Terminal
ls /proc/self/
Natija
cmdline  cwd  environ  exe  fd  limits  maps  root  stat  status  task

/proc/<PID>/ papkasi - bu PCB ning ochiq ko'rinishi.

Terminal
cat /proc/self/status | head -8
Natija
Name:    cat
Umask:    0022
State:    R (running)
Tgid:    2451
Ngid:    0
Pid:    2451
PPid:    1204
TracerPid:    0

Kontekst almashinuvi #

Kontekst almashinuvi (context switch) A jarayoni ishlayapti registrlar A ga tegishli PID 1234 Yadro 1. A ning registrlarini saqlaydi 2. B ning registrlarini tiklaydi B jarayoni ishlayapti registrlar B ga tegishli PID 5678 Almashinuv bepul emas Registrlarni saqlash/tiklash + kesh va TLB «sovib qoladi» Narxi: taxminan 1-10 mikrosoniya
Sekundiga minglab almashinuv sodir bo'ladi
Terminal
vmstat 1 3
Natija
procs -----------memory---------- ---system-- ------cpu-----
 r  b   swpd   free   buff  cache   in     cs us sy id wa st
 2  0      0 6823456 234560 4512332 1245  3421  3  1 96  0  0
 1  0      0 6823012 234560 4512332 1102  2987  2  1 97  0  0
 0  0      0 6822980 234560 4512332  987  2654  1  1 98  0  0

cs ustuni - sekundiga nechta kontekst almashinuvi bo'lganini ko'rsatadi. in esa uzilishlar (interrupts) soni.

Juda ko'p almashinuv - muammo belgisi

Agar cs qiymati o'n minglab bo'lsa, tizim foydali ish o'rniga almashinuv bilan band bo'lishi mumkin.

Sabablari:

  • juda ko'p faol oqim (thread);
  • qulflar uchun kurash (lock contention);
  • noto'g'ri sozlangan dastur.

Bu holat «thrashing» deb ataladi.

Jarayonni kuzatish #

Terminal
top -b -n 1 | head -12
Natija
top - 10:45:32 up 2 days,  3:12,  2 users,  load average: 0.42, 0.38, 0.35
Tasks: 312 total,   1 running, 311 sleeping,   0 stopped,   0 zombie
%Cpu(s):  2.1 us,  0.8 sy,  0.0 ni, 97.0 id,  0.1 wa,  0.0 hi,  0.0 si
MiB Mem :  15903.4 total,   6823.1 free,   4212.5 used,   4867.8 buff/cache

  PID USER      PR  NI    VIRT    RES    SHR S  %CPU  %MEM     TIME+ COMMAND
  842 husanboy  20   0  985432 398124 145232 S   1.2   2.4   0:45.23 firefox
 1204 husanboy  20   0   12456   5204   3412 S   0.0   0.0   0:00.12 bash
UstunMa'nosi
PR / NIUstuvorlik va «xushmuomalalik» darajasi
VIRTVirtual xotira - so'ralgan hajm
RESHaqiqiy xotira - RAM da yotgan hajm
SHRBoshqalar bilan bo'lishilgan xotira
%CPUProtsessor ulushi
TIME+Jami protsessor vaqti
VIRT va RES farqi

VIRT odatda RES dan ancha katta bo'ladi va bu normal.

Dastur 1 GB xotira so'rashi mumkin, lekin faqat 100 MB ini haqiqatan ishlatadi. Yadro qolganini RAM ga yuklamaydi.

Xotira muammosini baholashda RES ga qarang, VIRT ga emas. Buni 10-bo'limda, virtual xotira mavzusida batafsil ko'ramiz.

Jarayonga ta'sir qilish #

Terminal
kill 1234          # muloyim so'rov: tugating (SIGTERM)
kill -9 1234       # majburiy to'xtatish (SIGKILL)
kill -STOP 1234    # muzlatish
kill -CONT 1234    # davom ettirish

pkill firefox      # nom bo'yicha
killall firefox    # barcha nusxalarini
kill -9 - oxirgi chora

kill -9 jarayonga hech qanday imkon bermaydi: u ochiq fayllarni yopmaydi, buferni bo'shatmaydi, vaqtinchalik fayllarni tozalamaydi.

Natijada:

  • yozilmagan ma'lumot yo'qoladi;
  • yarim yozilgan fayl buziladi;
  • qulf fayllari qolib ketadi.

Avval oddiy kill (SIGTERM) ni sinang - u dasturga tozalanish imkonini beradi. Faqat javob bermasa -9 ga o'ting.

16-bo'limda signallarni batafsil ko'ramiz.

Amaliy topshiriq
  1. ps aux bilan tizimingizdagi jarayonlarni ko'ring.
  2. STAT ustunidagi turli holatlarni toping va izohlang.
  3. pstree bilan jarayonlar daraxtini chizing.
  4. O'z dasturingizning PID va PPID sini chiqaring.
  5. /proc/self/status faylini o'qing.
  6. /proc/<PID>/maps bilan jarayon xotira xaritasini ko'ring.
  7. vmstat 1 5 bilan kontekst almashinuvlarini kuzating.
  8. top da VIRT va RES farqini kuzating.
  9. Cheksiz sikl yozib, uni top da toping va kill bilan to'xtating.
  10. kill va kill -9 farqini sinab ko'ring.

Xulosa #

  • Dastur - diskdagi fayl; jarayon - ishga tushirilgan dastur.
  • Bir dasturdan ko'p jarayon yaratish mumkin, har birining o'z xotirasi bor.
  • Jarayon xotirasi beshta sohaga bo'linadi: text, data, bss, uyum, stek.
  • Stek va uyum bir-biriga qarab o'sadi.
  • Asosiy holatlar: tayyor, ishlayotgan, bloklangan.
  • I/O kutayotgan jarayon bloklanadi va protsessorni boshqasiga beradi.
  • D holati odatda apparat muammosidan darak beradi.
  • Yadro har bir jarayon haqidagi ma'lumotni PCB da saqlaydi; Linux'da uni /proc/<PID>/ orqali ko'rish mumkin.
  • Kontekst almashinuvi bepul emas - juda ko'p bo'lsa tizim sekinlashadi.
  • VIRT so'ralgan, RES haqiqatan ishlatilgan xotira.
  • kill -9 oxirgi chora - u tozalanishga imkon bermaydi.

Keyingi bo'limda jarayon qanday yaratilishini - fork va exec ni ko'ramiz.

Xatolik topdingizmi?

Imlo xatosi, ishlamaydigan kod yoki noto‘g‘ri ma‘lumotni ko‘rsangiz - bizga xabar bering. Har bir xabar administrator tomonidan ko‘rib chiqiladi.