10 4.104 8051 9 Acquy adc pic All datasheet ALTIUM Altium Designer AM-FM Arduino ARM ARM là gì Ấn Tượng Bản tin công nghệ Bản tin Thiết Bị Số Barobo bất động sản biến Binary Bit board lpc2378 Bộ chuyển đổi ADC Bộ Đếm Bộ điều khiển cửa cuốn Bộ Định Thời Buy Khóa Số Điện Tử Buy Mạch đếm sản phẩm Buy Mạch giao thông Buy Mạch nạp Buy Matrix Byte C cho AVR các hàm vào ra các loại lõi arm các mạch DAC cơ bản các ngắt trong pic Cách đọc điện trở Cách Đọc Giá Trị Điện Trở Cách đọc giá trị tụ điện Cách hàn linh kiện dán cách làm mạch khóa số cách tạo linh kiện dán cad/cam Cài Đặt cài đặt proteus 8 cảm biến Cấu Kiện Logic Khả Trình cấu tạo cấu trúc arm cấu trúc lệnh CCS Chân chân Transistor Chip Khả Trình chuyển đổi Chuyển đổi số tương tự Chuyển Đổi Tương Tự/Số - ADC Chuyển động số chương trình City Clip Điện Tử Code 8051 - ASM Code 8051 - C Code 8051-C code ASM code ASM mẫu 8086 Code AVR - C code C Code Lập Trình Code led sao băng code maupic code mẫu 8051 Code Mẫu 8086 Code Mẫu cho ARM - LPC1343 code mẫu pic Code PIC - C codemaupic Counter Cổng Vào Ra Cơ Bản Cuộn Cảm Cửa cuốn DA DAC Debug Decimal Delay8051 Dev-C++ Diode DIY Dò đường Do It Yourself doanh nghiệp Download DTMF Mobile đảo chiều động cơ Điện Trở Điện Tử Điện Tử Cơ Bản điều chế độ rộng xung điều chế xung PWM điều khiển bằng điện thoại Điều khiển cửa cuốn Điều khiển cửa cuốn bằng điện thoại điều khiển động cơ đo điện áp đo nhiệt độ đo nhiệt độ hiển thị lên lcd trên 8051 Đo Nhiệt Độ LM35 + LCD Đo Nhiệt Độ LM35 + Led 7 thanh đọc màu điện trở đồ chơi động cơ chân không Động cơ nhiên liệu Động cơ robo đồng hồ thời gian thực Ebook Đại Học ebook điện tử Ebook đồ án Ebook Tin Học Encoder Encoder là gì Full Giải Thuật Giải thuật PID Giáo Dục giao tiếp i2c pic 16f877a giao tiếp i2c pic16f877a với ic ds1307 giao tiếp máy tính qua rs232 Giao Tiếp Máy Tính VB6 giao tiếp rs232 giao tiếp spi giữa 2 pic giao tiếp spi trong pic Giáo Trình Điện Tử Giới thiệu 8051 Giới thiệu cơ bản GPIO Graphic Design hàm Hàn linh kiện dán Hexadecimal Hệ Hexa Hệ Nhị Phân Hệ Thập Lục Phân Hệ Thập Phân hiển thị lên lcd 16x2 Hoạt Động Học Học 8051 qua các ví dụ đơn giản Học ALtium Designer học AVR Học Corel Draw X3 Học Eagle HỌC LẬP TRÌNH 16F877A Học Lập Trình 8051 Học Lập Trình C Học Orcad Học Protues hoc-lam-robot-do-duong-qua-video Hồng ngoại hướng dẫn hướng dẫn Altium Designer hướng dẫn đo đồng hồ VOM hướng dẫn keil - C lập trình 8051 hướng dẫn làm led sao băng hướng dẫn làm led trái tim hướng dẫn lập trình ARM Hướng Dẫn Lập Trình ARM - LPC1343 hướng dẫn lập trình ARM-LPC2378 hướng dẫn lập trình CCS hướng dẫn lập trình PIC Hướng Dẫn Led Trái Tim hướng dẫn module sim548c hướng dẫn sử dụng keil hướng dẫn sử dụng proteus 8 Hyper Terminal hercules 3.2.4 I/O IC 555 IC 7447 IC 74HC151 IC 74HC154 IC 74HC245 IC 74HC595 IC 74LS138 IC DS1307 IC đồng hồ thời gian thực IC LM324 IC LM342 IC LM7805 IC số IC số opamp LM324 IC Thông Dụng IC555 Interrupt Keil 4 Full keil arm Keil C Keil uVision3 kế toán kiểm toán khái niệm Khái Niệm Cơ Bản Kho Vật Liệu khóa điện tử khóa số dùng 8051 khóa số dùng 89s52 Khóa Số Điện Tử khuếch đại kiểm tra Kinh doanh maketing kinh tế quản lí Kỹ Thuật Kỹ Thuật Vi Xử Lý làm mạch điện lý thú Làm quen AVR Lap Trinh Dieu Khien Robot Lập Trình lập trình 8051 Lập Trình AVR Lập Trình C lập trình c++ Lập Trình Led Quảng Cáo Lập Trình Nhúng Lập trình pic Lập trình Robot Lập Trình Vi Điều Khiển Lập Trình Với AVR Studio LCD 16x2 Lcd16x2 Led Clock Led Quay led sao băng led trai tim Led Trái Tim Lịch sử ra đời Linh Kiện Cơ Bản linh kiện điện tử Loa LPC 2378 LSB lý thú Mã AVR - C Mạch 7seg Mạch Amply.Mạch Loa Mạch Autorobo Mạch bảo vệ Mạch Cảm Biến mạch cảm ứng sờ tay Mạch Cầu H Mạch cube Mạch Đếm Sản Phẩm Mạch điện cơ bản Mạch điện hay Mạch Điện Ứng Dụng Mạch Điều khiển động cơ Mạch Động Cơ Mạch đồng hồ Mạch đồng hồ 4 led Mạch giao thông Mạch IC số Mạch in mạch khóa số mạch khuếch đại thuật toán mạch led chúc mừng năm mới mạch led đẹp Mạch Led đơn Mạch Led Quảng Cáo mach led trai tim mạch led trái tim Mạch Led Vumeter mạch lý thú Mạch Ma trận Phím Mạch Matrix Mạch nạp Mạch nguồn Mạch Nút Bấm mạch sóng rf mạch tăng áp Mạch thu phát Mạch tổ hợp MSI Mạch trái tim Mạch Vi điều khiển Microbicho module module GSM/GPS Module Sim548 Module Sim548 giao tiếp với vi điều khiển PIC Module Sim548C Mosfet Motor Mô Phỏng Phần Cứng Mô Tả Phần Cứng MSB mua led sao băng News Ngắt Ngắt Trong LPC23xx ngân hàng Ngôn Ngữ Ngôn Ngữ C Ngôn Ngữ Tự Học Lập Trình C Ngôn Ngữ VHDL Nguyên Lý nguyên lý ic 555 Nguyên Tắc nháy led Nhập môn C Nhỏ Gọn Nibble opamp People Phần Mềm phần mềm altium Designer Phần mềm điện tử Phần Mềm Điện Tử Phần Mềm Điện Tử Hay Phần Mềm Hay Phần Mềm Led Quảng Cáo phần mềm proteus 8 Phần mềm vi tính Phần Mền Phương pháp hàn linh kiện dán PIC pic16f877a Print Design Proteus Proteus 7.8 SP2 FULL PWM quà tặng bạn gái quà tặng độc đáo quản trị doanh nghiệp quản trị kinh doanh quét led 7 đoạn Relay robocon Robot ROBOT DÒ ĐƯỜNG rút gọn mạch logic tổ hợp Sach Dien Tu Sản Phẩm Thú Vị Sản Phẩm Thương Mại Sáng tạo Short Smart Home SMD sơ đồ nguyên lý spi Sports Sử Dụng Sử Dụng Đồng Hồ sử dụng đồng hồ VOM sử dụng ngắt trong pic sự khác nhau Sức mạnh số Tải tài chính tài chính doanh nghiệp tài chính ngân hàng Tài Khoản Chia Sẻ Tài Liệu Tài Liệu 8051 tài liệu avr Tài liệu Điện Tử Tài Liệu Pic Tài liệu robocon tài liệu về ngân hàng Tài Liệu Vi Điều Khiển tailieuvn Tạo cổng Com ảo Tạo cổng nối tiếp ảo tạo dự án trong keil arm Tạo Project trong Vi Xử Lý ARM tạo thư viện altium designer tạo xung vuông Tạp chí Tạp Chí Hay tăng áp Tập lệnh AT Team Support TEAMPLATE PROTEUS Test thị trường tài chính Thiết Bị Thú Vị Thiết kế robot Thiết lập Fuse Bits Thiết Lập Pin Thuật Toán Thuật Toán Điều Khiển PID Thuật Toán Quine MCCluskey Thư viện Protues Thực Hành Thyristor Timer Timer/Counter Tin Học Chia Sẻ Tổ Chức Bộ Nhớ tổng quan về proteus 8 Transistor Tranzito Tranzitor Trao đổi học tập Travel Trình Biên Dịch Trình Dịch Trong Suốt Truyền Thông Nối Tiếp Không Đồng Bộ- UART truyền thông nối tiếp RS232 Tụ điện TUT - 8051 - ASM TUT - 8051 - KeilC tự hành Tự Học C Tự Học Lập Trình C Tý hon UART Update USB Ứng Dụng Led Quảng Cáo ứng dụng mạch khuếch đại thuật toán vẽ mạch in vẽ mạch nguyên lý VHDL Vi Điều Khiển Vi điều khiển - Ứng dụng vi điều khiển PIC Vi mạch số Vi Xử Lý Vi Xử Lý 8051 Vi Xử Lý 8086 Vi Xử Lý ARM Vi Xử Lý PIC Video Video Mach Điện Virtual Serial Port Driver VOM vxl Web Design xác định góc quay động cơ xử lý chuỗi


