0
|
1 ;=============================================================================
|
|
2 ;
|
|
3 ; File adc.asm
|
|
4 ;
|
|
5 ;
|
|
6 ; Copyright (c) 2011, JD Gascuel, HeinrichsWeikamp, all right reserved.
|
|
7 ;=============================================================================
|
|
8 ; HISTORY
|
|
9 ; 2011-08-08 : [mH] moving from OSTC code
|
|
10
|
|
11 #include "ostc3.inc"
|
|
12 #include "math.inc"
|
|
13 #include "wait.inc"
|
|
14 #include "eeprom_rs232.inc"
|
|
15
|
|
16 sensors CODE
|
|
17
|
|
18 wait_adc:
|
|
19 movwf ADCON0
|
|
20 nop
|
|
21 bsf ADCON0,1 ; start ADC
|
|
22 wait_adc2:
|
|
23 btfsc ADCON0,1 ; Wait...
|
|
24 bra wait_adc2
|
|
25 return
|
|
26
|
|
27 global get_battery_voltage
|
|
28 get_battery_voltage: ; starts ADC and waits until fnished
|
|
29 bsf adc_running ; =1: The ADC is in use
|
|
30 movlw b'00100000' ; 2.048V Vref+ -> 1LSB = 500µV
|
|
31 movwf ADCON1
|
|
32 movlw b'00011001' ; power on ADC, select AN6
|
|
33 rcall wait_adc
|
|
34
|
|
35 movff ADRESH,batt_voltage+1 ; store value
|
|
36 movff ADRESL,batt_voltage+0 ; store value
|
|
37 bcf ADCON0,0 ; power off ADC
|
|
38
|
|
39 ; Multiply with 2,006 to be excact here...
|
|
40 ; bcf STATUS,C
|
|
41 ; rlcf xA+0,F
|
|
42 ;
|
|
43 ; rlcf xA+1,F ; x2
|
|
44
|
|
45 ; movff xA+0,batt_voltage+0 ; store value
|
|
46 ; movff xA+1,batt_voltage+1
|
|
47
|
|
48 movlw LOW lithium_36v_low
|
|
49 movwf sub_a+0
|
|
50 movlw HIGH lithium_36v_low
|
|
51 movwf sub_a+1
|
|
52 movff batt_voltage+0,sub_b+0
|
|
53 movff batt_voltage+1,sub_b+1
|
|
54 call subU16 ; sub_c = sub_a - sub_b
|
|
55 ; Battery is 3,6V (>lithium_36v_low?)
|
|
56 btfss neg_flag
|
|
57 bra get_battery_voltage4 ; No, use 1,5V
|
|
58
|
|
59 bsf battery_is_36v ; Yes, set flag (Cleared in power-on reset only!)
|
|
60
|
|
61 ; Check if the battery is near-dead already
|
|
62 movlw LOW lithium_36v_empty
|
|
63 movwf sub_a+0
|
|
64 movlw HIGH lithium_36v_empty
|
|
65 movwf sub_a+1
|
|
66 call subU16 ; sub_c = sub_a - sub_b
|
|
67 ; Battery is not dead yet (>lithium_36v_empty?)
|
|
68 btfsc neg_flag
|
|
69 bra get_battery_voltage2 ; Yes, battery is still ok
|
|
70
|
|
71 ; Battery is probably dead very soon
|
|
72 ; Set ">=24Ah used" into battery gauge registers
|
|
73 movlw .128
|
|
74 movff WREG,battery_gauge+5
|
|
75
|
|
76 get_battery_voltage2:
|
|
77 ; Use 3,6V battery gauging mode
|
|
78 movff battery_gauge+5,xC+3
|
|
79 movff battery_gauge+4,xC+2
|
|
80 movff battery_gauge+3,xC+1
|
|
81 movff battery_gauge+2,xC+0
|
|
82 ; battery_gauge:6 is nAs
|
|
83 ; devide through 65536
|
|
84 ; devide through 364
|
|
85 ; Result is in percent of a 2,4Ah Battery
|
|
86 movlw LOW .364
|
|
87 movwf xB+0
|
|
88 movlw HIGH .364
|
|
89 movwf xB+1
|
|
90 call div32x16 ; xC:4 / xB:2 = xC+3:xC+2 with xC+1:xC+0 as remainder
|
|
91 movff xC+0,lo
|
|
92 ; Limit to 100
|
|
93 movlw .100
|
|
94 cpfslt lo
|
|
95 movwf lo
|
|
96 ; lo will be between 0 (Full) and 100 (empty)
|
|
97 movf lo,W
|
|
98 sublw .100
|
|
99 movwf lo
|
|
100 get_battery_voltage3:
|
|
101 movlw .100
|
|
102 cpfslt lo
|
|
103 movwf lo
|
|
104 ; lo will be between 100 (Full) and 0 (empty)
|
|
105 movf batt_percent,W
|
|
106 cpfsgt lo ; keep batt_percent on the lowest value found
|
|
107 movff lo,batt_percent ; store value
|
|
108 btfsc battery_is_36v ; but always use computed value for 3,6V battery
|
|
109 movff lo,batt_percent ; store value
|
|
110 bcf adc_running ; =1: The ADC is in use
|
|
111 return
|
|
112
|
|
113 get_battery_voltage4:
|
|
114 ; Use 1,5V battery voltage mode
|
|
115 ; Use approximation (batt_voltage:2-aa_15v_low)/4 = lo
|
|
116 movff batt_voltage+0,sub_a+0
|
|
117 movff batt_voltage+1,sub_a+1
|
|
118 movlw LOW aa_15v_low
|
|
119 movwf sub_b+0
|
|
120 movlw HIGH aa_15v_low
|
|
121 movwf sub_b+1
|
|
122 call subU16 ; sub_c = sub_a - sub_b
|
|
123 bcf STATUS,C
|
|
124 rrcf sub_c+1
|
|
125 rrcf sub_c+0 ; /2
|
|
126 bcf STATUS,C
|
|
127 rrcf sub_c+1
|
|
128 rrcf sub_c+0 ; /4
|
|
129 movff sub_c+0,lo
|
|
130 bra get_battery_voltage3 ; Check limits and return
|
|
131
|
|
132 global get_ambient_level
|
|
133 get_ambient_level: ; starts ADC and waits until finished
|
|
134 btfsc adc_running ; ADC in use?
|
|
135 return ; Yes, return
|
|
136
|
|
137 movlw b'00000000' ; Vref+ = Vdd
|
|
138 movwf ADCON1
|
|
139 movlw b'00011101' ; power on ADC, select AN7
|
|
140 rcall wait_adc
|
|
141
|
|
142 movff ADRESH,ambient_light+1
|
|
143 movff ADRESL,ambient_light+0
|
|
144 bcf ADCON0,0 ; power off ADC
|
|
145
|
|
146 ; ambient_light:2 is between 4096 (direct sunlight) and about 200 (darkness)
|
|
147 ; First: Devide through 16
|
|
148 bcf STATUS,C
|
|
149 rrcf ambient_light+1
|
|
150 rrcf ambient_light+0
|
|
151 bcf STATUS,C
|
|
152 rrcf ambient_light+1
|
|
153 rrcf ambient_light+0
|
|
154 bcf STATUS,C
|
|
155 rrcf ambient_light+1
|
|
156 rrcf ambient_light+0
|
|
157 bcf STATUS,C
|
|
158 rrcf ambient_light+1
|
|
159 rrcf ambient_light+0
|
|
160 ; Result: ambient_light:2/16
|
|
161 ; Now, make sure to have value between ambient_light_low and ambient_light_max
|
|
162
|
|
163 movlw .254
|
|
164 tstfsz ambient_light+1 ; >255?
|
|
165 movwf ambient_light+0 ; avoid ADC clipping
|
|
166
|
|
167 incfsz ambient_light+0,W ; =255?
|
|
168 bra get_ambient_level2 ; No, continue
|
|
169
|
|
170 movlw .254
|
|
171 movwf ambient_light+0 ; avoid ADC clipping
|
|
172
|
|
173 get_ambient_level2:
|
|
174 banksel isr_backup ; Back to Bank0 ISR data
|
|
175 movff opt_brightness,isr1_temp
|
|
176
|
|
177 btfsc RCSTA1,7 ; UART module on?
|
|
178 clrf isr1_temp ; Yes, set temporally to eco mode
|
|
179
|
|
180 incf isr1_temp,F ; adjust 0-2 to 1-3
|
|
181
|
|
182 banksel common ; flag is in bank1
|
|
183 movlw ambient_light_max_high ; brightest setting
|
|
184 btfsc battery_is_36v ; 3,6V battery in use?
|
|
185 movlw ambient_light_max_high_36V ; Yes...
|
|
186 banksel isr_backup ; Back to Bank0 ISR data
|
|
187
|
|
188 dcfsnz isr1_temp,F
|
|
189 movlw ambient_light_max_eco ; brightest setting
|
|
190 dcfsnz isr1_temp,F
|
|
191 movlw ambient_light_max_medium; brightest setting
|
|
192
|
|
193 banksel common ; ambient_light is in Bank1
|
|
194 incf ambient_light+0,F ; +1
|
|
195 cpfslt ambient_light+0 ; smaller then WREG?
|
|
196 movwf ambient_light+0 ; No, set to max.
|
|
197
|
|
198 banksel isr_backup ; Back to Bank0 ISR data
|
|
199 movff opt_brightness,isr1_temp
|
|
200 incf isr1_temp,F ; adjust 0-2 to 1-3
|
|
201 movlw ambient_light_min_high ; darkest setting
|
|
202
|
|
203 dcfsnz isr1_temp,F
|
|
204 movlw ambient_light_min_eco ; darkest setting
|
|
205 dcfsnz isr1_temp,F
|
|
206 movlw ambient_light_min_medium; darkest setting
|
|
207 dcfsnz isr1_temp,F
|
|
208 movlw ambient_light_min_high ; darkest setting
|
|
209
|
|
210 banksel common ; ambient_light is in Bank1
|
|
211 cpfsgt ambient_light+0 ; bigger then WREG?
|
|
212 movwf ambient_light+0 ; No, set to min
|
|
213
|
|
214 movff ambient_light+0,max_CCPR1L ; Store value for dimming in TMR7 interrupt
|
|
215 return
|
|
216
|
|
217 global get_rssi_level
|
|
218 get_rssi_level: ; starts ADC and waits until fnished
|
|
219 bsf adc_running ; =1: The ADC is in use
|
|
220 movlw b'00100000' ; 2.048V Vref+
|
|
221 movwf ADCON1
|
|
222 movlw b'01000101' ; power on ADC, select AN17
|
|
223 rcall wait_adc
|
|
224
|
|
225 movff ADRESL,rssi_value
|
|
226 bcf ADCON0,0 ; power off ADC
|
|
227 bcf adc_running ; =1: The ADC is in use
|
|
228 return
|
|
229
|
|
230 global reset_battery_pointer
|
|
231 reset_battery_pointer: ; Resets battery pointer 0x07-0x0C and battery_gauge:5
|
|
232 clrf EEADRH
|
|
233 clrf EEDATA ; Delete to zero
|
|
234 write_int_eeprom 0x07
|
|
235 write_int_eeprom 0x08
|
|
236 write_int_eeprom 0x09
|
|
237 write_int_eeprom 0x0A
|
|
238 write_int_eeprom 0x0B
|
|
239 write_int_eeprom 0x0C
|
|
240 banksel battery_gauge+0
|
|
241 clrf battery_gauge+0
|
|
242 clrf battery_gauge+1
|
|
243 clrf battery_gauge+2
|
|
244 clrf battery_gauge+3
|
|
245 clrf battery_gauge+4
|
|
246 clrf battery_gauge+5
|
|
247 banksel common
|
|
248 movlw .100
|
|
249 movwf batt_percent
|
|
250 return
|
|
251
|
|
252
|
|
253 END |