kuroの覚え書き

96の個人的覚え書き

シリアル通信



Writer509で16F648Aの書き込みができるようになったので、シリアル通信のテストをいろいろやってみた。

送信については以前に使い方を理解していたが受信については未理解であったのでその辺の学習がまずはメイン。

各種設定は以下の通り


;USART INI TXSTA, SPBRG(バンク1),RCSTA(バンク0)
MOVLW 024H ;00100100 非同期モード、高速通信モード
MOVWF TXSTA ;set TX mode
;TXSTA: Transmit Status and Control Register
;bit 7 CSRC: Clock Source Select bit
; Asynchronous mode
; Don’t care
; Synchronous mode
; 1 = Master mode (Clock generated internally from BRG)
; 0 = Slave mode (Clock from external source)
;bit 6 TX9: 9-bit Transmit Enable bit
; 1 = Selects 9-bit transmission
; 0 = Selects 8-bit transmission
;bit 5 TXEN: Transmit Enable bit
; 1 = Transmit enabled
; 0 = Transmit disabled
; Note: SREN/CREN overrides TXEN in SYNC mode.
;bit 4 SYNC: USART Mode Select bit
; 1 = Synchronous mode
; 0 = Asynchronous mode
;bit 3 Unimplemented: Read as '0'
;bit 2 BRGH: High Baud Rate Select bit
; Asynchronous mode
; 1 = High speed
; 0 = Low speed
; Synchronous mode
; Unused in this mode
;bit 1 TRMT: Transmit Shift Register Status bit
; 1 = TSR empty
; 0 = TSR full
;bit 0 TX9D: 9th bit of transmit data. Can be parity bit.

MOVLW 019H ;4MHz, 9600bps, BRGH=1
MOVWF SPBRG ;ボーレートセット
;Desired Baud rate = Fosc / (64 (X + 1))
;example
; 9600 = 16000000 / (64 (X + 1))
; X = [25.042] = 25
;Calculated Baud Rate = 16000000 / (64 (25 + 1))
; = 9615
;Error = (Calculated Baud Rate - Desired Baud Rate) / Desired Baud Rate
; = (9615 - 9600) / 9600
; = 0.16%

BCF STATUS,RP0 ;バンク0に移動
MOVLW 090H ;10010000 非同期モード
MOVWF RCSTA ;set RX mode
;RCSTA: Receive Status and Control Register
;bit 7 SPEN: Serial Port Enable bit
; 1 = Serial port enabled (Configures RX/DT and TX/CK pins as serial port pins)
; 0 = Serial port disabled
;bit 6 RX9: 9-bit Receive Enable bit
; 1 = Selects 9-bit reception
; 0 = Selects 8-bit reception
;bit 5 SREN: Single Receive Enable bit
; Asynchronous mode
; Don’t care
; Synchronous mode - master
; 1 = Enables single receive
; 0 = Disables single receive
; This bit is cleared after reception is complete.
; Synchronous mode - slave
; Unused in this mode
;bit 4 CREN: Continuous Receive Enable bit
; Asynchronous mode
; 1 = Enables continuous receive
; 0 = Disables continuous receive
; Synchronous mode
; 1 = Enables continuous receive until enable bit CREN is cleared (CREN overrides SREN)
; 0 = Disables continuous receive
;bit 3 Unimplemented: Read as '0'
;bit 2 FERR: Framing Error bit
; 1 = Framing error (Can be updated by reading RCREG register and receive next valid byte)
; 0 = No framing error
;bit 1 OERR: Overrun Error bit
; 1 = Overrun error (Can be cleared by clearing bit CREN)
; 0 = No overrun error
;bit 0 RX9D: 9th bit of received data, can be parity bit.

で、受信サブルーチンは次のようなもの


;************************
;シリアル受信ルーチン
;受信したデータをWに格納
;************************
RCV
BTFSS PIR1,RCIF
GOTO RCV
BTFSC RCSTA,FERR
GOTO FRAME
BTFSC RCSTA,OERR
GOTO OVER
MOVF RCREG,W
GOTO EXIT
FRAME MOVF RCREG,W
MOVLW '?'
BTFSS RCSTA,OERR
GOTO EXIT
OVER BCF RCSTA,CREN
BSF RCSTA,CREN
MOVLW '?'
EXIT RETURN

これを


RCVSTART
CALL RCV
CALL LCD_DATA
GOTO RCVSTART

という風にループしてLCDに表示させるテストをしてみたところちゃんと受信し表示された。

ただしこのままでは表示がいっぱいになってもはみ出してしまって書き換えられないのであと一工夫いるだろう。

なお、PIC-PC間の通信をするときにはレベル変換をしてやらないといけないはずであるが、今回レベル変換ICは使わず、PICの通信ポートとUSB-シリアル変換アダプタをそのまま直結してみたが、特に問題なく通信ができた。まあせめて電流制限のための抵抗くらいは入れておいた方がよいだろうが、ちょっとした通信実験ならレベル変換しなくてもマージンの範囲内でいけるようだ。