Phần này Chip giới thiệu một số instruction mà  rất hay sử dụng khi lập trình cho AVR. Chip sẽ chia các instruction này ra thành nhiều nhóm dựa theo phạm vi tác động và chức năng của chúng.



Trước hết chúng ta thống nhất một số cách sử dụng ký hiệu trong cách viết cú pháp của các instruction như sau:

Rd: thanh ghi nguồn và cũng là đích thuộc Register File.
Rr: thanh ghi nguồn thuộc Register File.
Khái niệm nguồn (Source), đích (Destination) là chỉ các toán hạng và kết quả trong các phép toán đại số và Logic, ví dụ ADD R1, R2 là lệnh cộng 2 giá trị chứa trong 2 thanh ghi R1, R2, trong trường hợp này cả R1 và R2 đều được gọi là nguồn vì chứa giá trị trước khi thực hiện phép cộng. Sau khi phép cộng được thực hiện, kết quả được chứa lại trong R1 và vì thế R1 được gọi là đích trong trường hợp này. R1 vừa là nguồn, vừa là đích trong khi R2 chỉ là nguồn, nếu viết ví dụ này dưới dạng tổng quát sẽ là : ADD Rd, Rr.
R: kết quả sau khi lệnh được thực thi.
K: hằng số.
k: hằng số chỉ địa chỉ tuyệt đối của thanh ghi.
b: (0 đến 7) số thứ tự bit trong các thanh ghi của Register File và vùng nhớ I/O.
s: (0 đến 7) số thứ tự bit trong thanh ghi trạng thái SREG.
X,Y,X: các thanh ghi địa chỉ tương đối (X=R27:R26, X=R29:R28, X=R31:R30).
A: địa chỉ I/O.
q: độ dịch chuyển của địa chỉ tuyệt đối.
I. Instruction chỉ dùng cho Register Files.

