Bối cảnh và vấn đề nghiên cứu

Báo cáo kỹ thuật "Báo cáo Đồ án 3 - Nachos" được thực hiện trong khuôn khổ môn học Hệ điều hành (Học kỳ I, năm học 2021 – 2022) tại Trường Đại học Khoa học Tự nhiên – Đại học Quốc gia Thành phố Hồ Chí Minh, dưới sự hướng dẫn của giảng viên Lê Viết Long. Nhóm sinh viên thực hiện gồm ba thành viên: Bùi Phước Thiện (MSSV: 21127168), Phan Lâm Anh (MSSV: 21127580) và Quách Tấn Dũng (MSSV: 21127247). Văn bản hoàn thiện vào tháng 4 năm 2024.

Trong cấu trúc nguyên bản của hệ điều hành mô phỏng Nachos (phiên bản Nachos 3.4), môi trường thực thi được thiết kế ở trạng thái đơn chương, thiếu hụt các cơ chế quản lý vòng đời tiến trình, không gian địa chỉ động và cơ chế đồng bộ hóa giữa các luồng thực thi độc lập. Khi một tiến trình người dùng được nạp vào bộ nhớ, hệ thống chưa hỗ trợ các giao diện lập trình cấp hệ thống để tạo mới, chờ đợi hoặc kết thúc tiến trình một cách an toàn. Thực trạng này dẫn đến việc hệ thống tự động chấm dứt toàn bộ phiên làm việc ngay khi một luồng con kết thúc hoặc không thể điều phối nhiều chương trình cùng vận hành đồng thời.

Mục tiêu và nhiệm vụ nghiên cứu của đồ án được xác định cụ thể như sau:

  1. Nghiên cứu mô hình quản lý tiến trình, cơ chế đồng bộ hóa và các cấu trúc dữ liệu nền tảng trong hệ điều hành Nachos 3.4 (PTable, PCB, BitMap, Thread).
  2. Thiết kế và cài đặt ba lời gọi hệ thống (system call) cốt lõi phục vụ cơ chế đa chương: Exec (khởi tạo và thực thi tiến trình), Join (tiến trình cha chờ tiến trình con hoàn tất) và Exit (chấm dứt tiến trình con, trả mã thoát và nhường quyền điều khiển).
  3. Hiệu chỉnh mã nguồn hạt nhân của Nachos trong các tệp tin hệ thống (system.cc, system.h, addrspace.cc, addrspace.h, thread.cc, thread.h) nhằm hỗ trợ cấp phát bộ nhớ trang vật lý không liên tục và quản lý tiến trình cha - con.
  4. Cấu hình lại các thông số phần cứng mô phỏng (NumPhysPages, SectorSize) và kiểm thử tính đúng đắn của giải pháp thông qua chương trình điều phối scheduler chạy đồng thời hai tiến trình Ping và Pong.

Đối tượng nghiên cứu là nhân hệ điều hành mô phỏng Nachos 3.4 viết bằng ngôn ngữ C++, tập trung vào phân hệ quản lý tiến trình (userprog) và quản lý bộ nhớ. Phạm vi không gian nghiên cứu giới hạn trong môi trường giả lập máy ảo MIPS của Nachos. Phạm vi thời gian và phân công công việc kỹ thuật được ghi nhận: Bùi Phước Thiện chịu trách nhiệm cài đặt system call Exec và CreateSemaphore; Phan Lâm Anh chịu trách nhiệm cài đặt system call Join, Up và biên soạn báo cáo; Quách Tấn Dũng chịu trách nhiệm cài đặt system call Exit, Down và biên soạn báo cáo. Tỷ lệ hoàn thành công việc của cả ba thành viên đạt 100%.

Cơ sở lý thuyết và phương pháp

