LỜI NÓI ĐẦU
 
Ngày này, việc ứng dụng máy tính vào các kỹ thuật đo lường và điều khiển không còn mới vì khi các thiết bị, hệ thống đo lường và điều khiển được ghép nối với máy tính sẽ có thời gian thu thập và xử lý dữ liệu ngắn trong khi mức độ chính xác vẫn được đảm bảo, nhưng điều đáng quan tâm hơn cả là khả năng tự động hoá trong việc thu thập và xử lý dữ liệu. Chính vì điều này làm cho máy tính được ứng dụng trong hầu hết vào các lĩnh vực trong cuộc sống hàng ngày đặc biệt là trong lĩnh vực công nghiệp. 
Một bước tiến quan trọng trong kỹ thuật vi xử lý là sự ra đời của các bộ vi xử lý kỹ thuật số. Đây là một vi mạch điện tử có mật độ tích hợp cao bao gồm rất nhiều các mạch số có khả năng nhận, xử lý và xuất dữ liệu. Đặc biệt là quá trình xử lý dữ liệu được thực hiện theo một chương trình là một tập hợp các lệnh từ bên ngoài mà người sử dụng có thể thay đổi dễ dàng tùy thuộc vào từng ứng dụng. Do đó một bộ vi xử lý có thể thực hiện được rất nhiều các yêu cầu điều khiển khác nhau tuỳ thuộc vào nhu cầu sử dụng.
Sự ra đời của kỹ thuật vi xử lý là sự kết hợp giữa kỹ thuật phần cứng và phần mềm đã làm cho hoạt động của các mạch điện tử trở nên mềm dẻo hơn với những phần mềm rất linh hoạt mà người sử dụng có thể sửa chữa, thay đổi hoặc bổ sung làm cho ứng dụng ngày càng trở nên hoàn thiện mà không cần phải thiết kế lại toàn bộ ứng dụng.
Trong đồ án này, em sử dụng vi mạch điều khiển AT90S8535 của hãng Atmel để thiết kế một mạch đo nhiệt độ đơn giản. Đây là một bộ vi xử lý 8 bit năng lượng thấp (theo kiểu chíp CMOS) trên cơ sở cấu trúc RICS của hãng Atmel, tốc độ xử lý dữ liệu của IC AT90S8535 rất cao (xấp xỉ 8 MISP tại tần số 8MHz) cho phép hệ thống có thể được thiết kế tối ưu làm tăng tốc độ xử lý. Do đó, nó cung cấp khả năng linh hoạt rất cao trong các ứng dụng nhúng. Vì vậy, việc tìm hiểu cấu trúc và đặc tính của vi mạch điều khiển AT90S8535 có thể giúp chúng ta sử dụng vi mạch điều khiển này cho các ứng dụng cần thiết. 
Em xin chân thành cảm ơn thầy cô đã tận tình hướng dẫn để em hoàn thành đồ án này. Tuy nhiên, do trình độ còn nhiều hạn chế nên đồ án không thể tránh khỏi những thiếu sót, vì vậy em rất mong được sự chỉ bảo của các thầy cô cũng như của những người đi trước trong lĩnh vực này để đồ án của em hoàn thiện hơn qua đó em có thể xây dựng được những ứng dụng trong thực tế.
Đề tài: Thiết kế một mạch đo nhiệt độ đơn giản
                
              
                                            
                                
            
 
            
                 253 trang
253 trang | 
Chia sẻ: lvcdongnoi | Lượt xem: 2777 | Lượt tải: 0 
              
            Bạn đang xem trước 20 trang tài liệu Thiết kế một mạch đo nhiệt độ đơn giản, để xem tài liệu hoàn chỉnh bạn click vào nút DOWNLOAD ở trên
 10, kết quả này sẽ được gửi sang PC đồng thời dựng cờ báo có kết quả chuyển đổi A/D. Thao tác tiếp theo được thực hiện trong chương trình con DISPLAY_TEMPR_TO_LCD được gọi từ chương trình điều khiển khi cờ trên được nhận ra.
Ngoài các ngắt kể trên, chương trình còn có một số chương trình con có các chức năng khác nhau trợ giúp cho chương trình điều khiển hoạt động, bao gồm :
Các chương trình con điều khiển LCD controller : LCD_BUSY (kiểm tra LCD controller đang thực hiện thao tác trong?), LCD_INSTR (ghi lệnh tới LCD controller) và LCD _DATA (ghi dữ liệu tới LCD controller).
Các chương trình con tính toán và hiển thị kết quả thu được từ ADC : MULL_RESULT_CONVER, DIVIDE_TO_GET_TEMPR (thực hiện nhân chia 16 bit để thu được kết quả ADC ở số hệ 10), DISPLAY_TEMPR_TO_LCD (hiển thị kết quả của ADC ra giao diện LCD dưới dạng 0C hay 0K tuỳ thuộc vào điều kiện được xác định trong chương trình).
Các chương trình điều khiển của các phím chức năng : SHIFT_LEFT, SHIFT_RIGHT, SEND_TxBUFF_TO_PC, CLEAR_Tx_OR_Rx, BACK_SPACE, SELECT_TxRx.
Các chương trình điều khiển đối với phím thường : GET_ASCII_CODE (xác định mã ASCII của phím được ấn), FIND_ASCII_CODE (tìm mã ASCII tươngứng với số lần ấn của phím), DISPLAY_KEY (hiển thị phím được ấn và lưu vào bộ đếm TxBuff để chuyền sang PC).
Các chương trình điều khiển hiển thị dữ liệu ra giao diện LCD : SHOW_PREFACEA, SHOW_PREFACEB (hiển thị lời giới thiệu), DISPLAY_INTERFACE (hiển thị giao diện làm việc của LCD), SHOW_STRING (hiển thị một chuỗi ký tự ra giao diện LCD) vv...
4.2. Lưu đồ thuật toán của các chức năng chính.
	4.2.1. Chức năng giao tiếp với LCD controller.
	Để mC có thể giao tiếp được với LCD controller, ta cần thực hiện khởi tạo LCD controller ngay sau khi nguồn được bật. Do mục đích của đồ án, ta sử dụng cơ chế khởi tạo LCD controller ở chế độ giao tiếp 4 bit bus. 3 chương trình con được sử dụng để giao tiếp với LCD controller là LCD_BUSY, LCD_INSTR và LCD_DATA. Lệnh được đặt trong thanh ghi Instr và dữ liệu trong thanh ghi Data.
Hình 4.3 : Lưu đồ chương trình kiểm tra LCD busy
Bắt đầu
Cho phép đọc thanh ghi lệnh của LCD controller (RS = 0, RW = 1)
Đọc 4 bit MSB 
của thanh ghi lệnh
Đọc 4 bit LSB 
của thanh ghi lệnh
Kết thúc
BF = 1?
N
Y
Hình 4.4 : Lưu đồ chương trình ghi lệnh và
 dữ liệu tới LCD controller
Bắt đầu
Cho phép ghi thanh ghi lệnh của LCD controller (RS = 0, RW = 0)
Ghi 4 bit MSB của mã 
lệnh tới thanh ghi lệnh
Kết thúc
Lấy 4 bit thấp 
của mã lệnh 
Ghi 4 bit LSB của mã 
lệnh tới thanh ghi lệnh
Bắt đầu
Cho phép ghi thanh ghi dữ liệu của LCD controller (RS = 1, RW = 0)
Ghi 4 bit MSB của byte 
dữ liệu tới thanh dữ liệu
Kết thúc
Lấy 4 bit thấp 
của byte dữ liệu 
Ghi 4 bit LSB của byte 
dữ liệu tới thanh dữ liệu
	4.2.2. Chức năng điều khiển và hiển thị kết quả ADC.
	Khi bộ ADC thực hiện xong một chu kỳ chuyển đổi, kết quả chuyển đổi sẽ được lưu vào thanh ghi ADCL và ADCH, tiếp sau đó cờ ngắt kết thúc chuyển đổi A/D được dựng và chương trình con phục vụ ngắt tương ứng là END_CONVERT được gọi. 