- LDI (LoaD Immediate).

Cú pháp: LDI Rd,K
Chức năng: Load hằng số K vào thanh ghi Rd.
Giới hạn: chỉ áp dụng cho các thanh ghi từ R16 đến R31.
Ví dụ: LDI R16, 99 kết quả là thanh ghi R1 mang giá trị 99.

- MOV (MOVE).

Cú pháp: MOV Rd, Rr
Chức năng: Copy giá trị trong thanh ghi Rr vào thanh ghi Rd.
Giới hạn: áp dụng cho tất cả các thanh ghi trong RF.
Ví dụ: MOV R15, R16 kết quả là R15 có cùng giá trị với R16 (R15=R16=99).

- CLR (CLEAR Register).

Cú pháp: CLR Rd
Chức năng: Copy giá trị trong thanh ghi Rr vào thanh ghi Rd.
Giới hạn: áp dụng cho tất cả các thanh ghi trong RF.
Ví dụ: áp dụng cho tất cả các thanh ghi trong RF.

- SER (SET Register).

Cú pháp: SER Rd
Chức năng: set tất cả các bit trong thanh ghi Rd lên 1, sau lệnh này thanh ghi Rd=0xFF.
Giới hạn: chỉ áp dụng cho các thanh ghi từ R16 đến R31.
Ví dụ: SER R16 kết quả là R16 = 0xFF.

- CBR (CLEAR Bit in Register).

Cú pháp: CBR Rd, K
Chức năng: xóa các bit trong thanh ghi Rd với “mặt nạ”  K, nếu Bit nào trong K là 1 thì Bit tương ứng trong Rd sẽ bị xóa.
Giới hạn: chỉ áp dụng cho các thanh ghi từ R16 đến R31.
Ví dụ: CBR R16, 0xF0  kết quả là 4 bit cao nhất của  R16 bị xóa vì K=11110000 (B).

- SBR (SET Bit in Register).

Cú pháp: SBR Rd, K
Chức năng: set các bit trong thanh ghi Rd với “mặt nạ”  K, nếu Bit nào trong K là 1 thì Bit tương ứng trong Rd sẽ được set lên 1.
Giới hạn: chỉ áp dụng cho các thanh ghi từ R16 đến R31.
Ví dụ: SBR R16, 0xF0  kết quả là 4 bit cao nhất của  R16 được set lên 1 vì K=11110000 (B).

- BLD (Bit LoaD from T Flag).

Cú pháp: BLD Rd,b
Chức năng: Load giá trị trong cờ T của thanh ghi SREG vào bit thứ b trong thanh ghi Rd. Đây cũng chính là chức năng chính của cờ T.
Giới hạn: áp dụng cho tất cả các thanh ghi trong RF.
Ví dụ:
SET ; set bit T lên 1
BLD R16, 4
Kết quả là bit 4 của thanh ghi R16 được set lên 1 vì giá trị của bit T là 1.

- BST (Bit Storage from T Flag).