Nghiên cứu dựa trên nền tảng lý thuyết về hệ điều hành đa chương, mô hình tiến trình phân cấp (Parent - Child Process Model), không gian địa chỉ ảo và cơ chế đồng bộ hóa luồng thông qua Semaphore:

  • Mô hình quản lý tiến trình và đồng bộ hóa: Hoạt động phối hợp giữa luồng cha và luồng con dựa trên các nguyên lý đồng bộ hóa. Khi tiến trình cha gọi Exec, một luồng mới được tạo lập và biến đếm số lượng luồng con tăng lên. Khi gọi Join, tiến trình cha rơi vào trạng thái chờ (JoinWait(), sử dụng cơ chế Semaphore để chặn) cho đến khi tiến trình con kết thúc và phát tín hiệu giải phóng (JoinRelease()). Khi tiến trình kết thúc thông qua Exit, nó phải đợi tất cả các tiến trình con của chính nó hoàn tất thông qua ExitWait() trước khi gọi ExitRelease() để báo hiệu cho tiến trình cha.
  • Cơ chế chuyển đổi không gian nhớ và thanh ghi MIPS: Nachos mô phỏng kiến trúc phần cứng MIPS. Việc trao đổi dữ liệu giữa không gian người dùng (User Space) và không gian hạt nhân (System/Kernel Space) được thực hiện thông qua các thanh ghi máy ảo: thanh ghi R4 dùng để truyền tham số đầu vào (địa chỉ vùng nhớ, mã tiến trình hoặc mã thoát) và thanh ghi R2 dùng để chứa giá trị trả về của lời gọi hệ thống. Biến đếm chương trình (Program Counter) được điều chỉnh tăng sau mỗi system call để tránh hiện tượng lặp lệnh vô hạn.

Phương pháp nghiên cứu thực tế bao gồm:

  • Phương pháp phân tích và can thiệp mã nguồn: Khảo sát các lớp đối tượng có sẵn trong hệ thống Nachos, xác định các điểm bất đồng bộ trong constructor của lớp AddrSpace và tiến hành tái cấu trúc logic nạp dữ liệu từ tệp thực thi vào bộ nhớ chính.
  • Phương pháp kỹ thuật hệ thống (System Implementation): Khai báo các đối tượng quản lý toàn cục, bổ sung phương thức hỗ trợ dọn dẹp tài nguyên luồng (ThreadFinish()), tái sử dụng phương thức tìm kiếm vị trí bit trống của BitMap để quản lý khung trang vật lý và bảng tiến trình.
  • Phương pháp thực nghiệm kiểm thử: Xây dựng tệp mã nguồn người dùng scheduler.c kết hợp cùng ping.c và pong.c. Sử dụng cờ chuyển ngữ cảnh ngẫu nhiên -rs 1023 và cờ thực thi -x để kiểm tra khả năng chia sẻ thời gian của CPU giữa các tiến trình độc lập.

Nguồn dữ liệu kỹ thuật và tài liệu tham khảo được sử dụng gồm tài liệu hướng dẫn do giảng viên cung cấp ("Các Lớp Trong Project 3.docx", "DoAn3 CQ 2021.docx", "Cach Viet Mot SystemCall.pdf", "Seminar HDH_Project 3.pptx"), tài liệu lưu trữ hướng dẫn thực hành Nachos của Đại học Duke (CPS 110 Nachos Guide) và tài liệu kỹ thuật từ hệ thống Mystudy HCMUS.

Thiết kế và triển khai

Hệ thống được thiết kế dựa trên sự phối hợp của bốn cấu trúc dữ liệu chính trong Nachos, chịu trách nhiệm quản lý bảng tiến trình, khối điều khiển tiến trình, bộ nhớ bit và luồng thực thi.