Hình 4.6 : Lưu đồ chương trình con phục vụ ngắt END_CONVERT
Bắt đầu
Lưu lại trạng thái MCU
Lấy kết quả chuyển đổi A/D
Lưu lại các thanh ghi cần sử dụng 
Gửi ký hiệu truyền dữ
liệu ( # ) sang PC
Lấy phần nguyên của kết quả ADC đặt vào ResultADCH
Thực hiện chương trình MULL_RESULT_CONVER với số nhân = 100
Thực hiện chuơng trinh DIVIDE_TO_GET_TEMPR với số chia = 255
Gửi phần nguyên của 
kết quả ADC sang PC
Lấy phần thập phân của kết quả ADC đặt vào ResultADCL
Thực hiện chương trình MULL_RESULT_CONVER với số nhân = 10
Thực hiện chuơng trinh DIVIDE_TO_GET_TEMPR với số chia = 255
Gửi phần thập phân
 của kết quả ADC sang PC
Dựng cờ báo cần hiển thị
kết quả ADC ra giao diện LCD
Lấy lại giá trị các thanh ghi sử dụng
Lấy lại trạng thái MCU
Kết thúc
Trong ngắt END_CONVERT có sử dụng hai module MULL_RESULT_CONVER và DIVIDE_TO_GET_TEMPR được sử dụng để chuyển kết quả ADC sang số thập phân. Trước khi thực hiện các module này cần phải xác định số nhân hoặc số chia trong thanh ghi Data. Chương trình MULL_RESULT_CONVER sẽ thực hiện nhân nội dung hai thanh ghi ResultADCL và Data, kết quả đặt trong thanh ghi ResultADCH và ResultADCL. Chương trình DIVIDE_TO_GET_TEMPR thực hiện chia kết quả từ chương trình MULL_RESULT_CONVER cho nội dung thanh ghi Data, phần nguyên của kết quả đặt trong thanh ghi ResultADCH, phần dư của kết quả đặt trong thanh ghi ResultADCL. 
Hình 4.7 : Lưu đồ chương trình MULL_RESULT_CONVER
Bắt đầu
Xoá cờ carry ( C = 0 )
Khởi tạo các thanh ghi tạm
R11 = 0, R12 = ResultADCL
Giảm số nhân đi một
Data  Data - 1
Kết thúc
Data = 0?
Y
N
ResultADCL  ResultADCL + R12 
ResultADCH  ResultADCH + R11 + C 
Hình 4.8 : Lưu đồ chương trình DIVIDE_TO_GET_TEMPR
Bắt đầu
Xoá cờ carry ( C = 0 )
Khởi tạo các thanh ghi tạm R11  0, R12  0
ResultADCL  ResultADCL - Data 
ResultADCH  ResultADCH - R11 - C
C  0
R12  R12+1
Kết thúc
N
Lấy phần nguyên của kết quả
ResultADCH  R12
ResultADCL < Data?
N
ResultADCH = 0?
Y
Y
	Ngoài hai module trên, để hiển thị kết quả chuyển đổi A/D tới giao diện LCD, cần sử dụng chương trình con DISPLAY_TEMPR_TO_LCD chương trình này được gọi từ chương trình điều khiển khi cờ báo có kết quả ADC cần được hiển thị. Dữ liệu đầu vào của chương trình này là nội dung hai thanh ghi chứa kết quả A/D dưới dạng số hệ 10 sau khi thực hiện ngắt END_CONVERT, trong đó phần nguyên chứa trong thanh ghi ResultADCH và phần thập chứa trong thanh ghi ResultADCL. 
	Hình 4.9 : Lưu đồ chương trình con DISPLAY_TEMPR_TO_LCD
Kết thúc
Bắt đầu
Lấy toạ độ đầu Instr  $CB
Lưu nội dung ResultADCL
ResultADCL  ResultADCH
ResultADCL  0
N
Show_CK = 1?
Y
Đổi giá trị nhiệt độ sang 0K
ResultADCH:ResultADCL  ResultADCH:ResultADCL + 273
Lấy số hàng trăm để hiển thị
Gọi chương trình DIVIDE_TO_GET_TEMPR với Data = $64
Y
ResultADCH = 0?
N
Lấy mã ASCII của số cần hiển thị
Data  ResultADCH
Data  Data + 30
Không hiển thị số hàng trăm
Data  $20
Hiện dữ liệu
Lấy số hàng chục để hiển thị
ResultADCH  0
Gọi chương trình DIVIDE_TO_GET_TEMPR với Data = $0A
Y
ResultADCH = 0?
N
Lấy mã ASCII của số cần hiển thị
Data  ResultADCH
Data  Data + $30
Hiện 0 ở hàng chục
Data  $30 
Hiện dữ liệu
Hiện số hàng đơn vị
Data  ResultADCL
Data  Data + $30
Hiện dữ liệu
Hiện dấu chấm thập phân
Data  $2E
Hiện dữ liệu
Hiện số thập phân
Lấy lại nội dung ResultADCL
Data  ResultADCL
Data  Data + $30
Hiện dữ liệu
4.2.3. Chức năng giao tiếp với KeyPad.
	Chức năng giao tiếp với bàn phím được bắt đầu bằng việc giải mã ma trận bàn phím để xác định phím nào trên bàn phím được ấn. Để mC nhận biết có phím ấn, một yêu ngắt ngoài được xác định bằng mức thấp trên chân INT0 (PD2) được phát sinh và ngắt bàn phím SCAN_CODE được thực hiện. Trước khi bắt thực hiện chương trình con phục vụ ngắt, cần đặt 0 trên các hàng và đặt 1 trên các cột. 
Hình 4.10 : Lưu đồ ngắt SCAN_CODE giải mã ma trận bàn phím
Bắt đầu
Lưu lại trạng thái MCU
Keypress  0
Câm ngắt bàn phím
Đợi 0.2ms cho
 cổng ổn định 
Col1 = 0?
Y
N
Col2 = 0?
Y
N
Col3 = 0?
Y
N
Col4 = 0?
Y
N
KeyPress  0
KeyPress  4
KeyPress  8
KeyPress  12
Đảo 4 bit của cổng B
Đưa 0 ra các cột vào đưa 1 ra các hàng
Đợi 0.2ms cho các cột ổn định
Row1 = 0?
Y
N
KeyPress  KeyPress + 0
Row2 = 0?
Y
N
KeyPress  KeyPress + 1
Row3 = 0?
Y
N
KeyPress  KeyPress + 3
A
B
Kết thúc
Row4 = 0?
Y
N
KeyPress  KeyPress + 4
A
B
KeyPress<10?
N
Y
Dựng cờ báo phím điều khiển
Dựng cờ báo có phím ấn
Cấn ngắt KEY_RATE
Lấy lại trạng thái MCU
Do mỗi một phím thường trên bàn phím được mã hoá nhiều hơn một ký tự, vì vậy để xác định được chính xác ký tự nào được mã hoá của phím bị ấn được lựa chọn một thanh ghi OldKey được sử dụng. Nội dung của thanh ghi này chứa giá trị của phím được ấn và được dùng để so sánh với giá trị của phím được ấn trong thanh ghi KeyPress ở lần tiếp theo. Nếu hai thanh ghi này có giá trị bằng nhau thì tổng số lần ấn phím tăng lên 1 và ký tự tiếp theo được mã hoá bởi phím sẽ được chọn, ngược lại phím được coi là ấn lần đầu tiên. Nội dung thanh ghi OldKey sẽ được ghi nhớ trong một khoảng thời gian 200ms, nếu sau khoảng thời gian này mà phím không được ấn lại nội dung thanh ghi OldKey được xác lập lại trang thái không phím nào được ấn (OldKey = -1). Việc này được thực hiện bởi chương trình phục vụ ngắt KEY_RATE của ngắt tràn TC1.
Hình 4.11 : Lưu đồ ngắt KEY_RATE 
Kết thúc
Lưu trạng thái MCU
Cấn ngắt KEY_RATE
Lấy lại trạng thái MCU
Bắt đầu
OldKey  -1
	Tuỳ thuộc vào phím được ấn là phím điều khiển hay phím thường mà chương trình điều khiển sẽ thực hiện một trong hai chương trình con DISPLAY_KEY ứng với một phím thường và CONTROL_KEY ứng với một phím điều khiển. 
Hình 4.12 : Lưu đồ chương trình DISPLAY_KEY
Kết thúc
Gọi chương trình FIND_ASCII_CODE
Hiện thông báo 
tràn bộ đệm TxBuff
Bắt đầu
LPtrTx = EndTxBuf+1?
Y
N
Tăng con trỏ cuối bộ đệm TxBuff
LPtrTx  LPtrTx + 1 
Hiện 15 ký tự cuối trong bộ đệm
Gọi chương trình SHOW_CHAR_IN_TxBuff
Xác định vị trí hiển thị tiếp theo
Hiện ký tự tương ứng phím ấn
Lưu ký tự vào bộ đệm TxBuff
XL  LPTrTx, X  Data
Giảm con trỏ cuối bộ đệm TxBuff
LPtrTx  LPtrTx - 1
	Chương trình con FIND_ASCII_CODE có chức năng tìm mã ascii tương ứng với ký tự được lựa chọn và lưu kết quả vào thanh ghi Data với số lần phím được ấn lưu trong 4 bit cao của thanh ghi điều khiển CtrlReg.
Hình 4.13 : Lưu đồ chương trình FIND_ASCII_CODE
Bắt đầu
Tăng tổng số lần ấn phím
Xác định vị trí hiển thị và con trỏ LPtrTx
KeyPress = OldKey?
N
Y
A
OldKey  KeyPress
Tổng số lần ấn phím = 0
Số lần ấn phím = 4 ?
N
Y
B
Data  $38
Position  $58
Data  $37
Position  $55
Temp  0
CtrlReg  CtrlReg$0F
Data  $39
Position  $19
A
B
Tổng số lần ấn phím = 0
CtrlReg  CtrlReg$0F 
Lấy tổng số lần ấn phím
Temp  CtrlReg
swap Temp
Temp  Temp$0F
Keypress<5?
N
C
Y
Keypress<3?
N
Y
Keypress= 1?
Y
N
Data  $31
Position  $43
Keypress= 2?
Y
Data  $32
Position  $46
N
Data  $30
Position  $40
Keypress=4?
N
Y
Data  $33
Position  $49
Data  $34
Position  $4C
Lấy mã ASCII của ký tự tương ứng
chương trình GET_ASCII_CODE
Kết thúc
C
Keypress<7?
Y
N
Keypress= 6?
N
Y
Data  $35
Position  $4F
Data  $36
Position  $52
Keypress= 8?
Y
N
Temp= 3?
N
Y
Temp  0
CtrlReg  CtrlReg$0F
Keypress= 9?
Y
N
Temp= 2?
N
Y
Tổng số lần ấn phím = 0
CtrlReg  CtrlReg$0F 
Chương trình con GET_ASCII_CODE có chức năng lấy mã ascii và lưu vào trong thanh ghi Data. Đầu vào của chương trình là thanh ghi Data chứa mã ascii của chữ số và thanh ghi Position chứa mã ascii của ký tự đứng ngay trước ký tự đầu tiên được mã hoá bởi phím. Ví dụ, phím số 1 mã hoá các ký tự 1, D,E và F, khi đó nếu phím số 1 được ấn thì Data chứa giá trị $30 (mã ascii của số 1) còn Position chứa giá trị $43 (mã ascii của ký tự đứng trước chữ D). Tổng số lần ấn phím được đặt trong thanh ghi Temp.
Hình 4.14 : Lưu đồ chương trình GET_ASCII_CODE
Bắt đầu
Position  Position + Temp
Data  Postion
Temp = 0?
Y
N
Kết thúc
	Trước khi hiển thị ký tự của phím được ấn ra màn hình LCD, chương trình DISPLAY_KEY, gọi chương trình con SHOW_CHAR_IN_TxBuff để hiện thị lại 15 ký tự cuối cùng được lưu trong bộ đệm TxBuff, nếu tổng số ký tự đang có trong bộ đệm TxBuff lớn hơn 15 ký tự. 
	Ngoài chương trình DISPLAY_KEY được thực hiện khi một phím thường được ấn. Một chương trình khác là chương CONTROL_KEY sẽ được chương trình điều khiển thực hiện mỗi khi một phím chức năng được ấn. Trên bàn phím có tất cả 6 phím chức năng như trình bầy ở các phần trước. Tuỳ thuộc vào việc giải mã bàn phím các chương trình con tương ứng với phím chức năng bị ấn sẽ được thực hiện.
Hình 4.15 : Lưu đồ chương trình CONTROL_KEY
Kết thúc
Bắt đầu
Gọi chương trình BACK_SPACE
KeyPress <13?
N
Y
Xoá cờ báo phím điều khiển
Y
N
Gọi chương trình SHIFT_LEFT
N
Y
Gọi chương trình SEND_TxBUFF_TO_PC
KeyPress =11?
KeyPress =10?
Gọi chương trình SELECT_TxRx
Y
N
Gọi chương trình SHIFT_RIGHT
N
Y
Gọi chương trình CLEAR_Tx_OR_Rx
KeyPress =14?
KeyPress =15?
4.2.4. Chức năng truyền nhận dữ liệu nối tiếp với PC.
	Khi PC thực hiện truyền dữ liệu cho mC, thì mỗi khi mC hoàn thành việc nhận một byte dữ liệu từ cổng nối tiếp, cờ ngắt kết thúc nhận của bộ UART trên mC AT90S8535 được dựng. Chương trình con phục vụ ngắt tương ứng là Rx_COMPELET được thực hiện. Chương trình này có nhiệm vụ phân biệt dạng dữ liệu nhận được từ PC là mã lệnh hay chuỗi ký tự hiển thị để báo cho chương trình điều khiển thực hiện những tác vụ tương ứng. 
Hình 4.16 : Lưu đồ ngắt Rx_COMPELET
Bắt đầu
Lưu lại trạng thái MCU
Lưu thanh ghi cần sử dụng
Kết thúc
Đọc dữ liệu nhận được
Data  URD
Mã lệnh?
Y
N
Ký tự #?
Y
N
CR?
Y
N
Xác định địa chỉ cần lưu
ký tự vừa nhận trong RxBuff
Ghi ký tự vừa nhận
 vào bộ đệm RxBuff
Xác định con trỏ hiển thị của chuỗi ký tự
Lấy lại giá trị các thanh ghi 
Lấy lại trạng thái MCU
Lấy mã lệnh
Implement  Data
Xoá cờ báo 
nhận mã lệnh
Dựng cờ báo 
nhận mã lệnh
Dựng cờ báo cần hiển thị dữ liệu nhận được
	Khi mC nhận được một lệnh từ PC gửi tới, thanh ghi chứa mã lệnh Implement sẽ chứa giá trị mã hoá của lệnh. Khi mC nhận được một lệnh từ CPU, chương trình con EXCUTER_FROM_PC sẽ được gọi để thực hiện lệnh. Trong đồ án này, chương trình trên PC chỉ có thể truyền hai lệnh đơn giản cho mC thực hiện là hiển thị giá trị nhiệt độ theo 0C hay 0K. 
Hình 4.17 : Lưu đồ chương trình con EXCUTER_FROM_PC
Bắt đầu
Xác lập lại nội dung thanh ghi mã lệnh
Implement  -1
Hiển thị 0C?
Y
N
Kết thúc
Xoá cờ cho phép
 hiển thị theo độ K
Dựng cờ cho phép hiển ký hiệu dạng nhiệt độ hiển thị
Dựng cờ cho phép
 hiển thị theo độ K
	Không chỉ có khả năng nhận dữ liệu từ PC, mà mC AT90S8535 cũng có thể gửi một chuỗi dữ liệu trong bộ đệm TxBuff sang PC tại bất kỳ thời điểm nào mỗi khi phím Send trên bàn phím được ấn.
Hình 4.18 : Lưu đồ chương trình SEND_TxBUFF_TO_PC
Bắt đầu
SelectRx?
Y
N
Kết thúc
TxBuff = 0?
Y
N
Hiện thông báo truyền dữ liệu
Lấy địa chỉ đầu của bộ đệm
XL  LOW(TxBuff)
Truyền dữ liệu sang PC
CHƯƠNG 5 
THIẾT KẾ HỆ THỐNG PHẦN MỀM TRÊN PC
5.1. Mục đích của phần mềm trên PC.
	Để hệ thống có thể giao tiếp được với máy tính, ta cần phải thiết kế một phần mềm trên máy tính để nó có thể giao tiếp được với mC. Điều này có nghĩa là ta phải thiết lập một hệ thống trao đổi dữ liệu giữ máy tính và mC, nhằm mục đích tạo ra một sự kết hợp giữa máy tính và mC để tạo nên một hệ thống hoàn chỉnh cho dù chúng ở cách xa nhau. Mặt khác, so với mC thì PC có nhiều khả năng xử lý dữ liệu với độ phức tạp cao, điều này làm cho hệ thống hoạt động một cách thực sự có hiệu quả. 
	Toàn bộ chương trình phần mềm viết cho PC được thực hiện trên ngôn ngữ Visual C++ 6.0. Phương pháp trao đổi dữ liệu giữa PC và mC được thực hiện theo phương pháp truyền nối tiếp theo chuẩn RS232 như đã trình bầy ở các chương trước. Sơ đồ tổng thể của chương trình viết trên PC như trên hình 5.1. 
Hình 5.1 : Sơ đồ khối chương trình viết trên PC
Chương trình
Truyền thông tin sang mC qua cổng RS232
Nhận dữ liệu từ giao
diện nối tiếp RS232
Xử lý dữ liệu
nhận được
Hiện thông tin nhận được từ mC
Hiện dữ liệu
 nhận được từ mC
Lưu trữ dữ 
liệu nhận được
Sau khi chương trình được khởi động, nó sẽ do tìm port nối tiếp và thiết lập kết nối với mC. Nếu kết nối không được thực hiện, thì thao tác truyền nhận dữ liệu giữa PC và mC sẽ không được thực hiện. Trong trường hợp này, chương trình chỉ thực hiện các thao tác với các thông tin đã được lưu lại trên PC. Khi kết nối thành công chương trình sẽ liên tục nhận dữ liệu được gửi từ mC, khi đó chương trình sẽ thực hiện các xử lý tiếp theo tuỳ thuộc loại dữ liệu nhận được là thông tin hay giá trị nhiệt độ. 
Trong trường hợp chương trình không tự động thực hiện được kết nối, người sử dụng có thể tự thực hiện kết nối khi cần thiết bằng cách gọi chương trình thực hiện kết nối mới thông qua chức năng Configure\Set port to connect của Menu chính trong chương trình.
Hình 5.2 : Giao diện thiếp lập kết nối với mC
5.2. Một số chức năng chính của chương trình
	Sau khi kết nối được thực hiện, kết quả chuyển đổi A/D của mC sẽ được gửi liên tục sang PC. Khi nhận được dữ liệu, chương trình sẽ thực hiện phân tích dữ liệu nhận được. Nếu nhận được ký tự "#" thì hai byte dữ liệu tiếp theo sẽ được nhận dưới dạng giá trị của kết quả chuyển đổi A/D. Chương trình sẽ thực hiện hiển thị giá trị nhiệt độ vừa nhận được lên đồ thị nhiệt độ tức thời. Trong khoảng thời gian 1 phút, giá trị nhiệt độ trung bình sẽ được lưu lại cơ sở dữ liệu để có thể xử lý lại đồng thời giá trị này cũng được hiển thị trên đồ thị nhiệt độ trung bình. 
Hình 5.3 : Giao diện nhận và hiển thị kết quả ADC
	Bất kỳ byte dữ liệu nào nhận được mà trước đó chương trình không nhận được ký tự "#" đều được coi là ký tự hiển thị và sẽ được hiển thị trên cửa sổ truyền nhận thông tin giữa PC và mC. Đồng thời chương trình cũng có thể gửi một chuỗi thông tin sang mC để hiển thị trên giao diện LCD. Thao tác này có thể được thực hiện đồng thời với thao tác truyền dữ liệu của mC do vi mạch UART của mC hoạt động ở chế độ chuyền song công. Chương trình cũng có thể gửi lệnh để mC thực hiện thông qua việc lựa chọn thang nhiệt độ hiển thị là 0C hay 0K trong hộp thoại điều khiển và truyền nhận thông tin của chương trình. 
Hình 5.4 : Giao diện truyền nhận thông tin
	Ngoài các chức năng trên chương trình cũng cho phép xem lại dữ liệu được thu thập từ trước thông qua chức năng File\View data from list của Menu chương trình. Chức năng này không chỉ cho phép xem lại dữ liệu mà nó có thể dựng lại đồ thị diễn biến của nhiệt độ được lưu trong cơ sở dữ liệu theo thời gian giá trị nhiệt độ được cập nhật. 
Hình 5.5 : Giao diện xem lại dữ liệu được lưu trữ
5.3. Nhận xét và đánh giá.
	Nhìn chung, phần mềm trên máy tính và chương trình điều khiển mC chạy thử nghiệp cho kết quả tốt. Hai chương trình này hoạt động một cách đồng bộ trong việc truyền nhận dữ liệu, do đó kết nối thành một hệ thống hoàn chỉnh. Phần mềm trên PC không chỉ biểu diễn được các giá trị nhiệt độ dạng đồ thị theo thời gian mà còn có thể lưu trữ các thông tin cần thiết trong quá trình thu thập dữ liệu và các thông tin lưu trữ này có thể được xem lại khi cần thiết. Kết quả ADC được truyền sang máy tính để máy tính thực hiện các thao tác phức tạp như dựng đồ thị và lưu trữ, điều này giúp cho công việc lập trình trở nên đơn giản và đỡ tốn thời gian cũng như chi phí so với việc thực hiện công việc này trên mC.
	Về cơ bản mạch phần cứng đã được lắp rắp hoàn chỉnh và chạy thử cho kết quả tốt đáp ứng được yêu cầu đề ra của đồ án. Song do điều kiện về thời gian nên không kịp thiết kế mạch in theo kỹ thuật có nên cũng phần nào ảnh hưởng đến chất lượng kỹ thuật cũng như chất lượng về mặt cảm quan của sản phẩm. Ngoài ra, do kinh nghiệm trong việc thiết kế phần cứng còn nhiều hạn chế nên việc ghép nối giữa mC với các modul khác qua các cổng I/O của mC AT90S8535 chưa thực sự tối ưu. 
	Hoạt động trao đổi dữ liệu dữ máy tính và RTU được thực hiện dựa trên phương pháp truyền thông nối tiếp theo chuẩn RS232, do đó tốc độ truyền dữ liệu bị hạn chế. Mặt khác, do dữ liệu được truyền trực tiếp từ mC tới máy tính mà không qua Modem nên khoảng cách giữa máy tính vào RTU cũng bị giới hạn. 
Mặc dù hệ thống cần thiết kế đã hoàn thành, tuy nhiên có thể thấy nó có một số hạn chế trong đó hạn chế lớn nhất là khả ứng dụng trong thực tế của sản phẩm không cao. Nên mặc dù việc thay đổi đại lượng biến đổi ở đầu vào của bộ chuyển đổi A/D trong hệ thống để phù hợp với các ứng dụng thực tế không đòi hỏi nhiều chi phí và thời gian thiết kế lại mạch, nhưng chương trình điều khiển mC và chương trình trên PC cần có những thay đổi thích hợp. 
KẾT LUẬN 
	Trong bản báo có đồ án tốt nghiệp này, em đã nêu ra một số lý thuyết sử dụng để thiết kế và quy trình công việc phải thực hiện trong thực tế. Nói chung công việc đã hoàn thành theo đúng tiến độ đề ra, tuy nhiên do năng lực cũng như kinh nghiệm về lĩnh vực công nghệ phần cứng còn nhiều yếu kém nên đồ án không thể tránh được những thiếu sót. Tuy nhiên, trong thời gian thực hiện đồ án, em cũng đã rút ra được một số kinh nghiệm quý báu, điều này rất cần thiết cho em khi ra làm việc thực tế. 
	Nói chung, hệ thống cần thiết kế đã hoàn thành và chạy thử nghiệp cho kết quả tốt. Do mục đích của đồ án là tìm hiểu nguyên lý hoạt động và thực hiện điều khiển một bộ vi xử lý AT90S8535, đây là một mC còn rất mới của hãng ATMEL nên sản phẩm được thiết kế hầu như không được ứng dụng trong thực tế mà chỉ mang tính thử nghiệm. Tuy nhiên, thông qua quá trình tìm hiệu và sử mC AT90S8535 để thiết kế, có thể giúp em hiểu phần nào về công nghệ phần cứng ứng dụng trong các lĩnh vực khác nhau trong cuộc sống. Sau khi hoàn thành đồ án, em sẽ tìm hiểu thêm các kiến thức về kỹ thuật phối ghép để có thể thực hiện thiết kế những mạch điện tử có khả năng ứng dụng cao trong thực tế. 
	Một lần nữa em xin chân thành cảm ơn thầy giáo hướng dẫn Bùi Quốc Anh đã tận tình hướng dẫn và giúp đỡ em rất nhiều trong suốt thời gian thực hiện đồ án này. Em cũng xin chân thành sự giúp đỡ của các anh làm việc ở trung tâm NET.JSC đã giúp đỡ em hoàn thành bản đồ án này. 
PHỤ LỤC
CHƯƠNG TRÌNH ĐIỀU KHIỂN mC AT90S8535
.nolist
.include "\AVR\AvrAssembler\Appnotes\8535def.inc"	
.list
;Defined register 
.def	Save	= r1
.def	HPtrTx	= r2
.def	LPtrTx 	= r3
.def	HPtrRxL 	= r4
.def	HPtrRxH 	= r5
.def	ShowRxL	= r6
.def	ShowRxH 	= r7
.def	ResultADCL = r8
.def	ResultADCH = r9
.def	Implement	= r10
.def	StatementReg = r13
.def 	TimeOut	= r16
.def	Temp	= r17
.def 	Instr	= r18
.def 	Data	= r19
.def 	AddrShow	= r20	
.def	KeyPress	= r21
.def	CtrlReg	= r22
.def	OldKey	= r23
.def	Position	= r24
.def	PositionH	= r25
;Defined control constant 
.equ	RS	= 6	;RS signal
.equ	RW	= 5	;RW signal
.equ	E	= 4	;Enable signal
;Control KeyPad
.equ	Row1	= 7
.equ	Row2	= 6
.equ	Row3	= 5
.equ	Row4	= 4
.equ	Col1	= 0
.equ	Col2	= 1
.equ	Col3	= 2
.equ	Col4	= 3
.equ	INTRATE	= 4	;INT rate keypress
.equ	EnImpKey 	= 1
.equ	ImpKey	= 0
.equ	EnSelectTxRx = 4
.equ	SelectTxRx	= 2
.equ	EnShowRxBuff = 8
.equ 	ShowRxBuff	 = 3
.equ 	EnInstroduc	 = 2
.equ 	Instroduc 	 = 1
.equ	EnOnKeyPress = $80
.equ	OnKeyPress	 = 7
.equ	PressOne 	= 0
.equ	PressTwo 	= $10
.equ	PressThree 	= $20
.equ	PressFour 	= $30	
.equ	CR = $0D
.equ	Statement = $23	;Ascii '#'
.equ	EnShow_CK = $01	;Show cencius
.equ	Show_CK 	= 0	
.equ	EnShowSymbolTempr = $02	;Show symbol Tempr
.equ	ShowSymbolTempr = 1
.equ	EnCencius	= $01	;Display temprature for cencius
;Macro get address of last char in string 
.macro	Get_Addr_Char
	ldi Position,@0	;Last position show @0
	ldi Instr,@1	;Display on line @1
	ldi Temp,@2	;Total char of string @2
	ldi ZL,LOW(@3<<1)	;Name of string @3
	ldi ZH,HIGH(@3<<1)	
	adiw ZL,@2-1	;Get address of last char in string
.endmacro
;Macro get address of string
.macro Get_Addr_String
	ldi Instr,@0	;Position show @0
	ldi @1,LOW(@3<<1)	;Low pointer @1, name's string @3
	ldi @2,HIGH(@3<<1)	;High pointer @2
	ldi Temp,@4	;Total char @4 
.endmacro
;Macro set first ascii code for keypress
.macro Set_First_Ascii
	ldi Data,@0	;Ascii of number @0
	ldi Position,@1	;Ascii of prechar @1	
.endmacro
;Macro get position to display for char
.macro Get_Position
	cpi @0,@1	;Position to show @0, 
	breq GetPos	;Position last @1
	inc @0
GetPos:	mov Instr,@0
.endmacro
;Create buffer for RxD and TxD
.dseg
.org $0060
	TxBuff : .byte 128	;Buffer send
	RxBuff : .byte 128	;Buffer receive
;Defined constant of buffer
.equ	EndTxBuff 	= LOW(TxBuff)+127
.equ	StartTxBuff	= LOW(TxBuff)-1
.equ 	EndRxBuffL 	= $62
.equ	EndRxBuffH = $01
.equ	StartRxBuff	= LOW(RxBuff) 
.cseg
.org $000
	rjmp	RESET	
	rjmp	SCAN_CODE
.org $006
	rjmp	ENABLE_ADC	;Enable ADC
.org $008
	rjmp	KEY_RATE	;INT KEYRATE
.org $00B
	rjmp	Rx_COMPELET	
.org $00E
	rjmp	END_CONVERT	;End convert ADC
.org $011	
PrefA1 	: .db "TRUONG DHBK HA NOI"	
PrefA2 	: .db "KHOA CNTT"
PrefA3 	: .db "DO AN TOT NGHIEP"	
PrefA4 	: .db "NG.CUU IC AT90S8535"
PrefB1 	: .db "SINH VIEN THUC HIEN"
PrefB2 	: .db "VU TAN MANH"
PrefB3 	: .db "GIAO VIEN HUONG DAN"
PrefB4 	: .db "BUI QUOC ANH"
Tile	 	: .db " MEASURE TEMPERATURE"	
Info 	: .db "CURRTEMP ="
Symbol	: .db "Tx:"	
ADCon 	: .db "Waiting" 
OverTx	: .db "OverB! you send?" 
SendTo	: .db "Sending... "
RESET:
	ldi Temp,LOW(RAMEND)	;Init Stack
	out SPL,Temp
	ldi Temp,HIGH(RAMEND)
	out SPH,Temp
	cli
	;Init register Control
	clr CtrlReg	
	clr StatementReg	
	clr Implement	
	;Init port I/O of LCD
	ldi Temp,$0F	;Data lines 
	out DDRC,Temp 
	ldi Temp,$70	;Control Lines (bits 4,5,6)
	out DDRD,Temp	;Init INT0 and LCD busy 
	ldi Temp,$02	
	out PORTD,Temp	;set pullup on pin 2 
	rcall LCD_INIT
	rcall SHOW_PREFACEA
	rcall SHOW_PREFACEB
	rcall DISPLAY_INTERFACE
	Get_Addr_String $8B,ZL,ZH,ADCon,7
	rcall SHOW_STRING	;Show string wait
	rcall SHOW_SELECT_TxRx	
	;Create port for KeyPad and int register
	ldi Temp,$F0	;lower nibble input
	out DDRB,Temp
	ldi Temp,$0F	;Set pullup on lower nibble
	out PORTB,Temp
	ldi OldKey,-1
	ldi AddrShow,$97	;Preaddress to show
	clr KeyPress
	;Init address pointer to buffer Tx
	clr XH
	ldi Temp,StartTxBuff
	mov LPtrTx,Temp
	ldi Temp,LOW(TxBuff)
	mov HPtrTx,Temp
	;Init pointer to buffer Rx
	clr YH
	ldi YL,StartRxBuff
	mov HPtrRxH,YH	
	mov HPtrRxL,YL
	;Init INT of KeyPad
	ldi Temp,$40
	out GIMSK,Temp
	ldi Temp,$00	;Soure trigger INT0 at lower
	out MCUCR,Temp	
	;Init UART
	ldi Temp,$98	;Enable INT Rx compelet
	out UCR,Temp	;8 bit data 1 stop, 1 start
	ldi Temp,$33	;baud = 9600bps
	out UBRR,Temp
	clr Implement	;Init register statement 
	;Init Interrup comperaA match of TC1
	ldi Temp,$10
	out TIMSK,Temp
	ldi Temp,$0C	;Set value $0000 to counter
	out TCCR1B,Temp	;CK/256 = 31.250Hz
	ldi Temp,$01	;Value for comperaA match 312
	out OCR1AH,Temp	;312*(256*0,125)us = 10ms
	ldi Temp,$38	
	out OCR1AL,Temp	
	;Init ADC
	ldi Temp,$00	;Input ADC is PA0 
	out ADMUX,Temp
	ldi Temp,$8F	;Enable single mode
	out ADCSR,Temp
	ldi Temp,-1
	mov ResultADCH,Temp	;Condition show symbol Tempr
	clr ResultADCL
	sei
MAIN:
	sbrs KeyPress,OnKeyPress	;Have a key press
	rjmp NoKeyPress	
	cbr KeyPress,EnOnKeyPress	;Get real KeyPress
	sbrs CtrlReg,ImpKey
	rjmp NormalKey
	rcall CONTROL_KEY
	rjmp EndKeyPress	
NormalKey:rcall DISPLAY_KEY
	in Temp,TIFR	;Clear flag TC1
	andi Temp,INTRATE
	out TIFR,Temp
 	in Temp,TIMSK	;Enabl Int KeyRate
	sbr Temp,TOIE1
	out TIMSK,Temp	
	ldi Temp,$E7	;Init counter for int overflow TC1
	out TCNT1H,Temp	;65.536 - 6.250 = $E796
	ldi Temp,$96	;6.250*(256*0.125) = 200mS
	out TCNT1L,Temp
EndKeyPress:in Temp,GIFR	;Clear flag INT SCAN_CODE
	out GIFR,Temp
	ldi Temp,$40	;Enable INT SCAN_CODE
	out GIMSK,Temp 	
NoKeyPress:ldi Temp,-1
	cp ResultADCH,Temp
	brne SetShowSymbol 
	mov Temp,StatementReg
	sbr Temp,EnShowSymbolTempr
	mov StatementReg,Temp 
SetShowSymbol:sbrc StatementReg,ShowSymbolTempr
	rcall SHOW_SYMBOL_CK
	tst Implement
	brmi SkipToBack	
	rcall EXCUTER_FROM_PC
SkipToBack:rjmp MAIN
;Program control LCD
;(RS = 0,RW = 1)
LCD_BUSY:
	sbi PORTD,RW	;Select DR
Busy:	sbi PORTD,E	;Read 4 MSBs bit
	nop 
	cbi PORTD,E
	sbis PIND,7	;LCD Busy
	rjmp NoBusy
	sbi PORTD,E	;Ignore 4 LSBs bit
	nop
	cbi PORTD,E
	rjmp Busy
NoBusy:	sbi PORTD,E
	cbi PORTD,RW
	cbi PORTD,E
	ret
;Instroduction in register Intr
;(RS = 0, RW = 0)
LCD_INSTR:
	swap Instr	;Send 4 MSB bits
	out PORTC,Instr
	nop
	sbi PORTD,E	
	nop
	cbi PORTD,E	
	swap Instr	;Send 4 LSB bits
	out PORTC,Instr
	nop
	sbi PORTD,E
	nop
	cbi PORTD,E
	ret
;Data in register Data
;(RS = 1, RW = 0)
LCD_DATA:
	sbi PORTD,RS
	swap Data	;Send 4 MSB bits
	out PORTC,Data	
	nop
	sbi PORTD,E
	nop
	cbi PORTD,E
	swap Data	;Send 4 LSB bits
	out PORTC,Data
	nop
	sbi PORTD,E
	nop
	cbi PORTD,E
	cbi PORTD,RS
	ret
;Init LCD
LCD_INIT:
	ldi TimeOut,$96	;Wait 15ms after LCD on
	rcall DELAY
	ldi Instr,$3F	;Function set
	rcall LCD_INSTR
	ldi TimeOut,$29	;Wait 4.1ms
	rcall DELAY
	rcall LCD_INSTR
	ldi TimeOut,$01	;Wait 100us
	rcall DELAY
	rcall LCD_INSTR
	ldi Instr,$28	;Set 4 bits interface 
	rcall LCD_BUSY	;on 2 line, font 5x7 dots
	rcall LCD_INSTR
	ldi Instr,$08	;LCD off
	rcall LCD_BUSY
	rcall LCD_INSTR
	ldi Instr,$01	;Reset DDRAM
	rcall LCD_BUSY
	rcall LCD_INSTR
	ldi Instr,$0C	;LCD on
	rcall LCD_BUSY
	rcall LCD_INSTR
	ldi Instr,$06	;Set address of
	rcall LCD_BUSY	;DDRAM increment
	rcall LCD_INSTR
	ret
;Run char to fixed Position, char in Data
;first address in Instr 
RUN_TO_POS:
	cpi Data,$20
	breq NoRun
	push Temp
	push Instr	
RunChar:	rcall LCD_BUSY
	rcall LCD_INSTR
	rcall LCD_BUSY
	rcall LCD_DATA	;Show char
	cp Instr,Position	;Right position show
	breq HaltRun	
	ldi	Temp,$0A	;Wait 250ms	
	rcall TIMEWAIT
	push Data	;Clear char
	ldi Data,$20
	rcall LCD_INSTR	;Get position to clear 
	rcall LCD_BUSY
	rcall LCD_DATA
	pop Data
	inc Instr	;Next position show
	rjmp RunChar
HaltRun:	pop Instr
	pop Temp 	 	
NoRun:	ret
;Run char of string, Z pointer to last char of string
;coordine in Position, line address in Instr, total char in Temp 
RUN_STRING:
	lpm 	;Load char to Data
	mov Data,r0
	rcall RUN_TO_POS	
	sbiw ZL,1	;Next char in string
	dec Position	;Next position show
	dec Temp	;Remain char count
	brne RUN_STRING
	ret
;Clear char of display string to end of line, char in Data
;end of line in Position, address of char to clear in Instr
CLEAR_TO_POS:
	cpi Data,$20
	breq NoClear
	push Instr
	push Temp
CLRChar:	push Data	;Clear char
	ldi Data,$20
	rcall LCD_INSTR
	rcall LCD_BUSY
	rcall LCD_DATA
	pop Data
	cp Instr,Position	;End of line?
	breq HaltCLR	
	inc Instr	;Next position show
	rcall LCD_BUSY
	rcall LCD_INSTR
	rcall LCD_BUSY
	rcall LCD_DATA	;Reshow char at new position
	ldi TimeOut,10	;Wait 250ms
	rcall TIMEWAIT
	rjmp CLRChar
HaltCLR:	pop Temp
	pop Instr
NoClear:	ret
;Clear display string, Z pointer to last char of string, End of line 
;in Position, address of char to clear in Instr, Totla char in Temp
CLEAR_STRING:
	lpm	;Load char to Data
	mov Data,r0
	rcall CLEAR_TO_POS
	sbiw ZL,1	;Next char to clear
	dec Instr	;Next address of char to clear
	dec Temp	;Remain char count
	brne CLEAR_STRING
	ret
;Display notify PrefaceA
SHOW_PREFACEA:
	Get_Addr_Char $92,$80,18,PrefA1	
	rcall RUN_STRING	;Display on line 1
	Get_Addr_Char $CD,$C0,9,PrefA2	
	rcall RUN_STRING	;Display on line 2
	Get_Addr_Char $A5,$94,16,PrefA3	
	rcall RUN_STRING	;Display on line 3
	Get_Addr_Char $E7,$D4,19,PrefA4	
	rcall RUN_STRING	;Display on line 4
	ret
;Display notify PrefaceB
SHOW_PREFACEB:
	Get_Addr_Char $93,$92,18,PrefA1	
	rcall CLEAR_STRING	;Clear string on line 1
	Get_Addr_Char $93,$80,19,PrefB1
	rcall RUN_STRING	;Display new string on line 1
	Get_Addr_Char $D3,$CD,9,PrefA2	
	rcall CLEAR_STRING	
	Get_Addr_Char $CE,$C0,11,PrefB2
	rcall RUN_STRING	
	Get_Addr_Char $A7,$A5,16,PrefA3	
	rcall CLEAR_STRING	
	Get_Addr_Char $A7,$94,19,PrefB3
	rcall RUN_STRING
	Get_Addr_Char $E7,$E7,19,PrefA4	
	rcall CLEAR_STRING	
	Get_Addr_Char $E3,$D4,12,PrefB4
	rcall RUN_STRING
	ret	
;Display string, position in Instr, Z pointer 
;to first char of string, total char in Temp 
SHOW_STRING:
	rcall LCD_INSTR
ShowNext:	lpm
	mov Data,r0
	rcall LCD_BUSY
	rcall LCD_DATA
	adiw ZL,1
	dec Temp
	brne ShowNext
	ret
;Show symbol RxTx
SHOW_RxTx:
	cpi Position,9
	breq TwoChar
	cpi Position,10
	breq ThrChar
	ldi Temp,1
	rjmp ShowSym
TwoChar:	ldi Temp,2
	rjmp ShowSym
ThrChar:	ldi Temp,3
ShowSym:	ldi Instr,$94
	push Temp
	rcall SHOW_STRING
	pop Temp
	ldi Instr,$D4
	mov ZL,XL
	mov ZH,XH
	push Temp
	rcall LCD_BUSY
	rcall SHOW_STRING
	pop Temp
	cpi Temp,3
	brlo EndRxTx
	ldi Data,$52	;ASCII code of R 
	rcall LCD_BUSY
	rcall LCD_INSTR
	rcall LCD_BUSY
	rcall LCD_DATA
EndRxTx:	ret
;Show interface to LCD, total char in Temp
DISPLAY_INTERFACE:
	ldi Instr,$01	;Clear screen
	rcall LCD_INSTR	
	ldi TimeOut,49	;Wait 4.1ms
	rcall DELAY
	ldi ZL,LOW(Tile<<1)	;String on line 1	
	ldi ZH,HIGH(Tile<<1)
	adiw ZL,19
	ldi YL,LOW(Info<<1)	;String on line 2
	ldi YH,HIGH(Info<<1)
	adiw YL,9
	ldi XL,LOW(Symbol<<1)	;String on line 3,4
	ldi XH,HIGH(Symbol<<1)	
	adiw XL,2	
	ldi Instr,$80
	ldi Temp,1	;Total char show on line 1
	ldi Position,1	;Total char show on line 2
ReShow:	push Instr	
	push ZL
	push ZH
	push Temp
	rcall SHOW_STRING	;Show line 1
	pop Temp
	cpi Temp,11	;Show line 2
	brlo ShowOne	
	ldi Instr,$C0	
	push Temp
	mov Temp,Position
	mov ZL,YL
	mov ZH,YH
	rcall SHOW_STRING	;Show line 2	
	sbiw YL,1	;Part of string shown on line 2
	cpi Position,8
	brlo ShowTwo
	mov ZL,XL
	mov ZH,XH
	rcall SHOW_RxTx	;Show all screen
	sbiw XL,1
ShowTwo:	pop Temp
	inc Position
ShowOne:	pop ZH
	pop	ZL
	pop Instr
	sbiw ZL,1	;Part of string will show
	ldi TimeOut,4	;Wait 100ms	
	rcall TIMEWAIT	
	inc Temp
	cpi Temp,21
	brlo ReShow 
	ret
;Get ascii code of keypress
GET_ASCII_CODE:
	cpi Temp,0
	breq EndGetAscii
	add Position,Temp
	mov Data,Position
EndGetAscii:ret
;Find ascii code of keypress,
;ascii code contain Data
FIND_ASCII_CODE:
	cp KeyPress,OldKey	;First time key press 
	brne FirstPress
	subi CtrlReg,-$10	;increment total time keypress
	cbr CtrlReg,$40	;Get real time keypress	
	dec AddrShow	;reshow new char
	dec LPtrTx	;restore new char	
	rjmp GetTimeKey
FirstPress:	mov OldKey,KeyPress
	cbr CtrlReg,$F0	;Reset time keypress
GetTimeKey:mov Temp,CtrlReg	;Get time keypress
	swap Temp
	andi Temp,$0F	
	cpi KeyPress,5	;Scan code < 5
	brge Key5To9
	cpi KeyPress,3
	brge Key3Or4
	cpi KeyPress,1
	brne Key0Or2
	Set_First_Ascii $31,$43	;Ascii of 1 and D
	rcall GET_ASCII_CODE
	rjmp EndFindAscii
Key0Or2:	cpi KeyPress,2
	breq Key2
	Set_First_Ascii $30,$40
	rcall GET_ASCII_CODE
	rjmp EndFindAscii
Key2:	Set_First_Ascii $32,$46
	rcall GET_ASCII_CODE
	rjmp EndFindAscii
Key3Or4:	cpi KeyPress,3
	breq Key3
	Set_First_Ascii $34,$4C
	rcall GET_ASCII_CODE
	rjmp EndFindAscii
Key3:	Set_First_Ascii $33,$49
	rcall GET_ASCII_CODE
	rjmp EndFindAscii
Key5To9:	cpi KeyPress,7
	brge Key7To9
	cpi KeyPress,6
	brne Key5
	Set_First_Ascii $36,$52
	rcall GET_ASCII_CODE
	rjmp EndFindAscii
Key5:	Set_First_Ascii $35,$4F
	rcall GET_ASCII_CODE
	rjmp EndFindAscii
Key7To9:	cpi KeyPress,8
	brne Key7Or9
	Set_First_Ascii $38,$58
	cpi Temp,3
	brne SkipFour 
	cbr CtrlReg,$F0	;Loopback times keypress 
	ldi Temp,0	;to skip keypress four
SkipFour:	rcall GET_ASCII_CODE	
	rjmp EndFindAscii
Key7Or9:	cpi KeyPress,9
	brne Key7
	Set_First_Ascii $39,$19
	cpi Temp,2
	brne SkipThree
	cbr CtrlReg,$F0
	ldi Temp,0
SkipThree:	rcall GET_ASCII_CODE
	rjmp EndFindAscii
Key7:	Set_First_Ascii $37,$55
	rcall GET_ASCII_CODE
EndFindAscii:ret	
;Display char in Tx buffer, use pointer Z
;total char to show in Temp, position show in Instr
DISPLAY_CHAR_IN_TxBUFF:
	rcall LCD_INSTR
NextShow:	ld Data,Z+
	rcall LCD_BUSY
	rcall LCD_DATA
	dec Temp
	brne NextShow
	ret	
;Get pointer to first char show in Tx buff on LCD
GET_POINTER:
	push Temp
	mov Temp,AddrShow
	subi Temp,$97	;Total current char display
	mov Position,LPtrTx
	sub Position,HPtrTx
	cp Position,Temp	
	breq NoGetPoint
	mov Position,LPtrTx
	sub Position,Temp
	mov HPtrTx,Position	;Set pointer
	pop Temp
NoGetPoint:ret
;Display char in TxBuff to LCD
;Total char to show in Temp
SHOW_CHAR_IN_TxBuff:
	rcall GET_POINTER
	cpi AddrShow,$A7
	brne NoReShow
	cpi Temp,15	;Number char Need to show? 
	brne Show16Char 
	inc HPtrTx	;Show 15 last char	
Show16Char:ldi Instr,$98	;Show 16 last char
	clr ZL
	mov ZL,HPtrTx	;Get pointer to char
	push Data
	rcall DISPLAY_CHAR_IN_TxBUFF
	pop Data
NoReShow:ret
;Show char corresponding keypress, and store char
;into TxBuff to send to PC
DISPLAY_KEY:
	rcall FIND_ASCII_CODE
	inc LPtrTx	;Increment pointer buffer
	ldi Temp,EndTxBuff+1
	cp LPtrTx,Temp	;Over TxBuff
	breq OverBuff	
	ldi Temp,15
	rcall SHOW_CHAR_IN_TxBuff	;Reshow 15 lastchar in buff
	Get_Position AddrShow,$A7
	rcall LCD_INSTR	;Show char to LCD
	rcall LCD_BUSY
	rcall LCD_DATA
	mov XL,LPtrTx
	st X,Data	;Store char
	rjmp EndDisplay
OverBuff:	Get_Addr_String $98,ZL,ZH,OverTx,16
	rcall SHOW_STRING
	dec LPtrTx	;Get back LPtrTx
EndDisplay:ret
;Show symbol select on Tx or Rx
SHOW_SELECT_TxRx:
	ldi Temp,1
	sbrs CtrlReg,SelectTxRx
	rjmp SelectTx
	ldi Instr,$97
	rcall CLEAR_LINE
	ldi Instr,$D7
	rjmp ShowSymbol	
SelectTx:	ldi Instr,$D7
	rcall CLEAR_LINE
	ldi Instr,$97
ShowSymbol:rcall LCD_BUSY
	rcall LCD_INSTR
	ldi Data,$7E	;Symbol select
	rcall LCD_BUSY
	rcall LCD_DATA
	ret
;Perform function select display on Tx or Rx
SELECT_TxRx:
	sbrs CtrlReg,SelectTxRx
	rjmp EnableRx
	cbr CtrlReg,EnSelectTxRx	;Select Tx 	
	rjmp ShowSelect
EnableRx:	sbr CtrlReg,EnSelectTxRx	;Select Rx
ShowSelect:rcall SHOW_SELECT_TxRx
	ret
;Clear char at Addrshow
CLEAR_CHAR_IN_LCD:
	ldi Temp,16
	rcall SHOW_CHAR_IN_TxBuff
	mov Instr,AddrShow
	rcall LCD_INSTR
	ldi Data,$20
	rcall LCD_BUSY
	rcall LCD_DATA
	dec AddrShow
	cpi AddrShow,$97
	brne EndClear
	ldi Temp,LOW(TxBuff)
	cp HPtrTx,Temp
	breq EndClear
	inc AddrShow	;Yet char
	mov Instr,AddrShow
	rcall LCD_BUSY
	rcall LCD_INSTR
	dec HPtrTx
	mov XL,HPtrTx
	ld Data,X	;Get next char to show
	rcall LCD_BUSY
	rcall LCD_DATA
EndClear:ret 
;Perform function backspace
BACK_SPACE:
	sbrc CtrlReg,SelectTxRx	;Selecting Rx
	rjmp NoPerform
	cpi AddrShow,$97
	breq NoPerform	;No char
	dec LPtrTx
	rcall CLEAR_CHAR_IN_LCD	
NoPerform:ret
;Clear char in line, address start in Instr 
;Total char to clear in Temp
CLEAR_LINE:
	rcall LCD_INSTR
	ldi Data,$20
NextClear:	rcall LCD_BUSY
	rcall LCD_DATA
	dec Temp
	brne NextClear	
	ret
;Perform function clear TxRx
CLEAR_Tx_OR_Rx:
	sbrc CtrlReg,SelectTxRx
	rjmp SelectRx
	ldi Instr,$98
	ldi Temp,16	;Total char to clear
	rcall CLEAR_LINE
	ldi Temp,LOW(TxBuff)
	mov HPtrTx,Temp
	ldi Temp,StartTxBuff
	mov LPtrTx,Temp
	ldi AddrShow,$97
	rjmp HalfClear
SelectRx:	ldi Instr,$D8	;Clear display line 
	ldi Temp,16
	rcall CLEAR_LINE
	clr YH	;Reset pointer to RxBuff
	ldi YL,StartRxBuff
	mov HPtrRxH,YH	
	mov HPtrRxL,YL
HalfClear:	ret
;Display char in Rx buffer, use pointer Z
;total char to show in Temp, position show in Instr
DISPLAY_CHAR_IN_RxBUFF:
	rcall LCD_INSTR
NextDisplay:ld Data,Z+
	rcall LCD_BUSY
	rcall LCD_DATA
	cpi ZL,EndRxBuffL+1
	brne NoResetPoint
	clr ZH
	ldi ZL,StartRxBuff
NoResetPoint:dec Temp
	brne NextDisplay
	ret	
;Perform function shift right
SHIFT_RIGHT:
	sbrc CtrlReg,SelectTxRx
	rjmp ShiftR_Rx
	cpi AddrShow,$97
	breq NoShiftR	;No char
	mov Position,AddrShow
	subi Position,$98	;Number of current char 
	mov Temp,LPtrTx
	sub Temp,HPtrTx
	cp Temp,Position
	breq NoShiftR
	inc HPtrTx
	clr ZH
	mov ZL,HPtrTx
	mov Temp,LPtrTx
	sub Temp,HPtrTx
	inc Temp
	cpi Temp,16	;Number char to show
	brge ShowAllChar
	push Temp
	ldi Temp,$A7	;Clear part last in LCD 
	sub Temp,AddrShow
	mov Instr,AddrShow
	inc Instr
	rcall CLEAR_LINE
	pop Temp
	rjmp SetAddr
ShowAllChar:ldi Temp,16
SetAddr:	ldi Instr,$98
	rcall DISPLAY_CHAR_IN_TxBUFF
	rjmp NoShiftR
ShiftR_Rx:	cp HPtrRxL,YL
	breq NoShiftR	;No char in RxBuff
	mov	Position,ShowRxL
	mov PositionH,ShowRxH
	adiw Position,15
	cpi Position,EndRxBuffL+1
	brlo CheckLastPoint
	clr PositionH
	subi Position,$62
	ldi Temp,StartRxBuff-1
	add Position,Temp
CheckLastPoint:cp Position,YL
	breq NoShiftR
	mov	Position,ShowRxL
	mov PositionH,ShowRxH
	adiw Position,1
	cpi Position,EndRxBuffL+1
	brne GetNewPoint 	;Reset pointer
	clr PositionH
	ldi Position,StartRxBuff
GetNewPoint:mov ShowRxL,Position	;Get new pointor	
	mov ShowRxH,PositionH
	mov ZL,ShowRxL
	mov ZH,ShowRxH
	ldi Instr,$D8
	ldi Temp,16
	rcall DISPLAY_CHAR_IN_RxBUFF
NoShiftR:	ret
;Perform function shift left
SHIFT_LEFT:
	sbrc CtrlReg,SelectTxRx
	rjmp ShiftL_Rx
	ldi Temp,LOW(TxBuff)
	cp HPtrTx,Temp
	breq NoShiftL	;No shift
	dec HPtrTx
	mov Temp,LPtrTx
	sub Temp,HPtrTx	
	inc Temp	;Total char to show
	cpi Temp,17
	brlo ShiftTxL 
	ldi Temp,16
ShiftTxL:	ldi Instr,$98	;Position to show
	clr ZH
	mov ZL,HPtrTx
	rcall DISPLAY_CHAR_IN_TxBUFF
	rjmp NoShiftL
ShiftL_Rx:	cp ShowRxL,HPtrRxL
	breq NoShiftL
	mov	Position,ShowRxL
	mov PositionH,ShowRxH
	sbiw Position,1
	cpi Position,StartRxBuff-1
	brne NoGetNewPoint 
	ldi Position,EndRxBuffL
	ldi PositionH,EndRxBuffH
NoGetNewPoint:mov ShowRxL,Position	;Get new pointor	
	mov ShowRxH,PositionH
	ldi Temp,16
	ldi Instr,$D8
	mov ZL,ShowRxL
	mov ZH,ShowRxH
	rcall DISPLAY_CHAR_IN_RxBUFF
NoShiftL:	ret
;Perform function Send
SEND_TxBUFF_TO_PC:
	sbrc CtrlReg,SelectTxRx	;Selecting Rx
	rjmp NoSend
	cpi AddrShow,$97	;No char in buff
	breq NoSend
	Get_Addr_String $98,ZL,ZH,SendTo,16
	rcall SHOW_STRING
	ldi XL,LOW(TxBuff)
SendChar:	ld Data,X
WaitReady:sbis USR,UDRE
	rjmp WaitReady
	out UDR,Data
	cp XL,LPtrTx
	breq ClearToSend
	inc XL
	rjmp SendChar
ClearToSend:rcall CLEAR_Tx_OR_Rx
NoSend:	ret
;Perform control key
CONTROL_KEY:
	cbr CtrlReg,EnImpKey	;Clear confirm controlkey
	cpi KeyPress,13
	brge Key13To15
	cpi KeyPress,11
	brne Key10Or12
	rcall BACK_SPACE
	rjmp EndControlKey
Key10Or12:cpi KeyPress,10
	breq Key10
	rcall SHIFT_LEFT
	rjmp EndControlKey
Key10:	rcall SEND_TxBUFF_TO_PC
	rjmp EndControlKey
Key13To15:cpi KeyPress,14
	breq Key14
	cpi KeyPress,15
	breq Key15
	rcall SHIFT_RIGHT 
	rjmp EndControlKey
Key15:	rcall CLEAR_Tx_OR_Rx
	rjmp EndControlKey
Key14:	rcall SELECT_TxRx
EndControlKey:ldi OldKey,-1 	;Reset OldKey
	ret
;Service INT0
SCAN_CODE:
	in Save,SREG
	ldi KeyPress,$00
	out GIMSK,KeyPress
	ldi TimeOut,2	;Wait 0.2ms for settle
	rcall DELAY
	;Find col
	sbis PINB,Col1
	ldi KeyPress,0
	sbis PINB,Col2
	ldi KeyPress,4
	sbis PINB,Col3
	ldi KeyPress,8
	sbis PINB,Col4
	ldi KeyPress,12
	;invert port to find col
	push Temp
	ldi Temp,$F0	;Lower ninble is output
	out DDRB,Temp
	ldi Temp,$0F	;Set pullup on upper
	out PORTB,Temp
	ldi TimeOut,2	;Wait 0.2ms for settle
	rcall DELAY
	;Find Row
	sbis PINB,Row1
	subi KeyPress,0
	sbis PINB,Row2
	subi KeyPress,-1
	sbis PINB,Row3
	subi KeyPress,-2
	sbis PINB,Row4
	subi KeyPress,-3
	;Get sort KeyPress
	cpi KeyPress,10
	brlo Normal
	sbr CtrlReg,EnImpKey	;Confirm Control key
Normal:	sbr KeyPress,EnOnKeyPress	;Confirm a key press
	in Temp,TIMSK	;Disable int KEY_RATE overflow 
	sbrs Temp,TOIE1	;Enable? 
	rjmp HalfScanCode
	cbr Temp,INTRATE
	out TIMSK,Temp	
HalfScanCode:pop Temp
	out SREG,Save	
	reti
;Service INT delay for reloop of keypress
KEY_RATE:
	in Save,SREG
	ldi OldKey,-1	;Reset register for compera
	push Temp
	in Temp,TIMSK
	cbr Temp,INTRATE
	out TIMSK,Temp	;Disable INT KEY_RATE
	pop Temp
	out SREG,Save
	reti
;Service INT Receive compelet
Rx_COMPELET:
	in Save,SREG
	push Data
	in Data,UDR	;Get data
	sbrs CtrlReg,Instroduc	
	rjmp Get_Code	;Get symbol of Statement 
	mov Implement,Data
	cbr CtrlReg,EnInstroduc
	rjmp HalfRx
Get_Code:	cpi Data,Statement	;Receive symbol Statement 
	brne RxData
	sbr CtrlReg,EnInstroduc
	rjmp HalfRx
RxData:	cpi Data,CR	;End of receive
	brne SetStore
	sbr CtrlReg,EnShowRxBuff	;Reques show data in Rx buff
	ldi Data,$7C	;Symbol "|" end of char	
SetStore:	cpi YL,EndRxBuffL+1
	brne StoreRx
	clr YH	;Back to head RxBuff
	ldi YL,StartRxBuff
	inc HPtrRxL	;Increment head pointer
StoreRx:	st Y+,Data	;Store data to RxBuff
	push Temp
	ldi Temp,StartRxBuff
	cp HPtrRxL,Temp
	breq HalfRx
	cpi YL,EndRxBuffL+1
	brne GetHPtrRx
	clr HPtrRxH	;Reset pointer head RxBuff
	mov HPtrRxL,Temp
	rjmp ResetHPtrRx
GetHPtrRx:	mov HPtrRxL,YL	;Get pointer head RxBuff
	mov HPtrRxH,YH
ResetHPtrRx:pop Temp
HalfRx:	pop Data
	out SREG,Save
	reti
;Service INT enable adc
ENABLE_ADC:
	in Save,SREG	
	sbi ADCSR,ADSC	;Enable convert	
	out SREG,Save
	reti
;Mull result convert with content Data to divide
;Mulled in Data
MULL_RESULT_CONVER:
	clc
	clr r11
	mov r12,ResultADCL
Mull_Data:	dec Data
	breq HalfMull
	add ResultADCL,r12
	adc ResultADCH,r11
	rjmp Mull_Data
HalfMull:	ret
;Divide result convert to get temperature
;result in ResultADCH, remainde in ResultADCL
;Divider in Data
DIVIDE_TO_GET_TEMPR:
	clr r11
	sub r12,r12
LoopDivide:cp ResultADCH,r11
	brne Divide 
	cp ResultADCL,Data
	brlo EndDivide
Divide:	sub ResultADCL,Data
	sbc ResultADCH,r11
	clc
	inc r12
	rjmp LoopDivide
EndDivide:	mov ResultADCH,r12
	ret
;Service INT end convert adc
;Result in ResultADCH, remainde in ResultADCL
END_CONVERT:
	in Save,SREG
	in ResultADCL,ADCL
	in ResultADCH,ADCH
	lsr ResultADCH	;Get 8 bit result
	ror ResultADCL
	lsr ResultADCH
	ror ResultADCL
	push Data
	ldi Data,Statement
SendConfirm:sbis USR,UDRE
	rjmp SendConfirm
	out UDR,Data
	ldi Data,$64	;Mull result with 100
	rcall MULL_RESULT_CONVER
	ldi Data,$FF	;Divide with 255 to get tempr
	rcall DIVIDE_TO_GET_TEMPR
SendResult:	sbis USR,UDRE
	rjmp SendResult
	out UDR,ResultADCH	;Get result	
	push ResultADCH
	clr ResultADCH	;Clear upper byte
	ldi Data,$0A
	rcall MULL_RESULT_CONVER
	ldi Data,$FF
	rcall DIVIDE_TO_GET_TEMPR
	ldi Data,$80
	cp ResultADCL,Data
	brlo Get_Remainder
	inc ResultADCH
Get_Remainder:mov ResultADCL,ResultADCH
	pop ResultADCH
SendRemainde:sbis USR,UDRE
	rjmp SendRemainde
	out UDR,ResultADCL	;Get remainder
	;thay bng dung co bao 
	rcall DISPLAY_TEMPR_TO_LCD
	pop Data
	out SREG,Save
	reti
;Show temperature to LCD
DISPLAY_TEMPR_TO_LCD:
	push Instr
	ldi Instr,$CB
	rcall LCD_INSTR
	push ResultADCL
	mov ResultADCL,ResultADCH
	clr ResultADCH
	sbrs StatementReg,Show_CK
	rjmp ShowTemprC
	clr Instr
	ldi Data,$C8	;Get Kelvin
	add ResultADCL,Data
	adc ResultADCH,Instr
	ldi Data,$49
	add ResultADCL,Data
	adc ResultADCH,Instr 
ShowTemprC:ldi Data,$64
	rcall DIVIDE_TO_GET_TEMPR 	;Get number hundres
	ldi Data,0
	cp ResultADCH,Data
	breq No100
	mov Data,ResultADCH
	subi Data,-$30
	rjmp Show100
No100:	ldi Data,$20
Show100:	rcall LCD_BUSY
	rcall LCD_DATA
	ldi Data,$0A
	clr ResultADCH
	rcall DIVIDE_TO_GET_TEMPR 	
	ldi Data,0
	cp ResultADCH,Data
	breq No10
	mov Data,ResultADCH
	rjmp Show10
No10:	ldi Data,$30
Show10:	rcall LCD_BUSY
	rcall LCD_DATA
	mov Data,ResultADCL
	subi Data,-$30
	rcall LCD_BUSY
	rcall LCD_DATA
	ldi Data,$2E
	rcall LCD_BUSY
	rcall LCD_DATA
	pop ResultADCL
	mov Data,ResultADCL
	subi Data,-$30
	rcall LCD_BUSY
	rcall LCD_DATA
	pop Instr
	ret
;Show symbol temperature
SHOW_SYMBOL_CK:
	mov Temp,StatementReg
	cbr Temp,EnShowSymbolTempr
	mov StatementReg,Temp
	ldi Instr,$D0
	rcall LCD_INSTR
	ldi Data,$DF
	rcall LCD_BUSY
	rcall LCD_DATA
	sbrs StatementReg,Show_CK
	rjmp ShowSymbolC
	ldi Data,$4B	;Ascii of K
	rjmp DisplaySymbol
ShowSymbolC: ldi Data,$43	;Ascii of C
DisplaySymbol: rcall LCD_BUSY
	rcall LCD_DATA
	ret
;Excuter statement from PC
EXCUTER_FROM_PC:
	ldi Temp,EnCencius
	cp Implement,Temp
	brne EnKenvin
	mov Temp,StatementReg
	cbr Temp,EnShow_CK
	rjmp Excuted
EnKenvin:	mov Temp,StatementReg
	sbr Temp,EnShow_CK
Excuted:	sbr Temp,EnShowSymbolTempr
	mov StatementReg,Temp
	ldi Temp,-1
	mov Implement,Temp
	ret
;Program time out delay
;TimeOut delay = (0.1*TimeOut)ms
DELAY:
	push Data
	push Temp
Reloop:	ldi Data,$03
Back:	ldi Temp,$56	
Loop:	dec Temp
	brne Loop
	dec Data
	brne Back
	dec TimeOut
	brne ReLoop
	pop Temp
	pop Data
	ret	
;TimeWait = (25*Temp)ms
TIMEWAIT:
	ldi TimeOut,$FA
	rcall DELAY
	dec Temp
	brne TIMEWAIT
	ret
MỤC LỤC
MỤC LỤC
LỜI NÓI ĐẦU	3
CHƯƠNG I
NHIỆM VỤ VÀ PHƯƠNG HƯỚNG THỰC HIỆN
1.1. NHIỆM VỤ CỦA ĐỒ ÁN.	4
1.2. PHÂN TÍCH NHIỆM VỤ.	4
1.3. PHƯƠNG HƯỚNG THỰC HIỆN.	5
1.3.1. LỰA CHỌN THIẾT BỊ.	5
1.3.2. PHƯƠNG HƯỚNG THIẾT KẾ.	6
CHƯƠNG 2
 LỰA CHỌN LINH KIỆN THIẾT KẾ 
VÀ MỘT SỐ LÝ THUYẾT VỀ CHUYỂN ĐỔI A/D
2.1. LỰA CHỌN LINH KIỆN THIẾT KẾ.	8
2.1.1. GIỚI THIỆU VI MẠCH ĐIỀU KHIỂN AT90S8535.	8
2.1.1.1. CẤU TRÚC CỦA VI MẠCH AT90S8535.	12
2.1.1.2. TẬP THANH GHI ĐA NĂNG CỦA mC AT90S8535.	14
2.1.1.3. BỘ SỐ HỌC VÀ LOGIC - ALU.	15
2.1.1.4. ĐẶC ĐIỂM CÁC BỘ NHỚ TRONG CỦA mC AT90S8535.	15
2.1.1.5. CÁC CHẾ ĐỘ ĐỊA CHỈ CỦA mC AT90S8535.	18
2.1.1.6. THỜI GIAN TRUY CẬP BỘ NHỚ VÀ THỜI GIAN THỰC HIỆN LỆNH.	20
2.1.1.7. KHÔNG GIAN BỘ NHỚ I/O.	21
2.1.1.8. NGẮT VÀ XỬ LÝ NGẮT TRONG mC AT90S8535.	26
2.1.1.9. CÁC CHẾ ĐỘ NGHỈ CỦA mC AT90S8535	35
2.1.1.10. CÁC MẠCH ĐIỀU KHIỂN TRONG mC AT90S8535.	36
2.1.2. MODULE LCD (20X4 CHARACTERS).	85
2.1.3. IC MAX232.	89
2.1.3.1. GIỚI THIỆU CHUẨN RS232.	89
2.1.3.2. IC MAX232.	92
2.1.4. CẢM BIẾN NHIỆT LM335	93
2.2. MỘT SỐ LÝ THUYẾT VỀ CHUYỂN ĐỔI A/D.	94
2.2.1. KHÁI NIỆM CHUNG.	94
2.2.2. MỘT SỐ PHƯƠNG PHÁP CHUYỂN ĐỔI AD.	95
2.2.2.1. PHƯƠNG PHÁP CHUYỂN ĐỔI SONG SONG.	95
2.2.2.2. PHƯƠNG PHÁP XẤP XỈ LIÊN TIẾP.	96
2.2.2.3. PHƯƠNG PHÁP TÍCH PHÂN HAI SƯỜN DỐC.	96
CHƯƠNG 3
THIẾT KẾ HỆ THỐNG PHẦN CỨNG
3.1. SƠ ĐỒ CẤU TRÚC PHẦN CỨNG CỦA HỆ THỐNG.	98
3.2. SƠ ĐỒ GHÉP NỐI mC VỚI MODULE LCD.	98
3.3. SƠ ĐỒ GHÉP NỐI mC VỚI MODULE KEYPAD.	99
3.4. SƠ ĐỒ GHÉP NỐI mC VỚI CẢM BIẾN NHIỆT LM335.	100
3.4. SƠ ĐỒ GHÉP NỐI mC VỚI IC MAX232.	101
3.5. SƠ ĐỒ KẾT NỐI NGUỒN CHO VI MẠCH ĐIỀU KHIỂN.	102
CHƯƠNG 4
THIẾT KẾ HỆ THỐNG PHẦN MỀM CHO mC AT90S8535
4.1. BIỂU ĐỒ CHỨC NĂNG CỦA CHƯƠNG TRÌNH ĐIỀU KHIỂN mC.	103
4.2. LƯU ĐỒ THUẬT TOÁN CỦA CÁC CHỨC NĂNG CHÍNH.	107
4.2.1. CHỨC NĂNG GIAO TIẾP VỚI LCD CONTROLLER.	107
4.2.2. CHỨC NĂNG ĐIỀU KHIỂN VÀ HIỂN THỊ KẾT QUẢ ADC.	109
4.2.3. CHỨC NĂNG GIAO TIẾP VỚI KEYPAD.	112
4.2.4. CHỨC NĂNG TRUYỀN NHẬN DỮ LIỆU NỐI TIẾP VỚI PC.	118
CHƯƠNG 5
THIẾT KẾ HỆ THỐNG PHẦN MỀM TRÊN PC
5.1. MỤC ĐÍCH CỦA PHẦN MỀM TRÊN PC.	120
5.2. MỘT SỐ CHỨC NĂNG CHÍNH CỦA CHƯƠNG TRÌNH	121
5.3. NHẬN XÉT VÀ ĐÁNH GIÁ.	123
KẾT LUẬN	124
PHỤ LỤC	125
CHƯƠNG TRÌNH ĐIỀU KHIỂN mC AT90S8535	125
            Các file đính kèm theo tài liệu này:
 Thiết kế một mạch đo nhiệt độ đơn giản.doc Thiết kế một mạch đo nhiệt độ đơn giản.doc