Cú pháp: BST Rd,b
Chức năng: Copy bit thứ b trong thanh ghi Rd vào trong cờ T của thanh ghi SREG. Đây cũng chính là chức năng chính của cờ T.
Giới hạn: áp dụng cho tất cả các thanh ghi trong RF.
Ví dụ: BST R16, 4 kết quả là cờ T chứa giá trị của bit 4 của thanh ghi R16.

- CPI (COMPARE with Immediate).

Cú pháp: CPI Rd, K
Chức năng: so sánh thanh ghi Rd với hằng số K, lệnh này làm thay đổi nhiều bit trong thanh ghi SREG trong đó sự thay đổi của cờ Zero là quan trọng nhất, nếu Rd = K cờ Z=1, ngược lại Z=0, sử dụng đặc điểm thay đổi của cờ Z kết hợp với lệnh BRNE hoặc BREQ chúng ta có thể tạo thành một lệnh rẽ nhánh.
Giới hạn: chỉ áp dụng cho các thanh ghi từ R16 đến R31.
Ví dụ:
LDI R16, 10
CPI R16, 10
Kết quả là cờ Z được set thành 1 vì lúc này R16 =10.

- ANDI (AND with Immediate).

Cú pháp: ANDI Rd, K
Chức năng: thực hiện phép Logic AND giữa thanh ghi Rd với hằng số K và kết quả đặt lại trong Rd.
Giới hạn: chỉ áp dụng cho các thanh ghi từ R16 đến R31.
Ví dụ: ANDI R17, 0x00 kết quả là R17 có 0x00.

- AND (Logical AND).

Cú pháp: AND Rd, Rr
Chức năng: thực hiện phép Logic AND giữa 2 thanh ghi Rd và Rr , kết quả đặt lại trong Rd.
Giới hạn: áp dụng cho tất cả các thanh ghi trong RF.
Ví dụ:
LDI R1, 0xFF ;(11111111)
LDI R17, 0xAA; (10101010)
AND R1, R17
Kết quả là R1=0xAA vì 11111111 & 10101010 =10101010.

- ORI (Logical OR with Immediate).

Cú pháp: ORI Rd, K
Chức năng: thực hiện phép Logic OR giữa thanh ghi Rd với hằng số K và kết quả đặt lại trong Rd.
Giới hạn: chỉ áp dụng cho các thanh ghi từ R16 đến R31.
Ví dụ: ORI R17, 0xFF kết quả là R17 có 0xFF.

- OR (Logical OR).

Cú pháp: OR Rd, Rr
Chức năng: thực hiện phép Logic OR giữa 2 thanh ghi Rd và Rr , kết quả đặt lại trong Rd.
Giới hạn: áp dụng cho tất cả các thanh ghi trong RF.
Ví dụ:
LDI R1, 0xFF ;(11111111)
LDI R17, 0xAA; (10101010)
OR R1, R17
Kết quả là R1=0xFF vì 11111111 or 10101010 =11111111.

- LSL (Logical Shift Left).

Cú pháp: LSL Rd
Chức năng: dịch tất thanh ghi Rd sang trái 1 vị trí, Bit 7 (bit lớn nhất) của Rd sẽ được chứa trong cờ nhớ C, bit 0 của Rd bị xóa thành 0. Thực chất LSL tương đương với phép nhân thanh ghi Rd với 2. Bạn xem hình minh họa bên dưới.

Giới hạn: áp dụng cho tất cả các thanh ghi trong RF.
Ví dụ:
LDI R1, 0B11000011 ; (dạng nhị phân của 195)
LSL R1
Kết quả là R1=10000110 và cờ C =1 vì thanh ghi R1 đã được dịch sang trái 1 vị trí, trước khi dịch bit 7 của R1 là 1 nên sau khi dịch bit này được chứa trong C, cho nên C=1.

- LSR (Logical Shift Right).

Cú pháp: LSR Rd
Chức năng: dịch tất thanh ghi Rd sang phải 1 vị trí, Bit 0 (bit nhỏ nhất) của Rd sẽ được chứa trong cờ nhớ C, bit 7 của Rd bị xóa thành 0. Thực chất LSR tương đương với phép chia thanh ghi Rd cho 2. Bạn xem hình minh họa bên dưới.

Giới hạn: áp dụng cho tất cả các thanh ghi trong RF.
Ví dụ:
LDI R1, 0B11000110 ; (dạng nhị phân của 195)
LSR R1
Kết quả là R1=01100001 và cờ C =1 vì thanh ghi R1 đã được dịch sang phải 1 vị trí, trước khi dịch bit 0 của R1 là 1 nên sau khi dịch bit này được chứa trong C, cho nên C=1.

- ADD (ADD without Carry).

Cú pháp: ADD Rd, Rr
Chức năng: thực hiện phép cộng 2 thanh ghi Rd và Rr , kết quả đặt lại trong Rd. Cờ nhớ C không được sử dụng.
Giới hạn: áp dụng cho tất cả các thanh ghi trong RF.
Ví dụ:
LDI R16, 30
LDI R17, 25
ADD R16, R17
Kết quả là R16=55.

- INC (INCrement).