Tên lớp / Cấu trúc Thuộc tính chính Phương thức chính Vai trò kỹ thuật
PTable MAXPROCESS (hằng số = 10), BitMap* bm, PCB* pcb[MAXPROCESS], int psize, Semaphore* bmsem PTable(int size), ExecUpdate(char* filename), ExitUpdate(int ec), JoinUpdate(int pID), GetFreeSlot(), IsExist(int pID), Remove(int pID), GetName(int pID) Quản lý toàn bộ các tiến trình trong hệ thống. Một thể hiện duy nhất pTab được khởi tạo toàn cục tại system.cc.
PCB Semaphore* joinsem, Semaphore* exitsem, Semaphore* mutex, int exitCode, Thread* thread, int pid, int numwait, int parentID, int joinstatus PCB(int id), Exec(char* filename, int pID), GetID(), GetNumWait(), JoinWait(), ExitWait(), JoinRelease(), ExitRelease(), IncNumWait(), DecNumWait(), SetExitCode(int ec), GetExitCode(), GetNameThread() Khối điều khiển tiến trình (Process Control Block), lưu trữ trạng thái vòng đời, quan hệ cha - con và điều phối đồng bộ hóa cho từng tiến trình.
BitMap BitsInByte, BitsInWord, int numBits, int numWords, unsigned int* map BitMap(int nitems), Mark(int which), Clear(int which), Test(int which), Find(), NumClear(), Print(), FetchFrom(OpenFile* file), WriteBack(OpenFile* file) Quản lý cấp phát và giải phóng tài nguyên dạng mảng bit. Dùng để quản lý khe tiến trình rỗng trong PTable và khung trang trong physicalPage.
Thread MachineStateSize, StackSize, ThreadStatus status, int* stackTop, int machineState[], int processID, int* stack, char* name, int userRegisters[], AddrSpace* space Thread(char* threadName), Fork(), Yield(), Sleep(), Finish(), CheckOverflow(), setStatus(), ThreadFinish() (nhóm bổ sung), SaveUserState(), RestoreUserState() Quản lý ngữ cảnh thực thi CPU, ngăn xếp (stack), trạng thái luồng (JUST_CREATED, RUNNING, READY, BLOCKED) và vùng nhớ người dùng.

Quy trình hoạt động kỹ thuật của ba lời gọi hệ thống được cài đặt:

  • Cài đặt System Call Exec: Nhận địa chỉ vùng nhớ chứa tên tệp chương trình từ thanh ghi R4. Đọc chuỗi tên với độ dài MAX_BUFFER_LENGTH + 1 (tương đương 255 byte) và chuyển đổi từ User Space sang System Space. Nếu việc đọc tên thất bại, hệ thống ghi giá trị -1 vào thanh ghi R2 và thoát. Nếu thành công, gọi phương thức pTab->ExecUpdate(filename) để tiến hành khởi chạy tiến trình, lưu mã định danh tiến trình nhận được vào biến pid, sau đó ghi pid vào thanh ghi R2 và tăng biến đếm Program Counter.
  • Cài đặt System Call Join: Đọc mã định danh tiến trình con cần chờ từ thanh ghi R4 và gán vào biến pid. Chuyển pid vào phương thức pTab->JoinUpdate(pid). Phương thức này chặn tiến trình cha cho đến khi tiến trình con hoàn tất và trả về mã thoát exitCode. Kết quả được ghi vào thanh ghi R2 trước khi tăng Program Counter để tiếp tục lệnh kế tiếp.
  • Cài đặt System Call Exit: Đọc giá trị mã thoát từ thanh ghi R4 và gán vào biến joinExitCode. Nếu xảy ra lỗi từ phía Join (mã khác 0), chương trình tăng Program Counter và kết thúc. Trường hợp không có lỗi, giá trị này được nạp vào phương thức pTab->ExitUpdate(joinExitCode). Sau đó, hệ thống thực hiện giải phóng tài nguyên cho con trỏ luồng hiện hành currentThread bằng cách gọi phương thức tĩnh ThreadFinish(), tăng Program Counter và kết thúc.

