การสื่อสารข้อมูลผ่านพอร์ตอนุกรม
     ไมโครคอนโทรเลอร์ MCS-51 มีอุปกรณ์ช่วยในการติดต่อสื่อสารข้อมูลแบบอนุกรมกับอุปกรณ์อื่นอยู่ภายในเรียกว่า UART
(Universal Asynchronous Receiver/Transmitter) หรือที่เรารู้จักในชื่อ พอร์ตสื่อสารอนุกรม (Serial port) โดยก่อนการใช้งานเราต้อง
กำหนดโหมดการใช้งานของพอร์ตอนุกรม และอัตราบอด (Baud rate) เสียก่อน

กำหนดโหมดการทำงาน
     พอร์ตอนุกรมของ MCS-51 สามารถสื่อสารข้อมูลทั้งแบบรับและส่งในเวลาเดียวกัน เรียกว่า Full duplex โดยจะใช้พอร์ต P3.0
สำหรับรับข้อมูล และพอร์ต P3.1 สำหรับส่งข้อมูล ซึ่งภายในรีจิสเตอร์สำหรับรับและส่งข้อมูลแยกอีกต่างหาก แต่อย่างไรการใช้ งานเราจะอ้างถึงรีจิสเตอร์ 2 ตัวนี้ ด้วยชื่อเดียวกันคือ SBUF (แอดเดรสที่ 99H ใน SFR) เช่น ถ้าต้องการส่งข้อมูลก็เขียนข้อมูลลง ไปที่ SBUF หรือถ้าต้องการรับข้อมูลก็ให้อ่านข้อมูลจาก SBUF ดังนั้น ก่อนการใช้งานพอร์ตอนุกรมจะต้องกำหนดให้ MCS-51 รู้ เสียก่อนว่าจำนวนบิตที่จะส่งแต่ละครั้งเท่าไร Baud rate ที่ใช้รับ-ส่งข้อมูลเท่าไร และกำหนด Baud rate ที่ต้องการอย่างไร
     ในการกำหนดโหมดการทำงานของพอร์ตอนุกรม จะกำหนดผ่านรีจิสเตอร์ควบคุมพอร์ตอนุกรม หรือ SCON (Serial Port Control
Register) ซึ่งหน้าที่แต่ละบิตของรีจิสเตอร์ SCON อธิบายได้ดังนี้




                                                                               รูปที่ 1 รีจิสเตอร์ SCON

     SM0 (Serial port mode bit 0) สำหรับกำหนดโหมดการทำงานของพอร์ตอนุกรม โดยจะใช้รวมกับบิต SM1
     SM1 (Serial port mode bit 1) ใช้ร่วนกับบิต SM0 ในการกำหนดโหมดการทำานของพอร์ตอนุกรม ซึ่งมีรายละเอียดดังตารางต่อ      ไปนี้







                                                           ตารางที่ 1 การกำหนดโหมดการทำงานของพอร์ตอนุกรม

     SM2 (Serail ports mode bit 2).ใช้ควบคุมเมื่อมีการเชื่อมต่อไมโครคอนโทรลเลอร์หลายตัวในโหมด 2 และโหมด 3 นั่นคือ เมื่อ      เป็นลอจิก 0 จะทำงานในโหมด 0 และเป็นลอจิก 1 จะทำงานในโหมดหลายไมโครคอนโทรลเลอร์
     REN (Received enable bit) ใช้ Enable การับข้อมูล นั่นคือ เมื่อเป็นลอจิก 0 กำหนดให้รับข้อมูล เมื่อเป็นลอจิก 1 กำหนดให้ไม่รับ
     ข้อมูล
     TB8 (Transmit data bit 8) สำหรับเก็บข้อมูลบิตที่ 9 เมื่อต้องการส่งข้อมูลออกพอร์ตอนุกรมในโหมด 2 และโหมด 3
     RB8 (Receive data bit 8) สำหรับเก็บข้อมูลบิตที่ 9 เมื่อต้องการส่งข้อมูลออกพอร์ตอนุกรมในโหมด 2 และโหมด 3
     TI (Transmit Interrupt Flag) เป็นบิตที่ใช้แสดงสถานะการส่งข้อมูลออกพอร์ตอนุกรม เมื่อ MCS-51 ส่งข้อมูลเรียบร้อยแล้ว ก็จะ
     เซตบิต TI เป็นลอจิก 1 (ไม่มีข้อมูลใน SBUF) เพื่อบอกให้โปรแกรมรู้ว่าสามารถส่งข้อมูลอื่นได้ (นำข้อมูลมาใส่ใน SBUF)
     RI (Receive Interrupt Flag) เป็นบิตที่ใช้แสดงสถานพการรับข้อมูลจากพอร์ตอนุกรม เมื่อ MCS-51 รับข้อมูลเรียบร้อยแล้ว (มีข้อ      มูลมาที่ SBUF) ก็จะเซตบิต RI เป็นลอจิก 1 เพื่อบอกให้โปรแกรมรู้ว่าต้องอ่านข้อมูลมาจาก SBUF อย่างรวดเร็ว ก่อนที่ข้อมูล
     อื่นจะเข้ามาแทนที่

การกำหนด Baud rate
     หลังจากเลือกโหมดการทำงานพอร์ตอนุกรมจากข้างต้นแล้ว ต่อไปจะเป็นการกำหนด Baud rate ซึ่งก็คือความเร็วที่ใช้ในการรับ-
