aqui la 3ra Parte
; *******************************************************
; * Preset Mode *
; *******************************************************
preset_mode
bsf STATUS,RP0 ; Move to bank 1
movlw B'00000110' ; Set port A as digital inputs.
movwf ADCON1
bcf STATUS,RP0 ; return to bank 0
nop ; delay to reset porta
nop
movf PORTA,w ; copy port A in to shadowa
movwf shadowa
xorwf oldporta,w ; look for changes
andwf shadowa,w ; look for rising edge only.
movwf oldporta ; and store in oldporta !
btfsc oldporta,4
call channel5
btfsc oldporta,5
call channel6
movf shadowa,w
movwf oldporta
btfss flag2,savepreset ; if save preset active then
goto load_update_reg
bsf STATUS,RP0 ; move to bank 1
movlw B'00000010' ; set PORTA back to Analogue
movwf ADCON1
bcf STATUS,RP0 ; return to bank 0
nop ; Delay to reset
nop
goto Get_Analogue_Values ; display analogue values
channel5
btfsc flag2,savepreset ; Is save preset in progress
goto save_to_ee ; Yes,
btfsc shadowa,5 ; No, both buttons pressed ??
goto save_preset ; Yes,
movf Current_Preset,w ; No, Load Current Preset in to Status register
movlw Max_Preset+1 ; set up w with new value
btfsc STATUS,Z ; current preset = 0 ??
movwf Current_Preset ; Yes, reload with maxium value then
decf Current_Preset,f ; No, decrease current preset
goto update_preset
channel6
btfsc flag2,savepreset ; Is save preset in progress
goto save_to_ee ; Yes,
btfsc shadowa,4 ; No, Both buttons presed ?
goto save_preset ; Yes,
incf Current_Preset,f ; No, Increse present preset
movf Current_Preset,w
sublw Max_Preset ; subtract max preset from preset
btfsc STATUS,C ; To Large ??
goto update_preset
clrf Current_Preset
update_preset
movf Current_Preset,w ; Move current preset to ee_address (in all Mem)
movwf ee_address
rlf ee_address,f ; * 4.
rlf ee_address,f
call ee_read ; Get channel 1 value
movwf (Channel_Values)
incf ee_address,f
call ee_read ; Get channel 2 value
movwf (Channel_Values+1)
incf ee_address,f
call ee_read ; Get channel 3 Value
movwf (Channel_Values+2)
incf ee_address,f
call ee_read ; Get channel 4 Value
movwf (Channel_Values+3)
return
save_preset
bsf flag2,savepreset ; Set save preset mode
return
save_to_ee
btfss shadowa,4 ; Check CH5 is selected.
return ; No,
btfss shadowa,5 ; Check CH6 is selected
return ; No,
movf Current_Preset,w ; Yes, Both channels
movwf ee_address ; set up EEaddress with current preset
rlf ee_address,f ; * 4
rlf ee_address,f
movf (Channel_Values),w
movwf ee_data
call ee_write ; save Channel 1 Value
incf ee_address,f
movf (Channel_Values+1),w
movwf ee_data
call ee_write ; save Channel 2 Value
incf ee_address,f
movf (Channel_Values+2),w
movwf ee_data
call ee_write ; Save Channel 3 Value
incf ee_address,f
movf (Channel_Values+3),w
movwf ee_data
call ee_write ; save Channel 4 Value
bcf flag2,savepreset ; Clear flag
clrf oldporta ; to prevent rerunning
return
; *********************************************************
; * Display Errors *
; * Input - flags Output - Nothing *
; *********************************************************
D_Mains_Fail
if basic == 1
bsf Data_Rec_LED ; Switch On Both LEDs
bsf Data_Error_LED ;
else
movlw .15 ; Display a F for Mains Fail
call seven_seg
endif
bcf INTCON,T0IE ; Disable Timer0 Interrupts
D_No_Mains_Loop ; No Mains Loop........
btfsc flag,mains_fail
goto D_No_Mains_Loop
call Delay
bsf INTCON,T0IE ; Enable Timer0 Interrupts
return
; ***********************************************
; * Display Routien *
; * Input - Control flags output - Nothing *
; ***********************************************
display
btfsc flag,DMX_Data ; Dmx Currently ??
goto dmx_display ; Yes,
movlw B'11110000' ; No, Clear dmx part of dflag
andwf dflag,f
bcf flag,dmx_error ; clear dmx error flag
btfsc flag,presetmode ; In Preset Mode Currently
goto preset_display ; Yes,
analogue_display ; No,
movlw .11 ; Display A
goto seven_seg
dmx_display
bcf dflag,preset_intro
btfsc flag,dmx_error ; Dmx error recieved ??
goto display_error ; Yes,
btfsc dflag,dmx_lsb ; Displaying LSB ??
goto display_d ; Yes,
btfsc dflag,dmx_csb ; Displaying CSB ??
goto display_lsb ; Yes,
btfsc dflag,dmx_msb ; Displaying MSB ??
goto display_csb ; Yes,
btfsc dflag,dmx_recieve ; Displaying New d ??
goto display_msb ; Yes,
clrf IH_Long_Count
bcf flag,longcount ; Clear and reset Long Count
bsf dflag,dmx_recieve
movlw .10 ; display d.
goto seven_seg
display_msb
btfss flag,longcount ; Has long count finished ??
return ; No,
clrf IH_Long_Count ; Yes, reset long count
bcf flag,longcount
bsf dflag,dmx_msb ; set display flag
movf dmx_hund,w ; and display
goto seven_seg
display_csb
btfss flag,longcount ; Has long count finished ??
return ; No,
clrf IH_Long_Count ; Yes, reset long count
bcf flag,longcount
bsf dflag,dmx_csb ; set display flag
movf dmx_ten,w ; and display
goto seven_seg
display_lsb
btfss flag,longcount ; Has long count finished ??
return ; No,
clrf IH_Long_Count ; Yes, reset long count
bcf flag,longcount
bsf dflag,dmx_lsb ; set display flag
movf dmx_one,w ; and display
goto seven_seg
display_d
btfss flag,longcount ; Has long count finished ??
return
movlw .10 ; Value for d
goto seven_seg ; And display
display_error movlw .13 ; Value for E
goto seven_seg ; and display
preset_display
btfsc flag2,savepreset ; Preset Save taking Place ??
goto display_save ; Yes,
btfsc dflag,preset_intro ; Done Intro Yet ??
goto display_current_preset ; Yes,
display_p
bsf dflag,preset_intro ;
clrf IH_Long_Count ; clear and reset long count.
bcf flag,longcount
movlw .12 ; Value for p
goto seven_seg
display_current_preset
btfss flag,longcount ; Wait for long count
return
movf Current_Preset,w ; display current preset (0 - 9)
goto seven_seg
display_save movlw .14 ; Save chacture = c
goto seven_seg
; ***********************************************
; * 7 Segment Display Drive *
; * Input - w Output = Nothing *
; ***********************************************
seven_seg
movwf displayvalue
xorwf olddisplayvalue,w ; Has display value changed ?
btfsc STATUS,Z ;
return ; No,
; Yes, Display neww value
movf displayvalue,w
movwf olddisplayvalue ; Update old display value
call seg_table
movwf displayvalue
movlw .8
movwf display_count
seven_loop
bcf display_clk ; End of clock pulse
nop
btfsc displayvalue,0 ; Set next data output
bsf display_data
btfss displayvalue,0
bcf display_data
nop
nop
rrf displayvalue,f ; set up next data value
nop
bsf display_clk ; start of clock pulse
nop
nop
decfsz display_count,f ; all data done yet ??
goto seven_loop
return
; *************************************************
; * Find counter value required *
; * Input - position_count output - countervalue *
; *************************************************
find_countervalue ; find amount left on counter and adjust counter
; value to make counter = 255 at end.
bcf flag,phase_done ; do this only after new mains cycle.
btfss position_count,7; if position count >128 then decrese count
goto lower_count ; else increase count
higher_count movf position_count,w
sublw .255 ; Sutract 254 from positioncount
btfsc STATUS,C ; if < 0 then
incf countervalue,f ; increase count
return
lower_count movf position_count,w
sublw .1 ; Sutract 2 from positioncount
btfss STATUS,C ; if > 0 then
decf countervalue,f ; decrease count
return
; ******************************************************
; * EEREAD *
; * *
; * ee_address = Address in EEPROM w = data read *
; ******************************************************
ee_read
bsf STATUS,RP1 ; Move to bank 2
movf ee_address,w
movwf EEADR ; Store eeaddress in correct location
bsf STATUS,RP0 ; Go to Bank 3
bcf EECON1,EEPGD ; Point to Data Memory
bsf EECON1,RD ; Start EEprom read cycle
bcf STATUS,RP0 ; Back to bank 2
movf EEDATA,w
bcf STATUS,RP1 ; Bank to bank 0
return
; ******************************************************
; * EEWRITE *
; * *
; * EEadr = Address in EEPROM eedata = data to write *
; ******************************************************
ee_write
bcf PIR2,EEIF ; clear EE interupt flag
bsf STATUS,RP1 ; Move to bank 2
bcf STATUS,RP0 ;
movf ee_address,w
movwf EEADR ; Save eeaddress
movf ee_data,w
movwf EEDATA ; save eedata
bsf STATUS,RP0 ; Move to bank 3
bcf INTCON,GIE ; Disable interupts
bcf EECON1,EEPGD ; Access Data Memory
bsf EECON1,WREN ; put WREN
movlw H'55'
movwf EECON2
movlw H'AA'
movwf EECON2
bsf EECON1,WR ; write cycle started
bcf STATUS,RP0 ; goto Bank 0
bcf STATUS,RP1
wr1 clrwdt
btfss PIR2,EEIF ; wait for EE write interupt flag
goto wr1 ; write cycle wait
bsf INTCON,GIE ; Enable all interupts
return
; ***********************************************
; * Fast binary to decimal conversion (0..999) *
; * *
; * Input: NumH:NumL *
; * Output Hund:Tens_Ones (packed BCD) *
; * *
; * Size: 59 instructions *
; * Execution time (with return): 60 *
; * *
; * 8-July-2000 by Nikolai Golovchenko *
; * Based on 8bit BIN2BCD of Scott Dattalo *
; ***********************************************
bin2dec999fast
swapf NumL,w ;Add the upper and lower nibbles
addwf NumL,w ;to get the one's digit
andlw 0x0F
skpndc ;Go through a binary to bcd
addlw 0x16 ;conversion for just the one's
skpndc ;digit
addlw 0x06
addlw 0x06
skpdc
addlw -0x06
btfsc NumL,4 ;bit 4 is a special case
addlw 0x16 - 1 + 0x6
skpdc
addlw -0x06 ;now adjust the ten's digit
btfsc NumL,5 ;2^5 = 32, so add 3 to the ten's
addlw 0x30 ;digit if bit 5 is set
btfsc NumL,6 ;2^6 = 64, so add 6
addlw 0x60 ;if bit 6 is set
btfsc NumL,7 ;2^7 = 128, so add 2 (the ten's
addlw 0x20 ;digit) if bit 7 is set
addlw 0x60 ;convert the ten's digit to bcd
clrf Hund
rlf Hund,f ;if there's a carry, then the input
btfss Hund,0 ;was greater than 99.
addlw -0x60
movwf Tens_Ones
movlw 0x66 ;2^8 = 256, so add 0x56 to Tens_Ones
btfsc NumH,0
movlw 0x56 + 0x66 ;add 0x66 for decimal adjust
addwf Tens_Ones,f
skpnc
incf Hund,f
clrw
skpc
iorlw 0x60
skpdc
iorlw 0x06
subwf Tens_Ones,f
movlw 0x66 ;2^9 = 512, so add 0x12 to Tens_Ones
btfsc NumH,1
movlw 0x12 + 0x66
addwf Tens_Ones,f
skpnc
incf Hund,f
clrw
skpc
iorlw 0x60
skpdc
iorlw 0x06
subwf Tens_Ones,f
btfsc NumL,7 ;finish with hundreds
incf Hund,f
movlw 2
btfsc NumH,0
addwf Hund,f
movlw 5
btfsc NumH,1
addwf Hund,f
split
movf Hund,w
movwf dmx_hund
movf Tens_Ones,w
andlw 0Fh
movwf dmx_one
swapf Tens_Ones,w
andlw 0Fh
movwf dmx_ten
return
; *******************************************************
; * Delay Loop *
; * No Input No Output *
; *******************************************************
Delay
movlw Delay_Value
movwf Delay_Count
Delay_Loop
decfsz Delay_Count,f
goto Delay_Loop
return
; *******************************************************
; * Process Required Curve *
; * Input - w controls in flag output in w *
; * Inverts input to output
; *******************************************************
process_curve
movwf process_temp ; Save value in w
btfsc flag,switch ; Switching required ??
goto process_switching ; yes,
btfsc flag,curve ; Cuve or linear ??
goto process_scurve ; Curve
process_linear
comf process_temp,w ; invert value in to w
btfsc STATUS,Z ; If zero then
movlw .1 ; make value = 1
return
process_switching
btfss process_temp,7 ; Look for 50 % value
retlw .254 ; < 50 % ( inverted value)
retlw .1 ; > 50 % ( inverted value)
process_scurve ; Do table lookup.
movwf tbllo ; Store low table value
movlw HIGH (tablestart) ; Get High Table value
movwf PCLATH ; store High Table value
movlw Low (tablestart) ; add lower offset to low value
addwf tbllo,w ;
btfsc STATUS,C ; Carry from the addition ?
incf PCLATH,f ; yes,
;movf tbllo,w
;call do_table
;clrf PCLATH
;return
;addwf PCL,f ; Do Jump
movwf PCL ; Do Jump
tablestart
retlw .255
retlw .249
retlw .243
retlw .238
retlw .234
retlw .230
retlw .227
retlw .223
retlw .221
retlw .218
retlw .215
retlw .213
retlw .211
retlw .209
retlw .207
retlw .205
retlw .203
retlw .202
retlw .200
retlw .198
retlw .197
retlw .195
retlw .194
retlw .193
retlw .191
retlw .190
retlw .189
retlw .188
retlw .187
retlw .185
retlw .184
retlw .183
retlw .182
retlw .181
retlw .180
retlw .179
retlw .178
retlw .177
retlw .176
retlw .175
retlw .175
retlw .174
retlw .173
retlw .172
retlw .171
retlw .170
retlw .169
retlw .169
retlw .168
retlw .167
retlw .166
retlw .166
retlw .165
retlw .164
retlw .163
retlw .163
retlw .162
retlw .161
retlw .161
retlw .160
retlw .159
retlw .159
retlw .158
retlw .157
retlw .157
retlw .156
retlw .155
retlw .155
retlw .154
retlw .154
retlw .153
retlw .152
retlw .152
retlw .151
retlw .151
retlw .150
retlw .149
retlw .149
retlw .148
retlw .148
retlw .147
retlw .147
retlw .146
retlw .145
retlw .145
retlw .144
retlw .144
retlw .143
retlw .143
retlw .142
retlw .142
retlw .141
retlw .141
retlw .140
retlw .139
retlw .139
retlw .138
retlw .138
retlw .137
retlw .137
retlw .136
retlw .136
retlw .135
retlw .135
retlw .134
retlw .134
retlw .133
retlw .133
retlw .132
retlw .132
retlw .131
retlw .131
retlw .130
retlw .130
retlw .129
retlw .129
retlw .128
retlw .128
retlw .127
retlw .127
retlw .126
retlw .126
retlw .125
retlw .125
retlw .124
retlw .124
retlw .123
retlw .123
retlw .122
retlw .122
retlw .121
retlw .121
retlw .120
retlw .120
retlw .119
retlw .119
retlw .118
retlw .118
retlw .117
retlw .117
retlw .116
retlw .116
retlw .115
retlw .115
retlw .114
retlw .114
retlw .113
retlw .113
retlw .112
retlw .112
retlw .111
retlw .111
retlw .110
retlw .110
retlw .109
retlw .109
retlw .108
retlw .108
retlw .107
retlw .107
retlw .106
retlw .106
retlw .105
retlw .105
retlw .104
retlw .104
retlw .103
retlw .103
retlw .102
retlw .102
retlw .101
retlw .100
retlw .100
retlw .99
retlw .99
retlw .98
retlw .98
retlw .97
retlw .97
retlw .96
retlw .95
retlw .95
retlw .94
retlw .94
retlw .93
retlw .92
retlw .92
retlw .91
retlw .91
retlw .90
retlw .89
retlw .89
retlw .88
retlw .87
retlw .87
retlw .86
retlw .85
retlw .85
retlw .84
retlw .83
retlw .83
retlw .82
retlw .81
retlw .81
retlw .80
retlw .79
retlw .78
retlw .78
retlw .77
retlw .76
retlw .75
retlw .74
retlw .74
retlw .73
retlw .72
retlw .71
retlw .70
retlw .69
retlw .68
retlw .68
retlw .67
retlw .66
retlw .65
retlw .64
retlw .63
retlw .62
retlw .61
retlw .59
retlw .58
retlw .57
retlw .56
retlw .55
retlw .54
retlw .52
retlw .51
retlw .50
retlw .48
retlw .47
retlw .45
retlw .43
retlw .42
retlw .40
retlw .38
retlw .36
retlw .34
retlw .32
retlw .30
retlw .27
retlw .25
retlw .22
retlw .19
retlw .16
retlw .12
retlw .8
retlw .3
retlw .0
retlw .0
retlw .0
retlw .0
retlw .0
END ; directive 'end of program