Các hiệu chỉnh bổ sung trong mã nguồn hệ thống:

  1. Khai báo biến toàn cục mới tại vùng #USER_PROGRAM trong system.cc:
    • Semaphore* addrLock: Semaphore khởi tạo với giá trị ban đầu bằng 1, bảo đảm truy xuất độc quyền vào các thao tác của lớp AddrSpace.
    • PTable* pTab: Khởi tạo đối tượng bảng tiến trình với khả năng quản lý tối đa 10 tiến trình (MAXPROCESS = 10).
    • BitMap* physicalPage: Khởi tạo với kích thước 256 bit, chịu trách nhiệm quản lý việc cấp phát các khung trang bộ nhớ vật lý.
  2. Hiệu chỉnh phương thức GetFreeSlot() và ExecUpdate(): Tận dụng phương thức Find() của lớp BitMap để tìm vị trí trống và tự động đánh dấu, loại bỏ lệnh bm->Mark(ID) bị dư thừa trong ExecUpdate(). Bổ sung lệnh gán quan hệ cha - con: pcb[ID]->parentID = currentThread->processID.
  3. Hiệu chỉnh phương thức ExitUpdate(): Bỏ qua điều kiện kiểm tra tiến trình cha như phiên bản mã nguồn cũ nhằm đảm bảo tiến trình luôn thực hiện giải phóng Join để tránh việc Nachos dừng đột ngột khi tiến trình cha chưa hoàn tất.
  4. Tái cấu trúc constructor AddrSpace: Thay đổi chữ ký phương thức từ AddrSpace::AddrSpace(OpenFile* executable) sang AddrSpace::AddrSpace(char* filename). Đặt đoạn mã khởi tạo giữa cặp lệnh khóa addrLock->P() và addrLock->V(). Kiểm tra điều kiện số trang yêu cầu numPages không vượt quá số trang vật lý còn trống (physicalPage->NumClear()). Thay thế cơ chế gán trang vật lý tuần tự pageTable[i].physicalPage = i bằng phương thức cấp phát động physicalPage->Find(). Cập nhật lại logic chuyển phân đoạn dữ liệu tệp NOFF vào bộ nhớ chính machine->mainMemory. Gán định danh tiến trình thread->processID = currentThread->processID trong phương thức Exec().
  5. Bổ sung phương thức tĩnh Thread::ThreadFinish(): Thực hiện giải phóng không gian địa chỉ space của biến toàn cục currentThread và yêu cầu luồng dừng thực thi.
  6. Cập nhật hằng số phần cứng giả lập: Nâng giá trị hằng số NumPhysPages từ giá trị cũ lên 128 trang vật lý; điều chỉnh giá trị hằng số SectorSize lên 512 byte.

Nội dung chính theo từng chương

Thông tin nhóm và công việc phân công

Báo cáo liệt kê chi tiết cơ cấu thành viên nhóm và bảng phân bổ công việc. Cả ba thành viên đều đảm nhận khối lượng công việc cụ thể liên quan trực tiếp đến việc phát triển mã nguồn của các system call (Exec, CreateSemaphore, Join, Up, Exit, Down) và viết báo cáo, đạt mức độ hoàn thành 100%.

Mô hình quản lý tiến trình

Nội dung chương mô tả luồng điều phối của ba thao tác cơ bản trong hệ điều hành đa chương:

  • Hoạt động Exec: Luồng cha kích hoạt luồng con, tăng biến đếm quản lý luồng trong lớp luồng cha.
  • Hoạt động Join: Luồng cha rơi vào trạng thái chờ đợi thông qua JoinWait() (bản chất sử dụng cơ chế Semaphore). Khi luồng con thực thi xong, nó phát tín hiệu JoinRelease() để đánh thức luồng cha tiếp tục hoạt động.
  • Hoạt động Exit: Khi một luồng hoàn tất công việc, nó bắt buộc phải chờ toàn bộ các luồng con kết thúc thông qua ExitWait(). Khi các luồng con đã hoàn tất, luồng này gọi ExitRelease() để cho phép luồng cha tiếp tục. Điểm lưu ý quan trọng là nếu hệ thống chỉ dùng Join mà không có Exit, Nachos sẽ dừng ngay lập tức khi luồng con đầu tiên kết thúc.

Các lớp cần tìm hiểu

