; 25v2.ASM ; Version: 2 Date: 07. May 1999 ; Copyright (C) 1999 Georg Ziegler ; NMRA-DCC decoder for iron core motors based on PIC12CE519 with si9986 H-Bridge ; 14/28/126 speed step mode and two internal speed curves ; direct, paged and register mode programming ; 25us timestep for polling of DCC signal ; SPDTAB in LINSPEED.XLS worksheet ; EEPROM read/write routine from MICROCHIP PIC12CE519 documentation ; This program is free software; you can redistribute it and/or ; modify it under the terms of the GNU General Public License as ; published by the Free Software Foundation; either version 2 of ; the License, or (at your option) any later version. ; This program is distributed in the hope that it will be useful, ; but WITHOUT ANY WARRANTY; without even the implied warranty of ; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU ; General Public License for more details. ; You should have received a copy of the GNU General Public License ; along with this program; if not, write to the Free Software ; Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. ; Contact : ; Georg Ziegler ; Zwehrener Weg 23a ; 34121 Kassel ; g.zi@gmx.de ;-------------------------------------------------------------------- LIST P=12CE519, R=DEC INCLUDE __CONFIG _MCLRE_OFF & _CP_ON & _WDT_ON & _IntRC_OSC ;-------------------------------------------------------------------- ; 0AAA AAAA 01DL SSSS -> Lok Adress Direction Light & Speed ; 0AAA AAAA 100D DDDD -> Lok Function F1-F4 & FL ; 0AAA AAAA 1011 DDDD -> Lok Function F5-F8 ; 0000 0000 -> Broadcast Adress for all Lok Decoder ; 10AA AAAA 1AAA CDDD -> 9 Bit Accessory on/off F1-F8 ; 1011 1111 1000 CDDD -> Broadcast Command for all Accessory Decoder ; 11AA AAAA & AAAA AAAA -> long Adress ; 1111 1111 0000 0000 -> Idle Packet for all Decoder ;-------------------------------------------------------------------- CV8 EQU 0x0D ; Home Made Decoder CV7 EQU 0x02 ; Version No. XX00 0000 ; 00=Analog(0x00) 01=Stepper(0x40) ; 10=Fauli(0x80) 11=Other(0xC0) ;-------------------------------------------------------------------- INDF EQU 0x00 ; Indirect Adressing tmr0 EQU 0x01 ; Timer PC EQU 0x02 ; Programm Counter STATUS EQU 0x03 ; Status Register FSR EQU 0x04 ; Special Funcion Register OSCCAL EQU 0x05 ; Calibration Register GPIO EQU 0x06 ; GP0-GP5 input/output ;-------------------- CONFIG EQU 0x07 ; 0=DIR 1=CONSIST 2=STEPOK/NOCV 5=FS126 6=BITHI 7=FLAG S31 EQU 0x08 ; SOLL EQU 0x09 ; speed to go BT1 EQU 0x0A ; FSR auf 0x09 BT2 EQU 0x0B ; BT3 EQU 0x0C ; BT4 EQU 0x0D ; BT5 EQU 0x0E ; BT6 EQU 0x0F ; FSR auf 0x10 ;-------------------- ; EQU 0x10 ; ; EQU 0x11 ; ACC EQU 0x12 ; DEC EQU 0x13 ; ; EQU 0x14 ; ; EQU 0x15 ; ; EQU 0x16 ; ; EQU 0x17 ; XOR EQU 0x18 ; NOADR EQU 0x19 ; no adress since ... PWM EQU 0x1A ; (Z1) ; EQU 0x1B ; IST EQU 0x1C ; actual speed PRE EQU 0x1D ; Preample 12 BIT LO EQU 0x1E ; low bit counter HI EQU 0x1F ; hi bit counter ;-------------------- CV1 EQU 0x30 ; Primary Adress CV2 EQU 0x31 ; Vstart CV3 EQU 0x32 ; Acceleration Rate CV4 EQU 0x33 ; Deceleration Rate CV29 EQU 0x34 ; 0=DIR 1=14/28 2=PWRSRC 3=ADVACK 4=SPDTAB 5=LADRE 6= 7=ACCDEC MAPCV EQU 0x35 ; rom CV's copied to here CV5 EQU 0x36 ; Vhigh CV6 EQU 0x37 ; Vmid CV17 EQU 0x38 ; Extended Adress Low Byte CV18 EQU 0x39 ; Extended Adress High Byte CV19 EQU 0x3A ; Consist Adress CV49 EQU 0x3B ; Output F1-F8 to GP2 (CV49-64) CV50 EQU 0x3C ; reserved for FL/RL to map F1-8 CV51 EQU 0x3D ; space (page register) CV105 EQU 0x3E ; space CV106 EQU 0x3F ; space ;-------------------- CARRY EQU 0 ZERO EQU 2 SEITE EQU 5 #DEFINE DIR CONFIG,0 ; #DEFINE CONSIST CONFIG,1 ; #DEFINE STEPOK? CONFIG,2 ; #DEFINE NOCV CONFIG,2 ; is mapped with STEPOK? #DEFINE ROMCV CONFIG,3 ; is mapped with FLACKER #DEFINE FLACKER CONFIG,3 ; #DEFINE BRAKE CONFIG,4 ; #DEFINE FS126 CONFIG,5 ; #DEFINE BITHI CONFIG,6 ; #DEFINE FLAG CONFIG,7 ; #DEFINE FS28 CV29,1 ; 14/28 speed step #DEFINE STAB CV29,4 ; speedtab / CV2,CV5&CV6 #DEFINE LADRE CV29,5 ; long adress enable #DEFINE DIRINV CV29,0 ; #DEFINE LIINV CV29,2 ; PWRSRC #DEFINE LED GPIO,2 ; #DEFINE ACKBIT STATUS,6 ; never overwriten #DEFINE PROGBIT CV29,6 ; ORG 0 ; Reset Vector ;-------------------------------------------------------------------- INIT MOVWF OSCCAL ; write calibration value ;------------------------- ; BSF FSR,5 ;test ; GOTO TEST ;test ; MOVLW 00001000b ; GP3 input, rest output ; TRIS GPIO ; set port GPIO ;TEST1 CALL STEP ;test ; GOTO TEST1 ;-------------------------- ;------ no Processor with >E8 in osccal possible -------------------- ;INCCAL MOVLW 00100000b ; +2 (ca.+100kHz) for 24us time loop ; BTFSS OSCCAL,3 ; ; SUBWF OSCCAL,1 ; ; BTFSC OSCCAL,3 ; ; ADDWF OSCCAL,1 ; write calibration value +100kHz ; BTFSC STATUS,CARRY ; overflow? ; BSF OSCCAL,3 ; set fast bit ;-------------------------------------------------------------------- MOVLW 00010111b ; wakeup, pullup, T0 int., hightolow, T0, 1:256 OPTION ; ----------------------------------- COMF XOR,0 ; inverted stored for reset conditions (all zero) XORWF SOLL,0 ; for brown out to start XORWF IST,0 ; with same speed BTFSC STATUS,ZERO ; all Bytes ok? GOTO START ; ----------------------------------- CLEAR CLRF IST ; ----------------------------------- CLRF SOLL ; set all register to start condition CLRF S31 ; CLRF LO ; CLRF HI ; set PWM to 1 to force a jump CLRF PWM ; in STEP for stop condition INCF PWM ; ----------------------------------- BEGIN MOVLW 00111111b ; all Input TRIS GPIO ; tristate port GPIO ; EEPROM ............................................................ LOADREG MOVLW 0x30 ; MOVWF FSR ; Pointer for indirect Adressing CLRF EEADDR ; EEREAD BSF STATUS,SEITE ; set to 200H begin EEPROM CALL READ_RANDOM ; BCF STATUS,SEITE ; auf ROM seite 0 BTFSC STATUS,ZERO ; ERROR? GOTO EEREAD ; MOVF EEDATA,0 ; MOVWF INDF ; MOVLW 0x3F ; XORWF FSR,0 ; ANDLW 00111111b ; BTFSC STATUS,ZERO ; GOTO EEEXIT ; INCF FSR,1 ; INCF EEADDR ; GOTO EEREAD ; EEEXIT MOVF CV3,0 ; BTFSC STATUS,ZERO ; IORLW 1 ; XORLW 0xFF ; complement W BCF FSR,5 ; rampage back to 0x10.. MOVWF ACC ; BSF FSR,5 ; rampage to 0x30.. MOVF CV4,0 ; BTFSC STATUS,ZERO ; IORLW 1 ; XORLW 0xFF ; complement W CLRF MAPCV ; for old acknowledge BCF FSR,5 ; rampage back to 0x10.. MOVWF DEC ; MOVLW 0x09 ; adress = BT1 - 1 MOVWF FSR ; Pointer for indirect Adressing GOTO START ; ;^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ;.................................................................. SPDTAB MOVF S31,0 ;11 ADDWF PC ;12 RETLW 0 ;13-14 RETLW 0 ; RETLW 0 ; RETLW 0 ; RETLW 2 ; 1 RETLW 3 ; 2 RETLW 5 ; 3 RETLW 7 ; 4 RETLW 10 ; 5 RETLW 13 ; 6 RETLW 18 ; 7 RETLW 22 ; 8 RETLW 28 ; 9 RETLW 34 ; 10 RETLW 41 ; 11 RETLW 48 ; 12 RETLW 56 ; 13 RETLW 65 ; 14 RETLW 74 ; 15 RETLW 84 ; 16 RETLW 95 ; 17 RETLW 106 ; 18 RETLW 118 ; 19 RETLW 131 ; 20 RETLW 144 ; 21 RETLW 158 ; 22 RETLW 173 ; 23 RETLW 188 ; 24 RETLW 204 ; 25 RETLW 220 ; 26 RETLW 237 ; 27 RETLW 255 ; 28 SPDTAB1 MOVF S31,0 ;11 ADDWF PC ;12 RETLW 0 ;13-14 RETLW 0 ; RETLW 0 ; RETLW 0 ; RETLW 1 ; 1 RETLW 2 ; 2 RETLW 3 ; 3 RETLW 4 ; 4 RETLW 5 ; 5 RETLW 6 ; 6 RETLW 7 ; 7 RETLW 8 ; 8 RETLW 9 ; 9 RETLW 10 ; 10 RETLW 11 ; 11 RETLW 12 ; 12 RETLW 13 ; 13 RETLW 14 ; 14 RETLW 15 ; 15 RETLW 16 ; 16 RETLW 17 ; 17 RETLW 18 ; 18 RETLW 19 ; 19 RETLW 20 ; 20 RETLW 21 ; 21 RETLW 22 ; 22 RETLW 23 ; 23 RETLW 24 ; 24 RETLW 25 ; 25 RETLW 26 ; 26 RETLW 27 ; 27 RETLW 28 ; 28 ;^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ;.................................................................... ;--------------------- multiply MULT1 * MULT2 = hi MULT1 low MULT2 -- MULTIP MOVLW 9 ; 1 MOVWF COUNT ; 2 CLRW ; 3 BCF STATUS,CARRY ; 4 MULTI MOVWF TEMP ; 1 RRF TEMP,0 ; 2 RRF MULT2,1 ; 3 BTFSC STATUS,CARRY ; 4 ADDWF MULT1,0 ; 5 DECFSZ COUNT,1 ; 6 GOTO MULTI ; 7-8 MOVWF MULT1 ; 9*8=72 76 ;-------------------------------- RRF MULT1,1 ; 77 RRF MULT2,1 ;/2 78 RRF MULT1,1 ; 79 RRF MULT2,1 ;/4 80 RRF MULT1,1 ; 81 RRF MULT2,1 ;/8 82 RRF MULT1,1 ; 83 RRF MULT2,1 ;/16 84 RETLW 0 ; END MULTIP 85-86 ;^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ;SSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSS START CLRWDT ; 12 MOVLW 0xFF ; 13 MOVWF BT4 ; 14 MOVWF BT5 ; 15 MOVWF BT6 ; 16 MOVLW 0x09 ; Pointer for ind. Adressing 17 MOVWF FSR ; (BT1 - 1) 18 MOVLW 11 ; 19 MOVWF PRE ; PRE to 10 Bit for Preample 20 ;------------- INTEST BCF STEPOK? ; 21 NOP ; 22 CALL IN ; 23-24 BTFSC STEPOK? ; 4. GOTO STEPOK ; 5.-6 CALL STEP ; 6.-7. BTFSC GPIO,3 ; ########### input ########## 1 (25) BSF BITHI ; 2 NOP ; 3 BTFSC FLACKER ; 4 BCF LED ; 5 NOP ; 6 STEPOK MOVLW 11111100b ; FF-03 7 MOVF HI,1 ; 8 BTFSC STATUS,ZERO ; 0? 9 GOTO LOWBIT ; low half of bit 10-11 ADDWF HI,1 ; BIT im Carry 11 CLRF HI ; 12 DECFSZ PRE,1 ; Pre=0? 13 GOTO PRETEST ; 14-15 BTFSC STATUS,CARRY ; waiting for 0 15 GOTO BYTE ; Preample ok! 16-17 INCF PRE,1 ; 17 NOP ; 18 GOTO INTEST ; next Bit 19-20 PRETEST NOP ; 16 NOP ; 17 BTFSS STATUS,CARRY ; 18 GOTO INTEST ; 19-20 GOTO START22 ; no Preample! 20-21 LOWBIT NOP ; 12 NOP ; 13 NOP ; 14 BTFSC BITHI ; 15 INCF HI ; 16 BCF BITHI ; 17 INCFSZ LO,1 ; 18 GOTO INTEST ; 19-20 GOTO BEGIN ; >10000uS 20-21 ;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ IN BTFSS GPIO,3 ; ########### input ########## 1 (25) RETLW 0 ; 2.-3. INCF HI ; 3. CLRF LO ; 4. BSF STEPOK? ; 5. CALL STEP ; 6.-7. BTFSS GPIO,3 ; ########### input ########## 1 (25) RETLW 0 ; FF-03 2-3 INCF HI ; 3 NOP ; ----------------------------- 4 MOVF IST,0 ; for brown out 5 XORWF SOLL,0 ; to start with 6 MOVWF XOR ; same speed 7 COMF XOR,1 ; ----------------------------- 8 BTFSC FS126 ; 9 GOTO FS126OV ; 10-11 ;.....................SPEEDTAB.......................................... ; BTFSC DIR ;<- 11 ; CALL SPDTAB ; 12-13 ; BTFSS DIR ;<- 13 18 ; CALL SPDTAB1 ; 14-15 19 ; MOVWF SOLL ; 20 ;------------ BTFSS FLAG ;<- 11 CALL SPDTAB ; 12-13 BTFSC FLAG ;<- 13 18 CALL SPDTAB1 ; 14-15 19 MOVWF SOLL ; 20 ;^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ FS126BK BCF STEPOK? ; 21 INCFSZ HI,0 ; 22 GOTO IN ; 23-24 GOTO BEGIN ; >10000uS 24 FS126OV NOP ; 12 NOP ; 13 NOP ; 14 NOP ; 15 NOP ; 16 NOP ; 17 NOP ; 18 GOTO FS126BK ; 19-20 ;+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ ;..................................................................... STEP INCFSZ tmr0,0 ; ISO 25 GOTO INC ; 26-27 MOVF SOLL,0 ; 27 SUBWF IST,0 ; 28 BTFSC STATUS,ZERO ; 29 GOTO EQUAL ; Speed equal 30-31 BTFSC STATUS,CARRY ; 31 GOTO DECNEXT ; 32-33 INCF IST,1 ; 33 MOVF ACC,0 ; 34 GOTO ACCNEXT ; 35-36 DECNEXT DECF IST,1 ; 34 MOVF DEC,0 ; 35 BSF BRAKE ; 36 ACCNEXT MOVWF tmr0 ; 37 NOP ; 38 NOP ; 39 RETLW 0 ; 40-41 INC DECFSZ PWM,1 ; 28 GOTO MOTOR ; 29-30 BSF GPIO,0 ; 30 BSF GPIO,1 ; 31 MOVF IST,0 ; 32 NOP ; 33 NOP ; 34 NOP ; 35 NOP ; 36 NOP ; 37 NOP ; 38 NOP ; 39 RETLW 0 ; 40-41 MOTOR MOVF PWM,0 ; 31 SUBWF IST,0 ; 32 BTFSC DIR ; BTFSC Vorward <-> Reverse 33 GOTO REWIND ; 34-35 NOP ; 35 BTFSC STATUS,CARRY ; 36 BCF GPIO,0 ; IST >= PWM 37 BTFSS STATUS,CARRY ; 38 BSF GPIO,0 ; IST < PWM 39 RETLW 0 ; 40-41 REWIND BTFSC STATUS,CARRY ; 36 BCF GPIO,1 ; IST >= PWM 37 BTFSS STATUS,CARRY ; 38 BSF GPIO,1 ; IST < PWM 39 RETLW 0 ; 40-41 EQUAL BCF BRAKE ; 32 NOP ; 33 NOP ; 34 NOP ; 35 NOP ; 36 NOP ; 37 NOP ; 38 NOP ; 39 RETLW 0 ; 40-41 ;^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ LOWBIT1 MOVLW 0x10 ; ----------------------------- 12 SUBWF FSR,0 ; 13 ANDLW 00000111b ; more than 6 BYTE read 14 BTFSC STATUS,ZERO ; begin new! 15 GOTO START18 ; ----------------------------- 16-17 BTFSC BITHI ; 17 INCF HI ; 18 GOTO INTEST1 ; 19-20 BYTE MOVLW 9 ; PRE to 8 Bit for 1.Byte 18 MOVWF PRE ; 19 INCF FSR,1 ; Pointer for ind. Adressing 20 INTEST1 BCF STEPOK? ; 21 BCF BITHI ; 22 CALL IN ; 23-24 BTFSC STEPOK? ; 4. GOTO STEPOK1 ; 5.-6 CALL STEP ; 6.-7. BTFSC GPIO,3 ; ########### input ########## 1 (25) BSF BITHI ; 2 NOP ; 3 NOP ; 4 NOP ; 5 ; BTFSC FLACKER ; 4 ; BSF LED ; 5 NOP ; 6 STEPOK1 MOVLW 11111100b ; FF-03 7 MOVF HI,1 ; 8 BTFSC STATUS,ZERO ; 0? 9 GOTO LOWBIT1 ; low half of bit 10-11 ADDWF HI,1 ; BIT im Carry 11 CLRF HI ; 12 DECFSZ PRE,1 ; Pre=0? 13 GOTO NEXT ; 14-15 BTFSC STATUS,CARRY ; 15 GOTO BYTE ; 9.Bit=0 16-17 ;------------- Letztes BIT=1 ------------- MOVF BT1,0 ; 17 XORWF BT2,0 ; 18 XORWF BT3,0 ; 19 XORWF BT4,0 ; 20 XORWF BT5,0 ; 21 XORWF BT6,0 ; 22 BTFSS STATUS,ZERO ; all Bytes ok? 23 GOTO START2. ; 24-1. COMF BT1,1 ; 9.Bit=1 (inverting BYTE) 1. COMF BT2,1 ; (inverting BYTE) 2. COMF BT3,1 ; (inverting BYTE) 3. COMF BT4,1 ; (inverting BYTE) 4. COMF BT5,1 ; (inverting BYTE) 5. CALL STEP ; 6.-7. DECF FSR,1 ; auf vorletztes Byte 1 MOVLW 00001000b ; GP3 input, rest output 2 TRIS GPIO ; set port GPIO 3 BSF STATUS,SEITE ; 11 GOTO CV ; 12-13 ;-------------------------------- ; 0_____________<_PWM_______255 ; off ^on off ; PWM=IST EQUIL MOVF IST,0 ; 4 SUBWF PWM,0 ; 5 BTFSS STATUS,CARRY ; PWM > IST? 6 MOVF PWM,0 ; PWM > 8? 7 ANDLW 11111000b ; 8 BTFSC STATUS,ZERO ; difference > 8? 9 GOTO NEQUIL ; 10-11 BSF STATUS,SEITE ; 11 GOTO CV ; 12-13 NEQUIL MOVLW 6 ; 12 MOVWF PRE ; 13 LEQUIL DECFSZ PRE ; 14 17 20 23 2. 5. GOTO LEQUIL ; 15-16 18-19 21-22 24-1. 3.-4. 6. CALL STEP ; 7.-8. GOTO EQUIL ; 2-3 ;-------------------------------- NEXT BTFSC FLACKER ; 4 BSF LED ; 5 ; NOP ; 16 ; NOP ; 17 RLF INDF,1 ; 1.Byte zusammenbauen 18 GOTO INTEST1 ; nächstes Bit 19-20 ;.................................................................... VMIDHI EQU 0x0A ; BT1 VMIDLO EQU 0x0B ; BT2 MULT1 EQU 0x0C ; BT3 MULT2 EQU 0x0D ; BT4 COUNT EQU 0x0E ; BT5 TEMP EQU 0x0F ; BT6 ;------------------------------- TEST MOVLW 1 ; MOVWF CV2 ; MOVLW 255 ; MOVWF CV5 ; MOVLW 0 ; MOVWF CV6 ; ;-------------------------------- BORROW BTFSC S31,4 ; 198 MOVF CV5,0 ; 199 GOTO BBACK ; 200-201 ;-------------------------------- CV2CV5 MOVF CV2,0 ; CV2CV5 94 SUBWF CV5,0 ; 95 MOVWF MULT1 ; 96 BCF STATUS,CARRY ; 97 RRF MULT1,1 ;/2 98 MOVLW 24 ; correction 28/32 99 ADDWF MULT1,1 ; 100 MOVLW 3 ;4-31 -> 1-28 101 SUBWF S31,0 ; 102 MOVWF MULT2 ; 103 ;------- CALL MULTIP ; 104-105 (1-86) ;------- MOVLW 9 ; correction 28/32 192 SUBWF MULT2,1 ; 193 MOVF CV2,0 ; 194 BTFSS STATUS,CARRY ; 195 GOTO BORROW ; 196-197 NOP ; 197 NOP ; 198 ADDWF MULT2,0 ; 199 BTFSC STATUS,CARRY ; 200 MOVF CV5,0 ; 201 BBACK MOVWF SOLL ; 202 ;----------------------------------------------VMID------------------ VMID CLRF VMIDLO ; 200 MOVF CV6,0 ; 201 BTFSC STATUS,ZERO ; 202 GOTO VMIDEND ; no VMID 203 ANDLW 01111111b ; 204 MOVWF VMIDHI ; 205 BTFSS CV6,7 ; 206 GOTO NEGVMID ; 207-208 MOVLW 4 ; 208 SUBWF S31,0 ; 4-32 > 0-27 209 GOTO VMID1 ; 210-211 NEGVMID COMF S31,0 ; 211 ANDLW 00011111b ; 212 NOP ; 213 VMID1 MOVWF COUNT ; 214 BTFSS COUNT,4 ; 215 BTFSC COUNT,3 ; 216 GOTO VMIDMUL ; 217-218 MOVWF TEMP ; 218 BTFSC STATUS,ZERO ; 219 GOTO VMID3 ; 220 BCF STATUS,CARRY ; 221 VMID2 RRF VMIDHI,1 ; ->c 222 RRF VMIDLO,1 ; c-> /2 223 DECFSZ COUNT,1 ; 224 GOTO VMID2 ; 225 VMID3 COMF TEMP,0 ; 226 ANDLW 00000111b ; 227 MOVWF COUNT ; 228 BTFSC STATUS,ZERO ; 229 GOTO VMID5 ; 230 VMID4 NOP ; 231 NOP ; 232 DECFSZ COUNT,1 ; 233 GOTO VMID4 ; 234 VMID5 MOVF CV6,0 ; 235 ANDLW 01111111b ; 236 MOVWF TEMP ; 237 MOVF VMIDHI,0 ; 238 SUBWF TEMP,0 ; 239 GOTO VMIDEND ; 240-241 ;-------------------------------- VMIDMUL SWAPF VMIDHI,0 ; 241 ANDLW 00000111b ; 242 ADDWF VMIDHI,0 ; CV6 + CV6 / 16 243 MOVWF MULT1 ; 244 MOVLW 7 ; 245 SUBWF COUNT,0 ; 246 MOVWF MULT2 ; 247 ;------- CALL MULTIP ; 248-249 (1-86) ;------- MOVF MULT2,0 ; 336 MOVWF TEMP ; 337 RRF MULT1,1 ; 338 RRF MULT2,1 ;/2 339 RRF MULT1,1 ; 340 RRF MULT2,1 ;/4 341 DECF MULT2,0 ; 342 SUBWF TEMP,0 ; 343 SUBWF VMIDHI,0 ; 344 ;------------ VMIDEND BTFSS CV6,7 ; 1 345 GOTO SUBVMID ; 2-3 346-347 ADDWF SOLL,0 ; 3 347 BTFSS STATUS,CARRY ; 6 350 MOVWF SOLL ; 7 351 NOP ; 8 352 SUBEX BSF FS126 ; 9 353 ;------------------------------- ; NOP ; test ; GOTO CV2CV5 ; test ;------------------------------- BCF FSR,5 ; 354 GOTO START ; 355-356 SUBVMID SUBWF SOLL,0 ; 4 348 BTFSC STATUS,CARRY ; 5 349 MOVWF SOLL ; 350 GOTO SUBEX ; 7-8 351-352 ;------------------------------------------END VMID------------------ ;^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ;-------------------------------------------------------------------- START1. NOP ; 1. START2. NOP ; 2. START3. NOP ; 3. START4. NOP ; 4. START5. NOP ; 5. START6. CALL STEP ; 6.-7. START1 NOP ; 1 START2 NOP ; 2 START3 NOP ; 3 START4 NOP ; 4 START5 NOP ; 5 START6 NOP ; 6 START7 NOP ; 7 START8 NOP ; 8 START9 NOP ; 9 START10 GOTO START ; 10-11 START11 NOP ; 11 START12 NOP ; 12 START13 NOP ; 13 START14 NOP ; 14 START15 NOP ; 15 START16 NOP ; 16 START17 NOP ; 17 START18 NOP ; 18 START19 NOP ; 19 START20 NOP ; 20 START21 NOP ; 21 START22 NOP ; 22 START23 GOTO START1. ; 23-24 ;******************************************************************* ORG 0200h TITLE "PIC with EEPROM Data Memory Interface" LIST P=12CE519 SCL EQU 0x07 ; EEPROM Clock, SCL (I/O bit 7) SDA EQU 0x06 ; EEPROM Data, SDA (I/O bit 6) OK EQU 1 NO EQU 0 EE_OK EQU 7 ; Bit 7 in PC_OFFSET used as OK flag for EE PC_OFFSET EQU 0x07 ; PC offset register (low order 4 bits), ; value based on operating mode of EEPROM. ; Also, bit 7 used for EE_OK flag COUNTER EQU 0x08 ; Bit counter for serial transfer EEBYTE EQU 0x09 ; Byte sent to or received from ; EEPROM (control, address, or data) EEADDR EQU 0x0A ; EEPROM Address EEDATA EQU 0x0F ; EEPROM Data ;********************** Set up EEPROM control bytes ************************ READ_CURRENT MOVLW B'10000100' ; PC offset for read current addr. EE_OK bit7='1' MOVWF PC_OFFSET ; Load PC offset GOTO INIT_READ_CONTROL WRITE_BYTE MOVLW B'10000000' ; PC offset for write byte. EE_OK: bit7 = '1' GOTO INIT_WRITE_CONTROL READ_RANDOM MOVLW B'10000011' ; PC offset for read random. EE_OK: bit7 = '1' INIT_WRITE_CONTROL MOVWF PC_OFFSET ; Load PC offset register, value preset in W MOVLW B'10100000' ; Control byte with write bit, bit 0 = '0' START_BIT BCF GPIO,SDA ; Start bit, SDA and SCL preset to '1' ;******* Set up output data (control, address, or data) and counter ******** PREP_TRANSFER_BYTE MOVWF EEBYTE ; Byte to transfer to EEPROM already in W MOVLW 8 ; Counter to transfer 8 bits MOVWF COUNTER ;************ Clock out data (control, address, or data) byte ************ OUTPUT_BYTE BCF GPIO,SCL ; Set clock low during data set-up RLF EEBYTE,1 ; Rotate left, high order bit into carry bit BCF GPIO,SDA ; Set data low, if rotated carry bit is BTFSC STATUS,CARRY ;(SKPNC) a '1', then: BSF GPIO,SDA ; reset data pin to a one, otherwise leave low NOP BSF GPIO,SCL ; clock data into EEPROM DECFSZ COUNTER,1 ; Repeat until entire byte is sent GOTO OUTPUT_BYTE NOP ; Needed to meet Timing (Thigh=4000nS) ;************************** Acknowkedge Check ***************************** BCF GPIO,SCL ; Set SCL low, 0.5us < ack valid < 3us NOP ; Needed to meet Timing (Tlow= 4700nS) BSF GPIO,SDA NOP ; Necessary for SCL Tlow at low voltage, NOP ; Tlow=4700nS BSF GPIO,SCL ; Raise SCL, EEPROM acknowledge still valid BTFSC GPIO,SDA ; Check SDA for acknowledge (low) BCF PC_OFFSET,EE_OK ; If SDA not low (no ack), set error flag BCF GPIO,SCL ; Lower SCL, EEPROM release bus BTFSS PC_OFFSET,EE_OK ; If no error continue, else stop bit GOTO STOP_BIT ;***** Set up program counter offset, based on EEPROM operating mode ***** MOVF PC_OFFSET,0 ANDLW B'00001111' ADDWF PC GOTO INIT_ADDRESS ;PC offset=0, write control done, send address GOTO INIT_WRITE_DATA ;PC offset=1, write address done, send data GOTO STOP_BIT ;PC offset=2, write done, send stop bit GOTO INIT_ADDRESS ;PC offset=3, write control done, send address GOTO INIT_READ_CONTROL ;PC offset=4, send read control GOTO READ_BIT_COUNTER ;PC offset=5, set counter and read byte GOTO STOP_BIT ;PC offset=6, random read done, send stop ;********** Initalize EEPROM data (address, data, or control) bytes ****** INIT_ADDRESS INCF PC_OFFSET,1 ; Increment PC offset to 2 (write) or to 4 (read) MOVF EEADDR,W ; Put EEPROM address in W, ready to send to EEPROM GOTO PREP_TRANSFER_BYTE INIT_WRITE_DATA INCF PC_OFFSET,1 ; Increment PC offset to go to STOP_BIT next MOVF EEDATA,0 ; Put EEPROM data in W, ready to send to EEPROM GOTO PREP_TRANSFER_BYTE INIT_READ_CONTROL BSF GPIO,SCL ; Raise SCL BSF GPIO,SDA ; raise SDA INCF PC_OFFSET,1 ; Increment PC offset to go to READ_BIT_COUNTER next MOVLW B'10100001' ; Set up read control byte, ready to send to EEPROM GOTO START_BIT ; bit 0 = '1' for read operation ;************************** Read EEPROM data ***************************** READ_BIT_COUNTER BSF GPIO,SDA ; set data bit to 1 so we're not pulling bus down. NOP BSF GPIO,SCL MOVLW 8 ; Set counter so 8 bits will be read into EEDATA MOVWF COUNTER READ_BYTE BSF GPIO,SCL ; Raise SCL, SDA valid. SDA still input from ack SETC ; Assume bit to be read = 1 BTFSS GPIO,SDA ; Check if SDA = 1 BCF STATUS,CARRY ;(CLRC) if SDA not = 1 then clear carry bit RLF EEDATA,1 ; rotate carry bit (=SDA) into EEDATA; BCF GPIO,SCL ; Lower SCL bsf GPIO,SDA ; reset SDA DECFSZ COUNTER,1 ; Decrement counter GOTO READ_BYTE ; Read next bit if not finished reading byte BSF GPIO,SCL NOP BCF GPIO,SCL ;****************** Generate a STOP bit and RETURN *********************** STOP_BIT BCF GPIO,SDA ; SDA=0, on TRIS, to prepare for transition to '1' BSF GPIO,SCL ; SCL = 1 to prepare for STOP bit GOTO $+1 ; equivalent 4 NOPs neccessary for I2C spec Tsu:sto = 4.7us GOTO $+1 BSF GPIO,SDA ; Stop bit, SDA transition to '1' while SCL high BTFSS PC_OFFSET,EE_OK ; Check for error RETLW NO ; if error, send back NO RETLW OK ; if no error, send back OK ;************************ End EEPROM Subroutines ************************** ;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX ;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX ;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX ;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX ;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX ;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX ;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX ;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX ; ; 0111 1RRR DDDD DDDD -> register mode ; ; 0111 10AA AAAA AAAA 111K DBBB ; Bit manipulation ; verify/write^ ;.................................................................... CV BSF FSR,5 ; rampage to 0x30.. ;-------------------------------- MOVF BT1,0 ; 25 BTFSS BT1,7 ; >0= 120 (120=CV1 121=CV2 ...) BTFSC STATUS,ZERO ; GOTO PROG ; register mode (CV1-CV8) GOTO HOPP ; ;-------------------------------- SHORTA BTFSC STATUS,ZERO ; address = 0 29 GOTO BCAST ; 30-31 BTFSS LADRE ; long Adress enabled? 31 XORWF CV1,0 ; 32 BTFSC STATUS,ZERO ; 33 GOTO OVER ; 34-35 MOVF CV19,0 ; 35 ANDLW 01111111b ; 36 BCF CONSIST ; 37 BTFSS STATUS,ZERO ; 38 BSF CONSIST ; 39 XORWF BT1,0 ; consist? 40 BCBCK BTFSS STATUS,ZERO ; 41 GOTO CHKPROG ; 42-43 MOVLW 0x2B ; BT2 + FSR,5 43 MOVWF FSR ; to 2. byte 44 ;-------------------------------- DECOD SWAPF INDF,0 ; 45 MOVWF BT6 ; 46 RRF BT6,0 ; 47 ANDLW 00000111b ; 48 ADDWF PC ; 49 GOTO DECCON ; 000 50-51 GOTO ADVAN ; 001 GOTO FORWARD ; 010 GOTO REVERSE ; 011 GOTO FTION ; 100 GOTO FTION1 ; 101 GOTO TELNEW ; 110 GOTO PROGREG ; 111 ;^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ;..................................................................... BITMAN MOVWF FSR ; MOVLW 00000111b ; ANDWF BT3,0 ; CALL BITPOS ; BTFSS BT3,4 ; GOTO VBIT ; verify bit BTFSC BT3,3 ; IORWF INDF,1 ; set bit XORLW 0XFF ; BTFSS BT3,3 ; ANDWF INDF,1 ; clear bit MOVF FSR,0 ; EEADDR GOTO EEPROG ; write complete byte ;-------------------------------- VBIT ANDWF INDF,0 ; BTFSC STATUS,ZERO ; GOTO BITCLR ; ; NOP ; BITSET BTFSC BT3,3 ; GOTO ACKNOW ; =1 GOTO HOPP ; BITCLR BTFSS BT3,3 ; GOTO ACKNOW ; =0 GOTO HOPP ; ;-------------------------------- BITPOS ADDWF PC ; RETLW 00000001b ; 0 RETLW 00000010b ; 1 RETLW 00000100b ; 2 RETLW 00001000b ; 3 RETLW 00010000b ; 4 RETLW 00100000b ; 5 RETLW 01000000b ; 6 RETLW 10000000b ; 7 ;-------------------------------- ;^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ;..................................................................... DECCON BTFSC INDF,5 ; 000>0D< moved to carry 54 ANDLW 00000111b ; 55 ADDWF PC ; 56 GOTO RESET ; 000 reset / hard reset 57-58 GOTO FTEST ; 001 factory test instruction GOTO HOPP ; 010 GOTO ADVACK ; 011 advance acknowl. CV29,3 GOTO HOPP ; 100 GOTO ADVADR ; 101 advance adressing CV29,5 GOTO HOPP ; 110 GOTO ACKREQ ; 111 acknowledge request ;^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ;..................................................................... LIGHT MOVF CV50,1 ; FL/RL to F1-8 BTFSS STATUS,ZERO ; mapped? RETLW 0 ; if CV50 <>0 then no light BTFSS INDF,4 ; 1 GOTO NOLIGHT ; 2-3 BTFSC DIR ; direction invert? 3 GOTO BLIGHT ; 4-5 ; NOP ; 5 FLIGHT BTFSC LIINV ; light invert? (PWRSRC) 6 GOTO BLI ; 7-8 FLI BSF GPIO,4 ; 8 BCF GPIO,5 ; 9 RETLW 0 ; 10-11 BLIGHT BTFSC LIINV ; light invert? (PWRSRC) 6 GOTO FLI ; 7-8 BLI BCF GPIO,4 ; 8 BSF GPIO,5 ; 9 RETLW 0 ; 10-11 NOLIGHT BCF GPIO,4 ; 4 BCF GPIO,5 ; 5 ; NOP ; 6 ; NOP ; 7 ; NOP ; 8 ; NOP ; 9 RETLW 0 ; 10-11 ;^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ;.................................................................... FINDCV BCF NOCV ; BCF ROMCV ; XORLW (1-1) ; CV1 BTFSC STATUS,ZERO ; RETLW CV1 ; Primary Adress XORLW (1-1)^(2-1) ; CV2 BTFSC STATUS,ZERO ; RETLW CV2 ; Vstart XORLW (2-1)^(3-1) ; CV3 BTFSC STATUS,ZERO ; RETLW CV3 ; Acceleration Rate XORLW (3-1)^(4-1) ; CV4 BTFSC STATUS,ZERO ; RETLW CV4 ; Deceleration Rate XORLW (4-1)^(5-1) ; CV5 BTFSC STATUS,ZERO ; RETLW CV5 ; Vhigh XORLW (5-1)^(6-1) ; CV6 BTFSC STATUS,ZERO ; RETLW CV6 ; Vmid XORLW (6-1)^(17-1) ; CV17 BTFSC STATUS,ZERO ; RETLW CV17 ; Extended Adress Low Byte XORLW (17-1)^(18-1) ; CV18 BTFSC STATUS,ZERO ; RETLW CV18 ; Extended Adress High Byte XORLW (18-1)^(19-1) ; CV19 BTFSC STATUS,ZERO ; RETLW CV19 ; Consist Adress XORLW (19-1)^(29-1) ; CV29 BTFSC STATUS,ZERO ; RETLW CV29 ; 0=DIR 1=14/28 2=PWSRC 3=ADVACK 4=SPEEDTAB 5=LADRE 6= 7=ACCDEC XORLW (29-1)^(49-1) ; CV49 BTFSC STATUS,ZERO ; RETLW CV49 ; Output F1-F8 to GP2 XORLW (49-1)^(50-1) ; CV50 BTFSC STATUS,ZERO ; RETLW CV50 ; reserved to map FL/RL to F1-8 XORLW (50-1)^(51-1) ; CV51 BTFSC STATUS,ZERO ; RETLW CV51 ; space BSF ROMCV ; XORLW (51-1)^(7-1) ; CV7 BTFSC STATUS,ZERO ; RETLW CV7 ; Version No XORLW (7-1)^(8-1) ; CV8 BTFSC STATUS,ZERO ; RETLW CV8 ; Manufacturer BCF ROMCV ; BSF NOCV ; RETLW 0xFF ; no CV's to program ;^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ;.................................................................... PROG MOVF FSR,0 ; ANDLW 00001111b ; XORLW BT3 ; BTFSS STATUS,ZERO ; GOTO PROGREG ; 3 byte command MOVF BT2,0 ; CALL FINDCV ; BTFSC NOCV ; GOTO HOPP ; BTFSC ROMCV ; BTFSS BT1,3 ; write/verify bit GOTO ROMNEXT ; MOVWF MAPCV ; MOVLW MAPCV ; ROMNEXT BTFSS BT1,2 ; GOTO BITMAN ; bit manipulation BTFSS BT1,3 ; write/verify bit GOTO EEVERI ; ;-------------------------------- EEPROG ANDLW 00001111b ; MOVWF EEADDR ; CALL READ_RANDOM ; MOVF INDF,0 ; XORWF EEDATA,0 ; BTFSC STATUS,ZERO ; BCF STATUS,SEITE ; auf ROM seite 0 BTFSC STATUS,ZERO ; GOTO LOADREG ; MOVF INDF,0 ; MOVWF EEDATA ; BTFSC PROGBIT ; GOTO EEIN ; BSF PROGBIT ; 2x prog GOTO PROGEX ; EEIN CALL WRITE_BYTE ; BTFSC STATUS,ZERO ; ERROR? GOTO EEIN ; BCF STATUS,SEITE ; auf ROM seite 0 GOTO LOADREG ; ;^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ;.................................................................... OLDACK MOVF BT1,0 ;------ for old DCC-Programmer ------ MOVWF INDF ; save loco adress CLRW ; CV1 GOTO OACK ; EEVERI BTFSC ROMCV ; GOTO RDROMCV ; ANDLW 00001111b ; OACK MOVWF EEADDR ; CALL READ_RANDOM ; MOVF INDF,0 ; XORWF EEDATA,0 ; VERIBK BTFSS STATUS,ZERO ; BCF STATUS,SEITE ; auf ROM seite 0 BTFSS STATUS,ZERO ; GOTO START ; ACKNOW BTFSC ACKBIT ; GOTO ACKNOW1 ; BSF ACKBIT ; 2x verify GOTO PROGEX ; ACKNOW1 MOVLW 00110001b ; set FL/FR and motor on MOVWF GPIO ; LOOP MOVLW 7 ; 7x765uS (5355) 4,5,6,7 ok MOVWF BT5 ; OLOOP CLRF BT6 ; help register CLRWDT ILOOP INCFSZ BT6,1 ; 765uS ON 1 GOTO ILOOP ; 2-3 DECFSZ BT5,1 ; GOTO OLOOP ; CLRF GPIO ; BCF ACKBIT ; BCF FSR,5 ; BCF STATUS,SEITE ; auf ROM seite 0 GOTO START ; RDROMCV XORWF INDF,0 ; GOTO VERIBK ; ;^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ;.................................................................... PROGREG MOVF BT2,0 ;-------------------------------- XORLW 11111001b ; old acknowledge mode BTFSC STATUS,ZERO ; GOTO OLDACK ;-------------------------------- MOVF BT1,0 ; CV5=CV29 XORLW 01111101b ; reg6 BTFSC STATUS,ZERO ; GOTO REG6 ; XORLW (01111101b)^(01111100b) ; reg5 BTFSC STATUS,ZERO ; GOTO REG5 ; MOVF BT1,0 ; ANDLW 00000111b ; lower 3bit ADDWF MAPCV,0 ; CALL FINDCV ; BTFSC NOCV ; GOTO HOPP ; PREG BTFSS BT1,3 ; GOTO EEVERI ; GOTO EEPROG ; REG5 MOVF BT1,0 ; ANDLW 00000111b ; lower 3bit GOTO PREG ; REG6 DECF BT2,1 ; BCF STATUS,CARRY ; RLF BT2,1 ; RLF BT2,0 ; MOVWF MAPCV ; GOTO HOPP ; ;^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ;.................................................................... FTION BTFSC INDF,4 ; 100>LGP3 44 BTFSC STATUS,ZERO ; 45 GOTO FOFF ; 46 FON BTFSC CV49,5 ; BSF FLACKER ; BSF LED ; GOTO HOPP ; FTION1 BTFSS INDF,4 ; 101>1S0 60 MOVWF BT6 ; 61 RRF BT6,0 ; xxx65432->10 62 MOVWF S31 ; xxx43210 63 RLF INDF,0 ; 64 MOVWF SOLL ; 65 BSF FS28 ; 66 BSF FS126 ; 67 GOTO HOPP ; 68-69 ;^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ FTION2 ; 57 TELNEW ; 52 HOPP BCF PROGBIT ; BCF ACKBIT ; PROGEX BCF STATUS,SEITE ; BCF FSR,5 ; GOTO START ; ;******************************************************************** ORG 03FFh MOVLW 0x84 ; for OSCCAL END