ส่งข้อมูลของพอร์ตอนุกรม การกำหนด Baud rate นี้จะทำเฉพาะในโหมด 1 และ 3 เท่านั้น ส่วนในโหมด 0 และโหมด 2 จะถูกกำหนด
ให้โดยอัตโนมัติตามความถี่สัญญาณนาฬิกา (Crystal) ที่ป้อนให้กับ MCS-51
     สำหรับโหมด 0 ค่า Baud rate เกิดจากการนำเอาความถี่สัญญาณนาฬิกาหารด้วย 12 เช่น ถ้า Crystal ความถี่ 11.0592 MHz ค่า
Baud rate ที่ได้จะเป็น 921,583 bps (bps = baud per second) สำหรับในโหมด 2 ค่า Baud rate เิกิดจากการนำเอาความถี่สัญญาณนา-
ฬิกาหารด้วย 64 เช่น ถ้า Crystal ความถี่ 11.0592 MHz ค่า Baud rate ที่ได้จะเป็น 172,797 bps
     ส่วนในโหมด 1 และโหมด 3 ค่า Baud rate จะกำหนดโดยการให้ไทเมอร์ 1 เกิดดารนับเกิน (Overflow) วีธีที่ทำให้เกิดการนับเกิน
ของไทเมอร์ 1 มีหลายวิธี แต่ที่นิยมใช้คือ กำหนดให้ไทเมอร์ 1 ทำงานในโหมด 2 (8 bit auto-reload mode) และโหลดค่าที่จะทำให้ เกิดการนับเกินลงใน TH 1
     การกำหนดค่าให้ TH1 เพื่อกำเนิด Baud rate กรณีที่บิต PCON.7 เป็นลอจิก 0 คำนวณได้ดังนี้
         TH1 = 256 - ((Crystal-384)/Baud)
     ถ้า PCON.7 เป็นลอจิก 1 ค่า Baud rate จะเป็น 2 เท่า คำนวณได้ดังนี้
         TH1 = 256 - ((Crystal -192)/Baud)

ตัวอย่าง สมมติว่า Crystal ความถี่ 11.0592 MHz ต้องการกำหนด Baud rate ที่ 19,200 bps จงคำนวณหาค่าที่จะโหลดลงใน TH1
     
     วิธีคิด
          TH1 = 256 - ((Crystal)/384)/Baud)
          TH1 = 256 - ((11059200)/384)/19200)
          TH1 = 256 - ((2880)/19200) 
          TH1 = 256 - 1.5 = 254.5
     ซึ่งค่าที่ได้เป็นเลยทศนิยม ซึ่งการใช้งานจริงจะต้องกำหนดเป็นจำนวนเต็ม เมื่อทำการปัดขึ้นหรือลง ค่า Baud rate ที่ได้จะไม่ถูก ต้อง จึงต้องเปลี่ยนการคำนวณเป็น Baud rate 2 เท่า คำนวณใหม่ได้ดังนี้
          TH1 = 256 - ((Crystal)/192)/Baud)
          TH1 = 256 - ((11059200)/192)19200)
          TH1 = 256 - ((57600) /19200)
          TH1 = 256 - 3 = 253
     จากนั้นนำค่าที่ได้แปลงเป็นฐานสิบหกก่อนจะโหลดลง TH1 ซึ่งค่าที่ได้คือ FD สรุปขั้นตอนในการกำหนดค่า Baud rate 19200 bps ให้กับ MCS-51 ได้ดังนี้
      1. กำหนดพอร์ตอนุกรมทำงานในโหมด 1 หรือ 3
      2. กำหนดให้ไทเมอร์ 1 ทำงานในโหมด 2 (8-bit aoto-reload)
      3. เซตค่า TH1 เป็น FD
      4. เซตบิต PCON.7 (SMOD) เป็นลอจิก 1 เพื่อกำหนด Baud rate เป็นแบบ 2 เท่า
     
ตัวอย่างการใช้งาน
     เป็นตัวอย่างการับ-ส่งข้อมูลผ่านทางพอร์ตอนุกรม ที่ Baud rate 9600 bps ใช้ Crystal ความถี่ 11.0592 MHz

// AT89C51
// clock = 11.0592Mhz
// buad rate 9600
// transmit 8 bit
/////////////////////////
#pragma SMALL
#include <stdio.h>
#include <reg51.h>

//******* Function Prototypes *******//
void uart_init(void);
void putc(char TxBuff);
char getc(void);

void main (void)
{
     char d;
     uart_init();
          while(1)
               {
               printf("Enter number:");
               d = getc();
               putc(d);
               printf("\n\r");
               }
}

/* Function uart_init */
void uart_init(void)
{
     TR1      = 0;            // Timer1 Disable
     ET1      = 0;            // Timer1 Interrupt Disable
     TMOD = 0x21;      // Set Timer1 as Mode 2
     TH1      = 0xFD;     // Set buad rate 9600 bps
     TR1      = 1;            // Timer1 Enable
     SCON  = 0x50;      // Uart Enable and Set Uart as Mode1
     TI         = 1;            // Set Uart is every working
}

/* Function putc */
void putc(char TxBuff)
{
     while(!TI);
     TI=0;
     SBUF = TxBuff;
     return;
}

/* Function getc */
char getc(void)
{
     char RxBuff;
     while(!RI);
     RxBuff = SBUF;
     RI=0;
     return RxBuff;
}

CODE
กลับสู่หน้าหลัก