;************************************************************************* ; Copyright 2004 Hata Akihiro ; ; 第1章 電子工作初心者のためのハードウェア入門 ; 1−12 応用回路の実例 ; USBインターフェース ;------------------------------------------------------------------------- ;プログラムの説明 ;<動作> ; ホストPCからのコマンドでLED1〜4を点灯/消灯させる。 ; SW1〜4がONしたらホストPCへコマンドを送る。 ; ;<コマンド> ; L1ON HOST-> PIC LED1 ON ; L2ON HOST-> PIC LED2 ON ; L3ON HOST-> PIC LED3 ON ; L4ON HOST-> PIC LED4 ON ; L1OFF HOST-> PIC LED1 OFF ; L2OFF HOST-> PIC LED2 OFF ; L3OFF HOST-> PIC LED3 OFF ; L4OFF HOST-> PIC LED4 OFF ; ; S1ON PIC-> HOST SW1 ON ; S2ON PIC-> HOST SW2 ON ; S3ON PIC-> HOST SW3 ON ; S4ON PIC-> HOST SW4 ON ; ;<通信条件> ; SPEED 9600 bps ; DATA 8bit ; Parity Non ; Stop bit 1 ; Hand Shake Non ;------------------------------------------------------------------------- ; 2004/06/10 V1.00 初回リリース ; ; ; ; ;------------------------------------------------------------------------- ; CONFIGRATION FUSE ; WDT:Disable OSC:XT Code Protect:OFF Power up timer:ON ; OSCILLATOR ; 4MHz ;************************************************************************* ; LIST P=16F628A, R=DEC ;Target Processor INCLUDE P16F628A.INC ; __CONFIG _BODEN_OFF & _WDT_OFF & _XT_OSC & _CP_OFF & _PWRTE_ON & _DATA_CP_OFF & _LVP_OFF & _MCLRE_OFF & _DATA_CP_OFF __idlocs H'0100' ;V1.00 2004/06/10 ; ;------------------------------------------------------------------------- ; DEFINE I/O Port ;------------------------------------------------------------------------- ; PortA ; RA0 LED2 output ; RA1 LED1 output ; RA2 LED4 output ; RA3 LED3 output ; RA4 input ; RA5 input ; ; PortB ; RB0 input ; RB1 RS-232C RX input ; RB2 RS-232C TX output ; RB3 SW4 input ; RB4 SW3 input ; RB5 SW1 input ; RB6 SW2 input ; RB7 input ; ;------------------------------------------------------------------------- ; Variables ;------------------------------------------------------------------------- LED1 EQU 1 LED2 EQU 0 LED3 EQU 3 LED4 EQU 2 SW1 EQU 5 SW2 EQU 6 SW3 EQU 4 SW4 EQU 3 ;------------------------------------------------------------------------- ; Registers ;------------------------------------------------------------------------- ; ST_TEMP EQU H'20' ; Status Reg. Temp. for Interupt W_TEMP EQU H'21' ; Work Reg. Temp. for Interupt REC_ERR EQU H'22' ; FLAG for RX Error SEND_TEMP EQU H'23' ; TEMP Reg. for TX W_CNT0 EQU H'24' ; COUNTER for Wait W_CNT1 EQU H'25' ; COUNTER for Wait RA_OUT EQU H'26' ; PORTA OUT Reg. RB_OUT EQU H'27' ; PORTB OUT Reg. TEMP0 EQU H'28' ; Temporary Reg. TEMP1 EQU H'29' ; Temporary Reg. TEMP2 EQU H'2A' ; Temporary Reg. SW_NO EQU H'2B' ; SW Count Number REC_DATA EQU H'2C' ; Receive Data TX_FLAG EQU H'2D' ; TX Data FLAG LED_NO EQU H'2E' ; LED Number ;------------------------------------------------------------------------- ; Program code ;------------------------------------------------------------------------- ; ORG H'00' ; Power ON GOTO START ; ; ORG H'04' ; Go Interupt GOTO INTERUPT ;------------------------------------------------------------------------- ; Initialize ;------------------------------------------------------------------------- START MOVLW 0x20 ; BANK1 Data Clear MOVWF FSR REG_CLEAR CLRF INDF INCF FSR,F MOVF FSR,W XORLW 0x7F BTFSS STATUS,Z GOTO REG_CLEAR ; BSF STATUS,RP0 MOVLW B'00000111' ; PORTB Pull Up MOVWF OPTION_REG MOVLW B'11110000' ; Set I/O Port INPUT/OUTPUT MOVWF TRISA MOVLW B'11111011' MOVWF TRISB MOVLW H'24' ; Set Async mode MOVWF TXSTA ; Set TX mode MOVLW 25 MOVWF SPBRG ; SET BAUD RATE 9600bps BCF STATUS,RP0 MOVLW H'FF' MOVWF CMCON ; Set CMCON MOVLW H'90' ; Set Async mode MOVWF RCSTA ; Set RX mode ;---------------------- ; OUTPUT Initialize ;---------------------- MOVLW B'00000000' MOVWF RA_OUT MOVLW B'00000000' MOVWF RB_OUT MOVF RA_OUT,W MOVWF PORTA MOVF RB_OUT,W MOVWF PORTB ;******************************************************* ; MAIN PROGRAM ;******************************************************* MAIN ; GOTO SW_POLLING ;---------------------- ; Command Receive ;---------------------- BTFSS PIR1,RCIF ;check receive end frag GOTO LED_END BTFSC RCSTA,FERR ;framing error? GOTO ER_OUT ;error BTFSC RCSTA,OERR ;overrun error? GOTO ER_OUT ;error MOVF RCREG,W ;get data & reset RCIF MOVWF REC_DATA ;save data MOVLW A'L' SUBWF REC_DATA,W ; L? BTFSS STATUS,Z GOTO LED_END ; No CALL RX BTFSC REC_ERR,0 GOTO ER_OUT MOVF REC_DATA,W ; MOVWF LED_NO CALL RX BTFSC REC_ERR,0 GOTO ER_OUT MOVLW A'O' SUBWF REC_DATA,W ; O? BTFSS STATUS,Z GOTO LED_END CALL RX BTFSC REC_ERR,0 GOTO ER_OUT MOVLW A'N' SUBWF REC_DATA,W ; N? BTFSC STATUS,Z GOTO ON MOVLW A'F' SUBWF REC_DATA,W ; F? BTFSS STATUS,Z GOTO LED_END CALL RX BTFSC REC_ERR,0 GOTO ER_OUT MOVLW A'F' SUBWF REC_DATA,W ; F? BTFSS STATUS,Z GOTO LED_END CALL RX BTFSC REC_ERR,0 GOTO ER_OUT MOVLW H'0D' SUBWF REC_DATA,W ; IS IT CR? BTFSS STATUS,Z GOTO LED_END MOVLW B'00000111' ANDWF LED_NO,W ADDWF PCL,F GOTO LED_END GOTO LED1_OFF GOTO LED2_OFF GOTO LED3_OFF GOTO LED4_OFF GOTO LED_END GOTO LED_END GOTO LED_END ON CALL RX BTFSC REC_ERR,0 GOTO ER_OUT MOVLW H'0D' SUBWF REC_DATA,W ; IS IT CR? BTFSS STATUS,Z GOTO LED_END MOVLW B'00000111' ANDWF LED_NO,W ADDWF PCL,F GOTO LED_END GOTO LED1_ON GOTO LED2_ON GOTO LED3_ON GOTO LED4_ON GOTO LED_END GOTO LED_END GOTO LED_END ;---------------------- ; LED ON/OFF ;---------------------- LED1_ON BSF RA_OUT,LED1 MOVF RA_OUT,W MOVWF PORTA GOTO LED_END LED2_ON BSF RA_OUT,LED2 MOVF RA_OUT,W MOVWF PORTA GOTO LED_END LED3_ON BSF RA_OUT,LED3 MOVF RA_OUT,W MOVWF PORTA GOTO LED_END LED4_ON BSF RA_OUT,LED4 MOVF RA_OUT,W MOVWF PORTA GOTO LED_END LED1_OFF BCF RA_OUT,LED1 MOVF RA_OUT,W MOVWF PORTA GOTO LED_END LED2_OFF BCF RA_OUT,LED2 MOVF RA_OUT,W MOVWF PORTA GOTO LED_END LED3_OFF BCF RA_OUT,LED3 MOVF RA_OUT,W MOVWF PORTA GOTO LED_END LED4_OFF BCF RA_OUT,LED4 MOVF RA_OUT,W MOVWF PORTA GOTO LED_END LED_END ;---------------------- ; SW Polling ;---------------------- SW_POLLING BTFSC PORTB,SW1 ; TX FLAG Clear BCF TX_FLAG,SW1 BTFSC PORTB,SW2 BCF TX_FLAG,SW2 BTFSC PORTB,SW3 BCF TX_FLAG,SW3 BTFSC PORTB,SW4 BCF TX_FLAG,SW4 COMF PORTB,W ANDLW B'01111000' MOVWF TEMP0 BTFSC STATUS,Z ; SW ON Check GOTO SW_POLLING_END CALL W_25 CALL W_25 COMF PORTB,W ANDLW B'01111000' SUBWF TEMP0,W BTFSS STATUS,Z ; SW ON Check GOTO SW_POLLING_END CLRF TEMP2 ; ON SW NUMBER COUNT MOVF TEMP0,W MOVWF TEMP1 RLF TEMP1,F RLF TEMP1,F BTFSC STATUS,C INCF TEMP2,F RLF TEMP1,F BTFSC STATUS,C INCF TEMP2,F RLF TEMP1,F BTFSC STATUS,C INCF TEMP2,F RLF TEMP1,F BTFSC STATUS,C INCF TEMP2,F MOVF TEMP2,W SUBLW 1 BTFSC STATUS,Z ; If only one SW was ON GOTO TX_COMMAND ; Goto TX COMMAND SW_POLLING_END GOTO MAIN ;---------------------- ; TX Command ;---------------------- TX_COMMAND MOVF TEMP0,W SUBWF TX_FLAG,W BTFSC STATUS,Z GOTO TX_COMMAND_END BTFSS TEMP0,SW1 GOTO $+3 MOVLW A'1' GOTO TX_START BTFSS TEMP0,SW2 GOTO $+3 MOVLW A'2' GOTO TX_START BTFSS TEMP0,SW3 GOTO $+3 MOVLW A'3' GOTO TX_START BTFSS TEMP0,SW4 GOTO TX_COMMAND_END MOVLW A'4' TX_START MOVWF SW_NO MOVLW A'S' CALL TX MOVF SW_NO,W CALL TX MOVLW A'O' CALL TX MOVLW A'N' CALL TX MOVLW H'0D' CALL TX CALL W_10 MOVF TEMP0,W MOVWF TX_FLAG TX_COMMAND_END GOTO MAIN ;---------------------- ; ERROR PROCESS ;---------------------- ER_OUT MOVF RCREG,W ; dumy read CLRF RCSTA MOVLW 090H MOVWF RCSTA ; error status reset GOTO MAIN ; ;******************************************************* ; Subroutines ;******************************************************* ;---------------------- ; Data Recieve ;---------------------- ; RX CLRF REC_ERR BTFSS PIR1,RCIF ;check receive end frag GOTO RX BTFSC RCSTA,FERR ;framing error? BSF REC_ERR,0 ;error BTFSC RCSTA,OERR ;overrun error? BSF REC_ERR,0 ;error MOVF RCREG,W ;get data & reset RCIF MOVWF REC_DATA ;save data RETURN ; ;---------------------- ; Data Transmit ;---------------------- ; TX MOVWF SEND_TEMP ;data save BSF STATUS,RP0 ;switch to Bank1 TX_LOOP BTFSS TXSTA,TRMT ;ready check GOTO TX_LOOP BCF STATUS,RP0 ;return to Bank0 MOVF SEND_TEMP,W ;get data MOVWF TXREG ;start send RETURN ; ;---------------------- ; Wait Time count (at 4MHz CLOCK) ;---------------------- W_25 MOVLW 250 ; 25ms GOTO W_T W_10 ; 10ms MOVLW 100 GOTO W_T W_5 ; 5ms MOVLW 50 GOTO W_T W_2 ; 2ms MOVLW 20 GOTO W_T W_1 ; 1ms MOVLW 10 GOTO W_T W_P500 ; 500us MOVLW 5 GOTO W_T W_P300 ; 300us MOVLW 3 GOTO W_T W_P200 ; 200us MOVLW 2 GOTO W_T ; W_T MOVWF W_CNT0 W_P100 ;100uS MOVLW 32 MOVWF W_CNT1 W_P003 ;3uS DECFSZ W_CNT1,F ;1uS,(2uS) GOTO W_P003 ;1uS DECFSZ W_CNT0,F GOTO W_P100 RETURN ; ;******************************************************* ; INTERUPT ;******************************************************* INTERUPT ;**** save W register & status register MOVWF W_TEMP ;save w reg SWAPF STATUS,W ;status to wreg MOVWF ST_TEMP ;save status ; INT_END ;**** register restore and return SWAPF ST_TEMP,W ;get saved status MOVWF STATUS SWAPF W_TEMP,F ;get saved wreg SWAPF W_TEMP,W RETFIE ; END