Cú pháp: INC Rd
Chức năng: tăng thanh ghi Rd 1 đơn vị và kết quả đặt lại trong Rd. Lệnh này đặc biệt thích hợp cho các ứng dụng lặp, kết hợp với BREQ hay BRNE có thể tạo thành 1 vòng lặp FOR.
Giới hạn: áp dụng cho tất cả các thanh ghi trong RF.
Ví dụ: INC R17 kết quả là R17 được tăng thêm 1 đơn vị.

- SUB (SUBtract without Carry).

Cú pháp:  SUB Rd, Rr
Chức năng: thực hiện phép trừ 2 thanh ghi Rd - Rr , kết quả đặt lại trong Rd. Cờ nhớ C không được sử dụng.
Giới hạn: áp dụng cho tất cả các thanh ghi trong RF.
Ví dụ:
LDI R16, 30
LDI R17, 25
SUB R16, R17
Kết quả là R16=5.

- SUBI (SUBtract Immediate).

Cú pháp:  SUBI Rd, K
Chức năng: thực hiện phép trừ  thanh ghi Rd với hằng số K, kết quả đặt lại trong Rd.
Giới hạn: chỉ áp dụng cho các thanh ghi từ R16 đến R31.
Ví dụ:
LDI R16, 30
SUBI R16, 20
Kết quả là R16=10.

- DEC (DECrement).

Cú pháp: DEC Rd
Chức năng: giảm thanh ghi Rd 1 đơn vị và kết quả đặt lại trong Rd. Lệnh này đặc biệt thích hợp cho các ứng dụng lặp, kết hợp với BREQ hay BRNE có thể tạo thành 1 vòng lặp FOR.
Giới hạn: áp dụng cho tất cả các thanh ghi trong RF.
Ví dụ: DEC R17 kết quả là R17 được giảm đi 1 đơn vị.


- MUL (MULtiply unsigned).

Cú pháp: MUL Rd, Rr
Chức năng: thực hiện phép nhân không dấu 2 thanh ghi 8 bit Rd, Rr, kết quả là 1 số 16 bit đặt trong 2 thanh ghi R1:R0. Chú ý nếu Rd và Rr là các thanh ghi R1 và R0 thì kết quả sau khi tính được sẽ được viết đè lên. Xem hình minh họa instruction MUL bên dưới.



Giới hạn: áp dụng cho tất cả các thanh ghi trong RF.
Ví dụ:
LDI R16, 30
LDI R17, 25
MUL R16, R17
Kết quả là R1=0x2, R0=0xEE, vì 30x25=750=0x02EE.

II. Instruction cho các thanh ghi I/O.

Bốn instruction sau đây được thiết kế riêng để truy cập vùng nhớ I/O, các instruction này sử dụng địa chỉ I/O của các thanh ghi trong vùng nhớ này. Vì là thiết kế riêng cho vùng nhớ I/O, bạn không thể sử dụng các thanh ghi này để truy cập RF hay SRAM. Trong các cú pháp của instruction này, khái niệm địa chỉ A là địa chỉ I/O, 0 ≤ A ≤ 63, nếu trong ví dụ A=0x00 thì đó là thanh ghi đầu tiên của vùng I/O, không phải là thanh ghi R0.

- OUT (OUTPUT Data).

Cú pháp: OUT A, Rr
Chức năng:  xuất giá trị từ thanh ghi Rr ra thanh ghi có địa chỉ A trong vùng nhớ I/O. đây là cách phổ biến nhất để xuất giá trị ra vùng I/O.
Giới hạn: Rr là thanh ghi RF bất kỳ, A bị giới hạn từ 0 đến 63.
Ví dụ:
LDI R16, 0xFF
OUT 0x11, R16
Kết quả là thanh ghi có địa chỉ 0x11 trong vùng I/O, tức thanh ghi DDRD, có giá trị bằng 0xFF.

- IN (INPUT Data).

Cú pháp: IN Rr, A
Chức năng:  Load giá trị từ thanh ghi có địa chỉ A trong vùng nhớ I/O vào thanh ghi Rr. Đây là cách phổ biến nhất để nhận giá trị từ vùng I/O.
Giới hạn: Rr là thanh ghi RF bất kỳ, A bị giới hạn từ 0 đến 63.
Ví dụ:
IN R16, 0x10
Kết quả là thanh ghi R16 nhận được giá trị của thanh ghi có địa chỉ 0x11 trong vùng I/O, tức thanh ghi PIND, đây chính là ví dụ đọc giá trị các chân của PORTD vào R16.

- SBI (Set Bit in I/O Register).

Cú pháp: SBI A, b
Chức năng:  Set bit thứ b trong thanh ghi có địa chỉ A trong vùng nhớ I/O. Tuy nhiên lệnh này không có tác dụng trên toàn bộ vùng I/O mà chỉ có tác đối với 32 thanh ghi đầu (địa chỉ từ 0 đến 31).
Giới hạn: b là số thứ các bit trong thanh ghi, 0≤b≤7; A bị giới hạn từ 0 đến 31.
Ví dụ:
SBI 0x12, 2
Kết quả là bit 2 của thanh ghi có địa chỉ 0x12 trong vùng I/O, tức thanh ghi PORTD, được set lên 1. Đây chính là ví dụ set chân PD2 của PORTD.