Chương này hệ thống hóa toàn bộ thông tin kiến trúc của bốn lớp đối tượng quan trọng trong mã nguồn Nachos bao gồm: PTable, PCB, BitMap và Thread. Từng lớp được mô tả chi tiết dưới dạng bảng liệt kê tên thuộc tính, hằng số, kiểu dữ liệu, chức năng và nguồn gốc cung cấp từ phía giảng viên. Đây là nền tảng kỹ thuật để nhóm tiến hành chỉnh sửa và viết thêm mã nguồn.

Các system call mà nhóm cần cài đặt thêm vào

Phần này trình bày giải thuật chi tiết và mã giả của ba system call: Exec, Join và Exit. Nội dung giải thích rõ ràng cơ chế tương tác với các thanh ghi MIPS giả lập (R2, R4), quy trình chuyển đổi dữ liệu giữa bộ nhớ người dùng và hệ thống, cách thức gọi các phương thức tương ứng của biến toàn cục pTab (ExecUpdate, JoinUpdate, ExitUpdate) và thao tác cập nhật thanh ghi Program Counter để kết thúc system call.

Các chỉnh sửa đã thực hiện ở source code

Tài liệu ghi lại toàn bộ các can thiệp thực tế trên mã nguồn C++ của hệ thống Nachos:

  • Khai báo và khởi tạo 3 biến toàn cục mới trong system.cc (addrLock, pTab, physicalPage).
  • Điều chỉnh logic cấp phát trong GetFreeSlot(), tối ưu hóa ExecUpdate() và sửa đổi luồng kết thúc trong ExitUpdate().
  • Sửa đổi constructor của AddrSpace để hỗ trợ nạp tệp trực tiếp theo tên, đồng bộ hóa bằng Semaphore và phân phối trang nhớ vật lý động thông qua BitMap.
  • Cập nhật phương thức MyStartProcess(int pID), bổ sung hàm tĩnh ThreadFinish() dọn dẹp bộ nhớ và tăng kích thước phần cứng giả lập (NumPhysPages = 128, SectorSize = 512).

Chạy thử chương trình Scheduler

Chương này trình bày kịch bản thực nghiệm nhằm chứng minh hệ thống đã hỗ trợ đa chương thành công:

  • Tái cấu trúc chương trình scheduler.c sử dụng system call Join để chờ cả hai tiến trình Ping và Pong chạy xong, in ra chuỗi thông báo kết thúc "Finish Ping-Pong test".
  • Giữ nguyên cấu trúc của chương trình Ping và Pong theo yêu cầu đề bài.
  • Cung cấp câu lệnh thực thi kiểm thử và trích xuất nguyên văn nhật ký xuất ra từ màn hình console máy ảo.

Tổng kết và hướng dẫn sử dụng

Tổng kết các hạng mục đã hoàn thành, ghi nhận tình trạng thực hiện và cung cấp tài liệu hướng dẫn từng bước từ việc biên dịch mã nguồn bằng lệnh make đến câu lệnh khởi chạy chương trình kiểm thử trên console.

Kết quả và đóng góp

Đồ án ghi nhận kết quả thực nghiệm hoàn chỉnh thông qua việc biên dịch và chạy kịch bản kiểm thử đa chương với lệnh:

../userprog/nachos -rs 1023 -x ./test/scheduler

Kết quả hiển thị trên màn hình console cho thấy hai tiến trình Ping (in ký tự A) và Pong (in ký tự B) được CPU lập lịch luân phiên xuất hiện xen kẽ nhau liên tục. Trước khi hệ thống dừng lại, thông điệp kiểm thử hoàn tất đã xuất hiện chính xác:

Ping-Pong test starting.
AAAAAAAAABBBBBBBBBBBBBBAAAAAABBBBBBBAABBBAAABBBAABAABBBAAAAAABBAAAAAAAABBBBBAAAABAABBBABAABBBBBBBBABAABAABBB...
Finish Ping-Pong test
Machine halting!

Các thông số thống kê phần cứng máy ảo ghi nhận tại thời điểm kết thúc phiên thực thi:

