Duy Nguyen Hoang A fully enthusiastic boy

MIPS Architecture Series – Phần 5: Convert

5 min read

mips convert c++ to mips

Trong phần này của chuỗi bài viết về kiến trúc MIPS, chúng ta sẽ tìm hiểu về cách chuyển đổi các câu lệnh điều kiện và vòng lặp từ ngôn ngữ lập trình C++ sang MIPS Assembly. Trước khi đi vào phần chính, hãy tóm tắt lại những gì chúng ta đã học ở bốn phần trước.

Sơ lược về 4 phần trước của loạt bài MIPS Architecture

Phần 1: Datapath

Chúng ta đã tìm hiểu về cấu trúc tổng quan của datapath trong kiến trúc MIPS, bao gồm các thành phần chính như thanh ghi (register), bộ nhớ (memory), bộ điều khiển (control unit) và ALU (Arithmetic Logic Unit). Datapath chịu trách nhiệm thực hiện các phép tính và lưu trữ dữ liệu trong quá trình thực thi chương trình.

Phần 2: Lệnh

Chúng ta đã xem xét các loại lệnh cơ bản trong MIPS Assembly như lệnh di chuyển, lệnh logic, lệnh nhảy và lệnh điều kiện. Mỗi lệnh có định dạng và tác dụng riêng, và chúng được biểu diễn dưới dạng các mã máy thích hợp.

Phần 3: Syscall

Chúng ta đã tìm hiểu về các lệnh syscall trong MIPS, cho phép chương trình tương tác với hệ điều hành để thực hiện các thao tác nhập xuất thông qua bộ điều khiển.

Phần 4: MARS

Chúng ta đã khám phá công cụ MARS (MIPS Assembler and Runtime Simulator), một môi trường giả lập cho phép chạy các chương trình MIPS và xem kết quả.

Giới thiệu về lệnh rẽ nhánh và nhảy trong MIPS

Trong MIPS, có các lệnh rẽ nhánh (branch) và lệnh nhảy (jump) để điều khiển luồng thực thi của chương trình. Lệnh rẽ nhánh kiểm tra một điều kiện nào đó và dựa trên kết quả, quyết định xem chương trình tiếp tục thực hiện ở địa chỉ nào tiếp theo. Lệnh nhảy cho phép chương trình nhảy tới một địa chỉ được chỉ định.

Rẽ nhánh (branch)

Lệnh rẽ nhánh trong MIPS Assembly thường được sử dụng để kiểm tra một điều kiện và nhảy tới một địa chỉ kh

ác dựa trên kết quả của điều kiện đó. Cú pháp của lệnh rẽ nhánh như sau:

beq rs, rt, label  # Nhảy tới 'label' nếu giá trị của rs và rt bằng nhau
bne rs, rt, label  # Nhảy tới 'label' nếu giá trị của rs và rt khác nhau

Trong đó:

  • rsrt là các thanh ghi mà chúng ta muốn so sánh.
  • label là một nhãn (label) mà chúng ta muốn nhảy tới nếu điều kiện đúng.

Ví dụ, để kiểm tra xem giá trị trong thanh ghi $s0 có bằng 0 hay không, chúng ta có thể sử dụng lệnh beq như sau:

beq $s0, $zero, label

Nếu $s0 bằng 0, chương trình sẽ nhảy tới nhãn label.

Nhảy (jump)

Lệnh nhảy trong MIPS Assembly cho phép chương trình nhảy tới một địa chỉ cụ thể. Cú pháp của lệnh nhảy như sau:

j label  # Nhảy tới 'label'

Trong đó:

  • label là một nhãn (label) mà chúng ta muốn nhảy tới.

Ví dụ, để nhảy tới nhãn loop, chúng ta có thể sử dụng lệnh j như sau:

j loop

Chương trình sẽ tiếp tục thực hiện từ địa chỉ của nhãn loop.

Áp dụng lệnh rẽ nhánh để chuyển đổi câu lệnh if-else trong C++ sang MIPS