- CBI (Clear Bit in I/O Register).

Cú pháp: CBI A, b
Chức năng:  xóa bit thứ b trong thanh ghi có địa chỉ A trong vùng nhớ I/O. Tuy nhiên lệnh này không có tác dụng trên toàn bộ vùng I/O mà chỉ có tác đối với 32 thanh ghi đầu (địa chỉ từ 0 đến 31).
Giới hạn: b là số thứ các bit trong thanh ghi, 0≤b≤7; A bị giới hạn từ 0 đến 31.
Ví dụ:
CBI 0x12, 2
Kết quả là bit 2 của thanh ghi có địa chỉ 0x12 trong vùng I/O, tức thanh ghi PORTD, bị xóa thành 0. Đây chính là ví dụ xóa chân PB2 của PORTD.

III. Các con trỏ X, Y, Z và cách truy cập toàn bộ không gian bộ nhớ.

     Trong Register File của AVR, các thanh ghi từ R26 đến R31ngoài chứa năng thanh ghi thông thường còn có chức năng là con trỏ (Pointer) trong việc truy cập bộ nhớ (cả bộ nhớ data và bộ nhớ Program). Nếu được sử dụng như các Pointer, các thanh ghi trên được biết đến với tên gọi X, Y, Z. Định nghĩa như sau: X=R27:R26, Y=R29:R28, Z=R31:R30. Chúng là 3 thanh ghi 16 bit được định nghĩa trước cho tất cả các AVR. Ngoài ra trong các file định nghĩa cho chip chúng ta có thêm 6 định nghĩa khác là XL, XH, YL, YH, ZL, ZH cũng chính là tên gọi của R26-> R31. Phần này chúng ta khảo sát một số instruction dùng truy cập toàn bộ khồi nhớ của AVR bằng cách sử dụng địa chỉ trực tiếp và bằng cách sử dụng Pointer.

- LDS (LoaD direct from data Space).

Cú pháp: LDS Rd, k
Chức năng:  load giá trị 1 byte từ thanh ghi có địa chỉ k trong SRAM vào thanh ghi Rd, k là dạng địa chỉ tuyệt đối có giới hạn từ 0 đến 65535(2^16-1).
Giới hạn: Rd là thanh ghi bất kỳ trong RF nhưng giá trị lớn nhất của k là 65535, vì thế với lệnh này ta không thể truy cập vượt quá khoảng không gian 64KB. Nếu muốn truy cập vùng không gian lớn hơn 64KB chúng ta cần một số hỗ trợ, tuy nhiên ở đây tôi giả sử bộ nhớ của chip (thường là bộ nhớ data) không vượt quá 64KB (thực tế chưa có chip AVR nào có SRAM hay EEPROM vượt quá 64KB).
Ví dụ:
LDS R2, 0x0060
Kết quả là thanh ghi R2 chứa giá trị của thanh ghi có địa chỉ 0x0060, đây là thanh ghi đầu tiên trong khoảng SRAM (sau RF và vùng I/O) của AVR.

- STS (STorage  direc to data Space).

Cú pháp: STS k, Rr
Chức năng:  instruction này hoàn toàn giống LDS nhưng dùng để xuất dữ liệu từ thanh ghi Rr ra RAM, ngươi đọc có thể tham khảo phần giải thích cho LDS.
Sử dụng địa chỉ trực tiếp thì câu lệnh sẽ đơn giản nhưng rất khó nhớ phần địa chỉ, thông thường SRAM là vùng chúng ta hay sử dụng để chứa biến tạm thời, trong các ngôn ngữ cấp cao ta chỉ cần nhớ tên biến nhưng với ASM chúng ta phải nhớ địa chỉ của chúng. Một cách tốt để tránh việc này là dùng chỉ thị (DIRECTIVE, bạn xem lại bài 1) . EQU để gán tên biến cho 1 địa chỉ, ví dụ  .EQU  bientam = 0x0060 và sau đó sử dụng bientam thay cho 0x0060.

Một cách khác được dùng để truy cập bộ nhớ mà không dùng địa chỉ tuyệt đối là sử dụng sử dụng con trỏ. Có 2 instruction hỗ trợ con trỏ là LD(LoaD indirec from data Space),  và ST (STorage indirec to data Space), LD đọc dữ liệu từ SRAM vào thanh ghi còn ST lưu dữ liệu từ thanh ghi vào SRAM. Cả 3 con trỏ X, Y và Z đều có thể được dùng nhưng có một số điểm lưu ý: cả 3 đều dùng được trong trường hợp truy xuất thông thường nhưng với cách truy cập có offset, con trỏ X không sử dụng được. Để truy xuất bộ nhớ chương trình bằng con trỏ thì Z là giải pháp duy nhất…Dưới đây là 1 số cách sử dụng LD, ST kết hợp với con trỏ, chúng ta xét thông qua các ví dụ.