Thông số hoạt động hệ thống Giá trị ghi nhận
Tổng số nhịp đồng hồ (Ticks: total) 297,750
Nhịp trạng thái rảnh (Ticks: idle) 195,607
Nhịp thực thi hệ thống (Ticks: system) 70,030
Nhịp người dùng thực thi (Ticks: user) 32,113
Thao tác đĩa (Disk I/O: reads / writes) 0 / 0
Thao tác màn hình Console (Console I/O: reads / writes) 0 / 2,053
Lỗi trang bộ nhớ (Paging: faults) 0
Giao tiếp mạng (Network I/O: packets received / sent) 0 / 0

Đóng góp kỹ thuật của đồ án bao gồm:

  • Hoàn thành đầy đủ bộ ba system call cơ bản quản lý đa chương (Exec, Join, Exit), cho phép Nachos thực thi các chương trình người dùng độc lập.
  • Chuyển đổi thành công cơ chế quản lý bộ nhớ của Nachos từ cấp phát tĩnh liên tục sang cấp phát động theo từng khung trang vật lý dựa trên cấu trúc BitMap, giải quyết tình trạng xung đột không gian nhớ giữa các tiến trình khi chạy đa chương.
  • Đảm bảo an toàn luồng và đồng bộ hóa tiến trình thông qua việc tích hợp Semaphore (addrLock, joinsem, exitsem, bmsem) vào cấu trúc AddrSpace và PTable.

Hạn chế và hướng nghiên cứu tiếp

Trong văn bản báo cáo, phần "Những điều chưa làm được" được nhóm tác giả để trống nội dung. Tuy nhiên, căn cứ vào giới hạn cấu hình và phạm vi triển khai thực tế được trình bày trong tài liệu:

  • Hạn chế kỹ thuật: Số lượng tiến trình đa chương tối đa bị giới hạn cố định ở mức 10 tiến trình (MAXPROCESS = 10). Bộ nhớ vật lý được nâng lên 128 khung trang (NumPhysPages = 128), hệ thống chưa cài đặt cơ chế bộ nhớ ảo mở rộng (swap file/backing store) ra đĩa từ khi bộ nhớ đầy (thống kê Disk I/O ghi nhận 0 lượt đọc/ghi và Paging faults ghi nhận 0). Cơ chế phân phối trang chỉ dừng ở mức tìm kiếm vị trí bit trống đầu tiên (Find()).
  • Hướng nghiên cứu tiếp theo: Nâng cấp khả năng quản lý danh sách tiến trình động thay vì mảng tĩnh giới hạn bởi MAXPROCESS; nghiên cứu và hiện thực các giải thuật thay thế trang (Page Replacement Algorithms như FIFO, LRU) khi số lượng trang yêu cầu vượt quá dung lượng 128 khung trang vật lý có sẵn.

Giá trị tham khảo

Báo cáo là tài liệu tham khảo trực tiếp cho sinh viên ngành Khoa học Máy tính, Kỹ thuật Phần mềm và Công nghệ Thông tin đang theo học học phần Hệ điều hành hoặc các môn học có thực hành trên mã nguồn Nachos.

Các phần nội dung có giá trị tham khảo chuyên sâu gồm:

  • Quy trình chuẩn hóa thao tác đọc dữ liệu chuỗi từ User Space vào Kernel Space thông qua thanh ghi MIPS trong system call Exec.
  • Kỹ thuật tái cấu trúc constructor AddrSpace để nạp tệp chương trình và cấp phát bộ nhớ động không liên tục thông qua BitMap::Find().
  • Phương pháp phối hợp giữa JoinWait(), JoinRelease(), ExitWait() và ExitRelease() để kiểm soát tiến trình cha - con, ngăn ngừa việc hệ điều hành bị sập sớm khi có tiến trình hoàn tất trước.

Câu hỏi thường gặp

