Bài 2: khái quát về cấu trúc NES


Trước khi đi vào cấu trúc của NES, cần nắm rõ những khái niệm cơ bản trong lập trình. Và đối với ngôn ngữ cấp thấp như Asm thì cần phải hiểu biết nhiều về phần cứng. Tất cả mọi ngôn ngữ lập trình đều có chung 3 khái niệm cơ bản là tập lệnh (chỉ thị), biến số và lưu trình điều khiển. Nếu thiếu bất kỳ yếu tố nào trong số này thì đều không thể xem là ngôn ngữ lập trình được. Chẳng hạn, HTML vốn không có lưu trình điều khiển nên không được xem là một ngôn ngữ lập trình.


Tập lệnh: Câu lệnh (chỉ thị) là thành phần nhỏ nhất mà bộ xử lý thực hiện. Các câu lệnh được thực thi lần lượt từng câu một, lần lượt nối tiếp nhau. Trong bộ xử lý của NES chỉ có 56 câu lệnh, trong đó khoảng 10 câu lệnh thường dùng lặp đi lặp lại, chẳng hạn chứa một giá trị vào Register, câu lệnh so sánh một biến số với zero…

Biến số: Biến là một vùng lưu trữ dữ liệu có thể bị thay đổi. Chẳng hạn như số HP của nhân vật, nó có thể giảm xuống khi bị phe địch tấn công, được tăng lên khi dùng Item hồi phục. Biến có thể thay đổi bất kỳ lúc nào trong game khi một event liên quan xảy ra. Tất cả biến số trong mã nguồn đều có tên do người dùng đặt.

Lưu trình điều khiển: Về cơ bản thì các câu lệnh được thực hiện theo trật tự liên tục, một chiều từ trước ra sau. Nhưng đôi khi bạn muốn bộ xử lý thực thi một phần khác trong mớ code, tùy thuộc vào biến số. Lưu trình điều khiển có chức năng thay đổi hướng thực thi của chương trình, chẳng hạn như khi nhân vật đang bị tấn công thì nó sẽ nhảy đến đoạn code kiểm tra xem HP của nhân vật đã về zero hay chưa. Nếu đã về zero thì lại nhảy đến đoạn code xử lý hình ảnh nhân vật ngả xuống và không cho người chơi điều khiển nữa…

Mọi máy tính phổ thông đều có chung cơ cấu gồm một khu vực để chứa dữ liệu, code (ROM), một khu vực chứa các biến số (RAM) và một bộ xử lý (CPU) để thực thi code. Tuy nhiên CPU của NES còn có một thành phần khác gọi là APU (Audio Processing Unit) để xử lý âm thanh. Ngoài ra NES còn có một bộ xử lý khác để tạo ra hình ảnh, gọi là PPU. Những khái niệm ở đây hết sức cơ bản và sẽ lần lượt đề cập chi tiết trong những bài sau.

Hệ thống cấu trúc của NES

ROM: Viết tắt của cụm từ Read Only Memory, bộ nhớ chỉ đọc. Đây là khu vực chứa dữ liệu hình ảnh, âm thanh, mã chương trình… và không thể bị thay đổi trong quá trình thực thi. Đối với máy NES thì ROM được chứa trong con chip bên trong băng cartridge, đối với PlayStation thì ROM được chứa trong đĩa CD, với PlayStation 2 là DVD, PlayStation 3 là Blu-ray hay ổ cứng….

RAM: Viết tắt của cụm từ Random Access Memory, bộ nhớ truy cập ngẫu nhiên. Ram chứa dữ liệu có thể đọc hay ghi đè lên trong quá trình thực thi. Chẳng hạn cùng một địa chỉ Ram quản lý số HP, ban đầu giá trị là 80 (HP) nhưng khi bị địch tấn công, giá trị mới là 79 có thể ghi đè lên giá trị cũ. Khi tắt nguồn điện thì Ram mất hoàn toàn. Đối với máy NES thì có thể dùng pin để “nuôi” không cho Ram chết. Một số game như Final Fantasy, Fire Emblem có thời lượng rất dài, người chơi không thể hoàn thành game trong một thời gian ngắn nên băng cartridge cho những game này đều có pin nuôi dữ liệu (Ram) nên người chơi có thể tiếp tục ở chỗ đã dừng sau khi tắt máy đi ngủ một thời gian. Đây cũng là lý do khiến máy Gameboy mất hết dữ liệu save sau khi thay pin.