Để chuyển đổi câu lệnh if-else trong C++ sang MIPS, chúng ta có thể sử dụng lệnh rẽ nhánh. Ví dụ, giả sử chúng ta có một đoạn mã C++ như sau:

if (a > b) {
    // Khối lệnh A
} else {
    // Khối lệnh B
}

Chúng ta có thể chuyển đổi nó sang MIPS Assembly như sau:

slt $t0, $s0, $s1    # so sánh a và b
beq $t0, $zero, else # nếu a <= b, nhảy tới else
# Khối lệnh A
j end               # nhảy tới cuối khối if-else

else:
# Khối lệnh B

end:

Ở đây, $s0$s1 là thanh ghi lưu trữ giá trị của ab tương ứng. Lệnh slt so sánh giá trị của $s0$s1, và kết quả được lưu trong thanh ghi $t0. Lệnh beq kiểm tra xem $t0 có bằng 0 hay không (tức là a <= b), nếu có, chương trình nhảy tới nhãn else. Nếu không, chương trình tiếp tục thực hiện khối lệnh A và sau đó nhảy tới nhãn end.

Áp dụng lệnh rẽ nhánh để chuyển đổi câu lệnh lặp C++ sang MIPS

Để chuyển đổi câu lệnh lặp trong C++ sang MIPS, chúng ta có thể sử dụng lệnh rẽ nhánh kết hợp với các lệnh di chuyển. Ví dụ, giả sử chúng ta có một đoạn mã C++ như sau:

for (int i = 0; i < 10; i++) {
    // Khối lệnh
}

Chúng ta có thể chuyển đổi nó sang MIPS Assembly như sau:

li $t0, 0            # Khởi tạo biến đếm i = 0

loop:
bge $t0, 10, end     # Nếu i >= 10, thoát khỏi vòng lặp
# Khối lệnh
addi $t0, $t0, 1     # Tăng giá trị của i lên 1
j loop              # Quay lại đầu vòng lặp

end:

Ở đây, $t0 là thanh ghi lưu trữ giá trị của biến đếm i. Lệnh li được sử dụng để khởi tạo giá trị ban đầu của i là 0. Lệnh bge kiểm tra xem $t0 có lớn hơn hoặc bằng 10 hay không. Nếu có, chương trình nhảy tới nhãn end, kết thúc vòng lặp. Nếu không, chương trình tiếp tục thực hiện khối lệnh và sau đó tăng giá trị của i lên 1 bằng lệnh addi. Cuối cùng, chương trình nhảy lại đầu vòng lặp bằng lệnh j.

Kết luận

Trong phần này, chúng ta đã tìm hiểu về cách chuyển đổi các câu lệnh if-else và lệnh lặp từ ngôn ngữ lập trình C++ sang MIPS Assembly. Bằng cách sử dụng lệnh rẽ nhánh và nhảy trong MIPS, chúng ta có thể điều khiển luồng thực thi của chương trình một cách linh hoạt. Việc hiểu và áp dụng các lệnh này sẽ giúp chúng ta xây dựng các chương trình MIPS mạnh mẽ và hiệu quả.

References: Bài giảng môn Tổ chức và Cấu trúc Máy tính, khoa KTMT – Trường ĐH CNTT (UIT)

Avatar photo
Duy Nguyen Hoang A fully enthusiastic boy

Clean Code: Nguyên tắc viết hàm trong lập trình…

Trong quá trình phát triển phần mềm, việc viết mã nguồn dễ đọc, dễ hiểu là yếu tố then chốt để đảm bảo code...
Avatar photo Dat Tran Thanh
3 min read

Clean Code: Nguyên tắc comment trong lập trình

Trong lập trình, code không chỉ là một tập hợp các câu lệnh để máy tính thực thi, mà còn là một hình thức...
Avatar photo Dat Tran Thanh
3 min read

Clean Code: Nguyên tắc xử lý lỗi (Error Handling)

Trong quá trình phát triển phần mềm, việc xử lý lỗi không chỉ là một phần quan trọng mà còn ảnh hưởng trực tiếp...
Avatar photo Dat Tran Thanh
4 min read

Leave a Reply

Your email address will not be published. Required fields are marked *