1. Vì sao nhóm tác giả phải thay đổi constructor của lớp AddrSpace từ nhận con trỏ OpenFile* sang nhận chuỗi char* filename?
Nhóm tác giả thay đổi cấu trúc này do phát hiện sự bất đồng bộ trong cách gọi constructor ở đoạn mã nguồn có sẵn được cung cấp. Việc nhận trực tiếp tên tệp (char* filename) cho phép hàm tự quản lý việc mở tệp, đồng thời cho phép bao bọc toàn bộ logic kiểm tra dung lượng trang trống (NumClear()) và cấp phát khung trang vật lý động giữa cặp khóa đồng bộ addrLock->P() và addrLock->V().

2. Lời gọi hệ thống Exec trao đổi tham số và trả kết quả cho tiến trình thông qua các thanh ghi nào?
Tham số đầu vào là con trỏ mảng ký tự chứa tên tiến trình được đọc từ thanh ghi R4 với kích thước giới hạn MAX_BUFFER_LENGTH + 1 (255 byte). Kết quả thực thi là mã định danh tiến trình (pid) hoặc mã lỗi -1 (khi không đọc được tên tiến trình) được ghi trực tiếp vào thanh ghi R2 trước khi trả quyền điều khiển về cho người dùng.

3. Tại sao trong phương thức ExitUpdate(int ec), nhóm tác giả lại lược bỏ đoạn mã kiểm tra tiến trình cha như mã nguồn cũ?
Theo phân tích của nhóm, phương thức ExitUpdate chỉ được kích hoạt từ lời gọi hệ thống Exit. Để Exit có thể chạy, điều kiện tiên quyết là phải có một tiến trình nào đó đã được Join. Do đó, việc kiểm tra tiến trình cha là không cần thiết. Nếu không thực hiện thao tác giải phóng tiến trình tại bước này, Nachos sẽ lập tức ngừng hoạt động trong khi tiến trình cha vẫn chưa hoàn thành công việc.

4. Mục đích của việc viết lại chương trình kiểm thử scheduler.c và bổ sung lệnh gọi Join là gì?
Nếu không sử dụng lệnh gọi hệ thống Join, khi một trong hai chương trình Ping hoặc Pong chạy xong trước, hệ thống Nachos sẽ hiểu lầm là toàn bộ công việc đã hoàn tất và dừng máy ảo ngay lập tức. Việc bổ sung Join bắt buộc tiến trình điều phối scheduler phải chờ cả hai tiến trình Ping và Pong kết thúc hoàn toàn rồi mới tiếp tục chạy đến lệnh in dòng chữ "Finish Ping-Pong test" trước khi hệ thống dừng lại.

5. Các thông số phần cứng của Nachos đã được nhóm điều chỉnh như thế nào và kết quả nhịp xung nhịp khi chạy kiểm thử đạt bao nhiêu?
Hằng số số lượng trang vật lý NumPhysPages được điều chỉnh thành 128 và kích thước sector đĩa SectorSize được đổi thành 512. Khi chạy kiểm thử với tham số -rs 1023, tổng số nhịp xung nhịp của máy ảo đạt 297,750 Ticks, bao gồm 195,607 nhịp rảnh (idle), 70,030 nhịp hệ thống (system) và 32,113 nhịp người dùng (user).

Kết luận

Đồ án "Báo cáo Đồ án 3 - Nachos" của nhóm sinh viên Trường Đại học Khoa học Tự nhiên – ĐHQG-HCM đã hiện thực hóa thành công cơ chế quản lý tiến trình đa chương trên hệ điều hành mô phỏng Nachos 3.4. Nghiên cứu đã hoàn thành việc cài đặt ba lời gọi hệ thống nòng cốt Exec, Join, Exit kết hợp cùng cơ chế đồng bộ hóa bằng Semaphore và cấp phát khung trang vật lý động thông qua cấu trúc BitMap. Kết quả kiểm thử thực nghiệm trên chương trình scheduler điều phối luân phiên hai tiến trình Ping và Pong chứng minh hệ thống vận hành ổn định, chính xác theo đúng các nguyên lý thiết kế của hệ điều hành.