PGR: Program Memory, bộ nhớ chương trình. Nói nôm na là phần code của game. Đây là một trong những thành phần chính của ROM.

CHR: Character Memory. Một trong những thành phần chính của ROM. Nó chính là vùng chứa dữ liệu đồ họa của game. 

CPU: Cental Processing Unit, chip xử lý chính. Phần này nằm trong máy NES.

PPU: Picture Processing Unit, chip xử lý đồ họa nằm trong máy NES.

APU: Audio Processing Unit, chip âm thanh nằm trong CPU.



Tổng quan về hệ thống

Máy NES bao gồm một CPU 6502, một APU và Controller chung trong một con chip, một APU xử lý đồ họa trong con chip khác. Khi cắm Rom (băng Cartridge) vào máy, người chơi nhấn nút trên Controller, CPU sẽ đọc code trong Rom và thực thi chúng, gửi mệnh lên đến APU và PPU, từ đó phát âm thanh ra loa và hình ảnh ra màn hình. 

Sơ đồ dưới đây thể hiện khái quát về cách hoạt động của máy NES

[​IMG]

Chỉ có 2KB RAM kết nối với CPU để lưu trữ biến số và 2KB RAM kết nối với PPU để giữ 2 màn hình TV đối với hình ảnh nền (bối cảnh, background). Chú ý, KB là viết tắt của chữ KiloByte, 1KB=1024 byte. Nếu viết là Kb (chữ “b” viết thường) thì có nghĩa là KiloBit. 1 byte = 8 bit nên 1Kb=1/8 của 1KB.
Một vài băng Cartridge còn có thêm WRAM (Work RAM), một dạng CPU RAM. Nếu game cần lưu dữ liệu save (như Final Fantasy) thì sẽ có thêm viên pin nuôi WRAM này để dữ liệu không bị mất khi tắt máy, như đã nói ở phần trên. Một vài băng game còn có thêm PPU RAM để giữ 4 màn hình ảnh nền (background) cùng lúc, nhưng số lượng băng này không nhiều.

Mỗi băng Cartridge có ít nhất 3 con chip: chip chứa code chương trình (PRG ROM), chip chứa dữ liệu đồ họa (CHR) và một chip cho bộ khóa. Tuy nhiên dữ liệu hình ảnh có thể là RAM thay vì ROM, tùy vào game. Điều này có nghĩa là code của game sẽ cspy hình ảnh từ PRG ROM sang CHR RAM.

Bộ khóa

Bên trong máy NES và trong băng Cartridge luôn có 2 con chip khóa. Chip bộ khóa quản lý việc reset máy. Đầu tiên, bộ khóa trong NES gửi đi một xung với tần số nào đó, bộ khóa trong Cartridge ghi nhận con số này. Sau đó cả 2 bộ khóa thực hiện một phương trình phức tạp sử dụng con số đó và gửi kết quả cho nhau. Cả 2 chip đều biết rõ đối phương cần phải gửi dữ liệu gì nên cả 2 đều biết rõ khi có bất thường xảy ra. Khi có bất thường thì hệ thống sẽ đi vào vòng lặp khởi động lại liên tục. Điều này giải thích cho hiện tượng màn hình chớp sáng khi cắm băng bị bẩn vào.
Mục đích của bộ khóa là để ngăn chặn băng game lậu. Những băng lậu sau này đều có bộ bẻ khóa. Nguyên tắc hoạt động của chúng là gửi dòng điện từ băng làm tê liệt bộ khóa trong máy NES, ngăn không cho nó khởi động lại hệ thống. Sau đó, Nintendō cũng dần có đối sách phòng ngừa chuyện này. Khi mở máy NES, kiểm tra bản mạch sẽ thấy dòng NES-CPU- và con số tiếp sau đó. Con số này chính là phiên bản. 11 là phiên bản cuối cùng và hầu như không có game lậu nào chơi được trên máy NES-CPU-11.

Tổng quan về CPU

