[ บทความ : มาเขียนโปรแกรมกับ 68HC11 กันเถอะ ตอนที่ 4 ]  พอร์ตของ 68HC811E2

 

                 

ในบทความตอนนี้จะเป็นเรื่องเกี่ยวกับพอร์ตของ 68HC811E2 ทั้งนี้ที่ผมได้กระโดดมากล่าวถึงเรื่องนี้ก่อนที่จะเข้าสู่ชุดคำสั่งนั้น เป็นเพราะว่า ในบทความตอนที่ 2 นั้น ผมได้บอกไปว่า จะใช้ตัวแสดงผลลัพธ์เป็น LED ซึ่งการที่เราจะขับ LED ได้นั้น เราจะต้องอาศัยการติดต่อกับพอร์ตของ 68HC811E2 ด้วยเหตุนี้ ผมจึงจำเป็นต้องศึกษาเรื่องของพอร์ตก่อนที่จะทำอย่างอื่นต่อไป (อย่าลืมนะครับ บทความชุดนี้เป็นลักษณะของคุณและผมเรียนรู้ไปด้วยกัน ผมศึกษาพบเจออะไร ผมก็เขียนออกมาเล่าสู่กันฟังอย่างนั้น) มาเริ่มกันเลยดีกว่าครับ

จุดประสงค์

                ศึกษาเรียนรู้เกี่ยวกับลักษณะและคุณสมบัติของพอร์ตต่างๆ ใน 68HC811E2 พร้อมทั้งศึกษาถึงส่วนที่เกี่ยวข้องกับพอร์ตนั้น หลังจากนั้น เราจะมาลองส่งข้อมูลออกไปที่พอร์ต C เพื่อขับหลอด LED

พอร์ตของ 68HC811E2

พอร์ตของ 68HC811E2 นั้น จะมีการทำงานแบบขนาน ดังนั้น พอร์ตจะมีขนาดหลายบิต (งงไหม?? .. ก็หมายความว่าการรับส่งข้อมูลผ่านพอร์ตนั้น กระทำครั้งละหลายๆบิต หรือที่เรียกว่า ทำงานแบบขนาด หรือ Parallel  ไงล่ะ .. งง กว่าเดิมไหม .. ฮา) ซึ่งจะมีด้วยกันทั้งสิ้น 5 พอร์ตคือ Port-A, Port-B, Port-C, Port-D และ Port-E คราวนี้เรามาดูรายละเอียดของแต่ละตัวกันดีกว่าครับ

1. Port-A

                Port-A จะเป็นพอร์ตขนาด 8 บิต และมีแอดเดรสอยู่ที่ตำแหน่ง 1000h และในพอร์ตนี้ จะถูกแบ่งหน้าที่ทำงานของแต่ละขาแตกต่างกันออกไป นั่นคือ จะมีอยู่ 3 บิตที่เป็นขา Input , 4 บิตสำหรับ Output และ 1 บิตที่ทำงานได้ทั้ง Input และ Output ส่วนรายละเอียดที่มากกว่านี้ เอาไว้กล่าวถึงทีหลังล่ะกันครับ (ถ้ามีโอกาสนะครับ .. J)

2. Port-B

                Port-B จะเป็นพอร์ตขนาด 8 บิต และมีแอดเดรสอยู่ที่ตำแหน่ง 1004h มีหน้าที่เป็น Output ทั้ง 8 บิต

3. Port-C

                Port-C จะเป็นพอร์ตขนาด 8 บิต และมีแอดเดรสอยู่ที่ตำแหน่ง 1003h สามารถทำงานเป็นได้ทั้ง Input และ Output โดย การกำหนดว่าจะให้ทำหน้าที่เป็นอะไรนั้น เราจะต้องกำหนดค่าให้กับเรจิสเตอร์ที่ชื่อว่า DDRC (อยู่ที่ตำแหน่ง 1007h) ซึ่งถ้าเรากำหนดให้บิตใดของ DDRC เป็น 1 ก็แสดงว่า ขานั้นของ Port-C จะทำหน้าที่เป็น Output

                นอกจากนี้ Port-C นั้นจะมีเรจิสเตอร์พิเศษที่ชื่อว่า PORTCL ที่ทำหน้าที่เป็น Latch สำหรับการทำ I/O ของ Port-C ซึ่งเรจิสเตอร์ตัวนี้จะมีขนาด 8 บิต และมีแอดเดรสอยู่ที่ตำแหน่ง 1005h

4. Port-D

                Port-D จะเป็นพอร์ตขนาด 8 บิต แต่เราจะใช้งานได้เพียง 6 บิต โดยอีก 2 บิตจะต้องมีค่าเป็น 0  ใน 6 ขา นี้จะมี 2 ขาที่ชื่อว่า PD0 กับ PD1 ที่เราใช้กับการสื่อสารแบบอนุกรม  (SCI) ส่วนอีก 4 ขานั้น จะนำมาใช้กับระบบ SPI  และมีแอดเดรสอยู่ที่ตำแหน่ง 1008h  หรือเรียกง่ายว่า พอร์ตนี้นั้น เน้นนำไปใช้สำหรับงานด้านการสื่อสารอนุกรมเลยก็ว่าได้ครับ

                เราสามารถกำหนดการทำงานของ Port-D ได้จากเรจิสเตอร์ที่ชื่อว่า DDRD ซึ่งเป็นเรจิสเตอร์ขนาด 8 บิต อยู่ที่ตำแหน่ง 1009h โดยการกำหนดจะเหมือนกับ DDRC คือ ถ้าต้องการให้บิตไหมเป็น Input เราก็กำหนดให้บิตนั้นเป็น 0 แต่ถ้าต้องการให้เป็น Output เราก็กำหนดให้เป็น 1 แต่อย่าลืมว่า บิต 6 กับ 7 นั้นจะต้องเป็น 0 ทั้ง 2 ตัวนะครับ