Ví dụ 1:

CLR R27 ; xóa R27, tức xóa byte cao của pointer X
LDI R26, 0x60 ; load giá trị 0x60 vào R26, tức byte thấp của pointer X
; sau 2 dòng trên, giá pointer X là 0x0060, sẵn sàng để trỏ đến vị trí đầu tiên trong SRAM.

LD R1, X+ ; Load giá trị ở ố nhớ 0x0060 vào R1 (vì X trỏ đến 0x0060), sao đó tăng giá trị ;X lên 1, như thế sau lệnh này X=0x0061
LD R2, X+ ; Load giá trị ở ố nhớ 0x0061 vào R2, sao đó tăng giá trị ;X lên 1, như thế sau lệnh này X=0x0062
LD R3, X ; Load giá trị ở ô nhớ 0x0062 vào R3 và không thay đổi X
LD R4, -X ; Giảm giá trị của X trước (X=0x0061), sau đó load giá trị ở ô nhớ 0x0061 vào R4

Từ ví dụ này chúng ta thấy có 3 cách cơ bản để load dữ liệu từ SRAM bằng con trỏ, cách Load trực tiếp trong trường hợp  LD R3, X, cách load post-increment (hoặc post-decrement) như trong trường hợp LD R1, X+ và cách load pre-decrement (hoặc pre-increment) trong trường hợp LD R4, -X.

Chúng ta có thể viết lại ví dụ trên nhưng sử dụng con trỏ Y hoặc Z thay cho X. Ví dụ viết cho instruction ST cũng hoàn toàn tương tự.

Tuy nhiên cách truy cập theo cách pre hay post đều làm thay đổi giá trị của con trỏ, điều này có 1 bất lợi là nếu chúng ta muốn quay lại vị trí ô nhớ nào đó, chúng ta phải tiếp tục thay đổi con trỏ. Để tránh việc làm này, 1 cách truy cập khác được hỗ trợ là truy cập “Offset”. Xét ví dụ sau:

LD R1, Y+1

Đây chính là cách truy cập Offset dùng con trỏ Y, cách viết trên là tương đương với cách viết

LD R1, Y+

Nhưng điểm khác biệt ở đây là cách viết Offset không làm thay đổi giá trị của con trỏ Y. Sử dụng Offset có ưu điểm như sử dụng mảng (array) trong các ngôn ngữ lập trình cấp cao. Cần chú ý là giá trị offset không vượt quá 63 và phương pháp này chỉ dùng cho 2 thanh ghi Y và Z.

IV. Rẽ nhánh và vòng lặp.

Không giống như các ngôn ngữ cấp cao, khi lập trình bằng ASM bạn không được hỗ trợ các cấu trúc điều khiển như If, For, While…người lập trình ASM phải tự xây dựng cho mình các cấu trúc này từ những instruction cơ bản. Nếu bạn có trong tay tài liệu tra cứu instruction cho AVR bạn sẽ thấy có rất nhiều instruction có dạng BRxx, với BR là viết tắt của từ Branch (rẽ nhánh). Đây là các instruction cơ bản giúp bạn xây dựng các cấu trúc điều khiển tương đương If, For, While…cho riêng mình.

Trước hết ta sẽ khảo sát instruction BRNE bằng cách xem lại ví dụ trong bài "Làm quen AVR", đây là đoạn chương trình con DELAY:

DELAY:
LDI R20, 0xFF
DELAY0:
LDI R21, 0xFF
DELAY1:
DEC R21
BRNE DELAY1
DEC R20
BRNE DELAY0
RET

Bạn hãy chú ý 4 dòng lệnh nằm giữa đoạn chương trình trên (bắt đầu từ dòng 4), dòng đầu tiên thì bạn đã biết - load giá trị 255 vào thanh ghi R21, sau đó tôi đặt 1 label DELAY1- xem như là 1 cột mốc, dòng 3, instruction DEC bạn mới được học hôm nay - giảm giá trị thanh ghi R21 đi 1 đơn vị, và cuối cùng BRNE DELAY1, BRNE là viết tắt của BRanch if Not Equal – rẽ nhánh nếu không bằng, thực ra bản chất của lệnh này là rẽ nhánh nếu cờ Zero không bằng 1. Như thế câu lệnh BRNE DELAY1 của chúng ta được AVR thực hiện như sau: kiểm tra cờ Z, nếu Z=1 tiếp tục thực hiện dòng tiếp theo sau mà không quan tâm đến nhãn DELAY1, nhưng nếu Z=0 thì nhảy đến nhãn DELAY1. Bạn thấy rằng ban đầu R21 =255, sau khi giảm 1 bởi DEC, thanh ghi R21=254≠0, cờ Z =0, rẽ nhánh xảy ra, bộ đếm chương trình nhảy về nhãn DELAY1. Quá trình này lặp lại khoảng 255 lần trước khi R21 =0 dẫn đến Z=1.