NES (Famicom) sử dụng CPU 6502 của hãng Motorola với một chút chỉnh sửa. 6502 là CPU 8 bit, nổi tiếng vì nó được sử dụng trong máy NES và máy Apple II, Atari 2600. Đương thời, sức mạnh của NES không thể sánh với một cỗ máy tính bình thường, nhưng cũng là quá đủ để chơi game.
CPU 6502 có Address bus 16 bit nên có thể truy cập vào 64KB bộ nhớ ($00~$FF). Bao gồm trong không gian bộ nhớ đó là 2KB của CPU RAM, các cổng để truy cập vào PPU/APU/Controller, WRAM (trong băng) và 32 KB dành cho PRG ROM. Chẳng hạn, RAM nội bộ bắt đầu từ $0000 ~ $0800. $0800 = 2048, tức 2 Kb. Phần chương trình gói gọn trong 32 KB, nhưng 32 KB là con số khá nhỏ đối với nhiều game nên Memory mapper được dùng để giải quyết vấn đề này. 

[​IMG]

Tổng quan về PPU

PPU trên NES là con chip hiển thị đồ họa, nó bao gồm RAM nội bộ chứa sprite (ảnh nhân vật) và palette màu. Trên bảng mạch NES còn có RAM chứa ảnh nền, và hình ảnh thực tế đều được xử lý từ bộ nhớ CHR trong băng Cartridge.
Chương trình chính không chạy trên PPU mà nó chỉ chứa vài tùy chỉnh như màu sắc hay cuốn màn hình. PPU xử lý một đường quét của TV tại một thời điểm. Đầu tiên, dữ liệu sprite được nạp từ CHR trong băng cắm, nếu có nhiều hơn 8 sprite trên một đường quét thì phần còn lại sẽ bị bỏ qua. Vì vậy, ở một số game thì hình ảnh sẽ nhấp nháy khi có nhiều thứ cùng thể hiện trên màn hình. Sau sprite là đến ảnh nền được nạp từ CHR. Khi tất cả các đường quét đều được xử lý xong thì sẽ có một khoảng thời gian không có bất kỳ hình ảnh nào được gửi ra màn hình. Khoảng này gọi là VBlank và là thời gian duy nhất để cập nhật đồ họa. TV hệ PAL có thời gian VBlank dài hơn, cho phép nhiều thời gian cập nhật hơn. Một vài game hệ PAL không chạy được trên TV NTSC vì khác biệt trong thời gian VBlank này. Cả PAL và NTSC đều cho độ phân giải 256x240 điểm ảnh, nhưng hàng trên cùng và dưới cùng của TV NTSC thường bị cắt đi 8 điểm ảnh, nên chỉ còn 256x224.

Tổng quan về đồ họa

Tile: tất cả mọi hình ảnh đều được cấu thành từ những tile 8x8 điểm ảnh. Những hình ảnh lớn hơn, như ảnh nhân vật, được cấu thành từ liên hợp nhiều tile 8x8. Hình ảnh dạng tile cần ít bộ nhớ hơn, nhưng không thể hiện được hình ảnh 3D hay bitmap. Có thể dùng các phần mềm như Tile Molester hay YY-CHR để xem tile bên trong game NES.

Sprite: PPU có đủ bộ nhớ để chứa 64 sprite hay những thứ chuyển động trên màn hình. Trên mỗi đường quét chỉ được phép tối đa là 8 sprite, số nhiều hơn sẽ bị bỏ qua.

Background: chính là ảnh nền, có thể cuộn theo chiều ngang hay dọc. Chẳng hạn trong game Mario, khi nhân vật di chuyển sang phải thì bối cảnh cũng thay đổi theo, tạo cảm giác màn hình đang cuốn sang phải. Bối cảnh gồm các tile 32x30 điểm ảnh. Có 2 màn hình bối cảnh được giữ trong bộ nhớ. 

Pattern Table: là vùng chứa dữ liệu hình ảnh thực tế, có thể là trong ROM hay RAM trong băng Cardtridge. Mỗi pattern gồm 256 tile. Một table được dùng cho bối cảnh, một để chứa sprite. Tất cả hình ảnh hiện trên màn hình đều phải nằm trong những table này.
Table thuộc tính: những table này thiết lập thông tin màu sắc trong những khu vực 2x2 tile. Có nghĩa là một vùng 16x16 điểm ảnh chỉ có 4 màu khác nhau được lựa chọn từ palette.

Palette: 2 khu vực này đều giữ thông tin về màu sắc, 1 cho ảnh nền và 1 cho ảnh sprite. Mỗi palette có 16 màu. Để hiển thị 1 tile lên màn hình, con số chỉ định màu sắc của điểm ảnh được đọc từ Pattern table và table thuộc tính, rồi con số này tìm trong palette để lấy màu sắc thực tế.

Dưới đây là hình ảnh sơ đồ PPU.

[​IMG]

0 bình luận :

Post a Comment

 
Top