5. Port-E

                Port-E จะเป็นพอร์ตขนาด 8 บิต และมีแอดเดรสอยู่ที่ตำแหน่ง 100Ah ถูกกำหนดให้เป็นพอร์ต Input ทั้ง 8 บิต และยังสามารถกำหนดให้ทำงานเป็นขาสำหรับทำ A/D ที่มีความละเอียดขนาด 8 บิต ได้อีกด้วย

ส่งข้อมูลออกพอร์ต C

                 จากรายละเอียดของพอร์ต C จะพบว่า ก่อนที่เราจะส่งข้อมูลออกจากพอร์ตนี้ เราจะต้องกำหนดลักษณะการทำงานของพอร์ต ที่เรจิสเตอร์ DDRC แล้วค่อยสั่งงานพอร์ต  เนื่องจาก ผมต้องการขับหลอด LED ดังนั้น ในตัวอย่างนี้ผมจะกำหนดให้ Port-C นั้นเป็นพอร์ตแบบ Output  ทั้ง 8 บิต ดังนั้น DDRC จึงต้องมีค่าเป็น FFh ตัวอย่างโปรแกรมจึงเป็นดังนี้ครับ

;

; Filename  : hc11w02.asm

; Author    : Supachai Budsaratij

; Assembler : Cross-32 version 4

;

        CPU     "68HC11.TBL"

        HOF     "MOT8"

 

PORT_C: EQU     1003h

DDRC:   EQU     1007h

 

        ORG     0000H        ; Data memory (128Bytes)

 

        ORG     0F800H      ; Start point (for 68HC811E2)

MAIN:

        LDS     #0FFh        ; SP = FFh

        LDAB    #0FFh        ; B  = FFh

        STAB    DDRC        ; DDRC = B

 

MAIN_LOOP:

        LDAA    #0AAh       ; A = AAh

        STAA    PORT_C

        BRA     MAIN_LOOP

 

        ORG     0FFFEH      ; Reset vector

        DWM     MAIN

 

        END

 

                ตัวอย่างโปรแกรมรอบนี้จะคล้ายกับบทความที่ 2 แต่เราได้เพิ่มโค้ด (คำสั่ง) เข้าไปเยอะแยะเลยครับ ถ้าอ่านไม่เข้าใจก็ยังไม่เป็นไรครับ เพราะเรายังไม่เจาะรายละเอียดของคำสั่งกันเลย เอาไว้คราวหน้าผมค่อยอธิบายเกี่ยวกับการ LOAD และ STORE ก็แล้วกันครับ ส่วนที่เพิ่มเข้ามาและเป็นเรื่องของ Cross-32 โดยตรง คือ คำสั่ง EQU, # และ DWM

1. กำหนดค่าคงที่ ( EQU )

                EQU เป็นเสมือนคำสั่งสร้าง Macro นั่นคือ ถ้าเราสั่งว่า

                                PORT_C                               EQU                       1007h

                เวลาที่ Cross-32 ทำการแปลชุดคำสั่ง มันก็จะคอยดูว่า มีการใช้คำว่า PORT_C อยู่ที่ใดบ้าง  ถ้าพบว่ามีการใช้ PORT_C ที่ใด มันก็จะนำค่า 1007h ไปใส่แทนคำว่า PORT_C

2. ข้อมูลตัวเลข ( # )

                เนื่องจากตัวเลขนั้นจะมีความหมายได้ 2 อย่าง คือ ข้อมูลและตำแหน่งของหน่วยความจำ Cross-32 เจาะจงว่า ถ้าเรากำลังอ้างถึงข้อมูลที่เป็นตัวเลข ให้เขียน # นำหน้าตัวเลขนั้นไว้ เพราะไม่เช่นนั้น Cross-32 จะมองว่า ตัวเลขนั้นเป็นค่าตำแหน่งของหน่วยความจำ

3. DWM : Define Word (MSB First)

                ในตัวอย่างโปรแกรม เรามีบรรทัดคำสั่งที่เขียนว่า  DWM  MAIN  ซึ่งมีความหมายว่า ให้นำค่าตำแหน่งของ MAIN มาใส่ ณ ตรงนั้น เนื่องจาก MAIN เป็น Label มันจึงเป็นค่าตำแหน่งแบบ 16 บิต ถ้าเราใช้ DFB ก็จะใช้ไม่ได้ (DFB ใช้กับ 8 บิต) ดังนั้น ถ้าเราไม่ต้องการกำหนดเป็นค่าตำแหน่งด้วยตัวเอง เหมือนในตัวอย่างแรก (บทความที่ 2) เราก็ต้องใช้ DWM

หลังจากทำการแปลภาษา และอัพโหลดลงบอร์ดเสร็จแล้ว ผลลัพธ์ที่แสดงบนบอร์ด  ET-EXP/4 I/O จะเป็นดังนี้ครับ

 

สรุป

                จากบทความนี้ ผู้อ่านจะสามารถ ส่งข้อมูลออกจากพอร์ต B เพื่อไปขับหลอด LED ได้แล้ว ในตอนต่อไปเรามาเริ่มเรียนรู้คำสั่งกันดีกว่าครับ .. เจอกันครั้งต่อไปครับ

  


เขียนโดย : ศุภชัย  บุศราทิจ
Author : Supachai  Budsaratij
วันที่ทำการปรับปรุง : ๒๗ ธ.ค. ๒๕๔๕