Bao bên ngoài vòng lặp của nhãn DELAY1 là vòng lặp của nhãn DELAY0, cách hiểu hoàn toàn tương tự nhưng trước khi lệnh DEC R20 được thực thi thì phải chờ cho vòng lặp DELAY1 kêt thúc. Bản thân DELAY0 cũng là 1 vòng lặp 255 lần. kết quả cuối cùng là ta thu được 1 vòng lặp khoảng 255x255 lần mà không làm gì cả, đó chính là ý nghĩa và cách hoạt động của đoạn chương trình con DELAY.

Bên cạnh BRNE chúng ta có 1 số instruction phục vụ rẽ nhánh khác như:

- BREQ (BRanch if EQual).

Cú pháp: BREQ LABEL
Chức năng:  Nhảy đến nhãn LABEL nếu cờ Z =1. Cờ Z chịu tác động của rất nhiều instruction như CP, CPI, SUB, SUBI…vì thế BREQ thường được sử dụng sau các instruction này.
Ví dụ:
LDI R16, 0xFF
LDI R17, 0xFF
CP R16, R17 ; so sanh 2 thanh ghi R16, R17
BREQ RENHANH
…..
RENHANH:
; thực hiện những việc khi rẽ nhánh.

Kết quả là việc rẽ nhánh xảy ra vì khi so sánh bằng CP,  R17=R16 nên cờ Z tự động được set bằng 1, lệnh BREQ được thực thi và nhảy đến nhãn RENHANH. Ví dụ này tương đương cấu trúc if (R16=R17) {thực hiện những việc khi rẽ nhánh}.

- BRLO (BRanch if LOwer).

Cú pháp: BRLO LABEL
Chức năng:  bản chất của câu lệnh là nhảy đến nhãn LABEL nếu cờ C =1. Tuy nhiên, thông thường lệnh này sử dụng theo sau các instruction như CP, CPI, SUB, SUBI…khi đó việc rẽ nhánh sẽ xảy ra nếu thanh ghi Rd
Ví dụ:
EOR  R16, R16 ;XOR R16 với chính nó, tương đương CLR R16
VONG LAP:
INC R16 ;tăng R16  thêm 1 đơn vị
CPI R16, $10 ;so sánh R16 với số hexadecimal $10
BRLO VONGLAP ;nhảy về  VONGLAP nếu R16 <$10
NOP  ;câu lệnh này sẽ được thực thi nếu điều kiện rẽ nhánh ở trên không thỏa,
; NOP là 1 instruction, chức năng là không làm gì cả.
Kết quả là phần lệnh bên trong VONGLAP sẽ được thưc hiện khoảng 16 lần ($10=16) trước khi thực hiện lệnh NOP.

- BRSH (BRanch if Same or Higher).

Cú pháp: BRSH LABEL
Chức năng:  bản chất của câu lệnh là nhảy đến nhãn LABEL nếu cờ C =0. Tuy nhiên, thông thường lệnh này sử dụng theo sau các instruction như CP, CPI, SUB, SUBI…khi đó việc rẽ nhánh sẽ xảy ra nếu thanh ghi Rd ≥Rr.
Ví dụ:
SUBI  R16, 4 ;trừ R16 đi 4 đơn vị
BRSH RENHANH ; nhảy đến RENHANH nếu R16 ≥ 4
….
RENHANH:
NOP

Còn rất nhiều instruction rẽ nhánh bạn có thể sử dụng để tạo cấu trúc điều khiển, chú ý là các instruction này đều hoạt động dựa trên trạng thái của 1 cờ nào đó, do đó bạn cần lựa chọn 1 lệnh phù hợp để thực thi trước các instruction rẽ nhánh này, để làm được như vậy bạn cần xem kỹ tài liệu hướng dẫn INSTRUCITON cho AVR.

Nguồn: Echipkool - Điện Tử | Tin Học - Chia sẻ kiến thức - Kết nối đam mê điện tử

AVR, lap trinh avr, tai lieu dien tu

Đăng nhận xét

Author Name

{picture https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjN0PUWA2genMqX3Sm26mBTX_30OJgDenoIi4K6BR-E1vl3nI7LALp0X759QZgzqrMcGBB7jEbdZnubJbp4n2ZZ22KT196CWCg9DLs3MfEivocdmkjZEPEn-A42hyphenhyphen9dmsca0VIDQr_LjqM/s512-Ic42/pham-van-ngoc-anh.jpg}

Tôi là Ngọc Anh. Tôi đến từ Nghệ An. Tôi tốt nghiệp một trường đại học tại Sài Gòn. Hiện tôi đang phát triển công ty riêng. Liên lạc với tôi qua:

{facebook https://www.facebook.com/phamvanngocanh}
{twitter https://twitter.com/nghiphong1993}
{google https://plus.google.com/+dientuchiase/posts}
{youtube https://www.youtube.com/channel/UCeJKhA_goBNFmDw6RKNtmYQ}

Biểu mẫu liên hệ

Tên

Email *

Thông báo *

Được tạo bởi Blogger.