1 ///////////////////////////////////////////////////////////////////////////////
\r
3 // IAR Atmel AVR C/C++ Compiler V4.30F/W32 13/Mar/2008 04:52:02 /
\r
4 // Copyright 1996-2007 IAR Systems. All rights reserved. /
\r
6 // Source file = C:\home\kevin\pub\src\bc100\IAR\NIMHcharge.c /
\r
7 // Command line = C:\home\kevin\pub\src\bc100\IAR\NIMHcharge.c /
\r
8 // --cpu=tiny861 -ms -o C:\home\kevin\pub\src\bc1 /
\r
9 // 00\IAR\Release\Obj\ -D NDEBUG -lCN /
\r
10 // C:\home\kevin\pub\src\bc100\IAR\Release\List\ /
\r
11 // -lB C:\home\kevin\pub\src\bc100\IAR\Release\Li /
\r
12 // st\ --initializers_in_flash -s9 /
\r
13 // --no_cross_call --no_tbaa /
\r
14 // -DENABLE_BIT_DEFINITIONS -e -I "C:\Program /
\r
15 // Files\IAR Systems\Embedded Workbench /
\r
16 // 4.0\avr\INC\" -I "C:\Program Files\IAR /
\r
17 // Systems\Embedded Workbench 4.0\avr\INC\CLIB\" /
\r
18 // --eeprom_size 512 --misrac=5-9,11-12,14,16-17, /
\r
19 // 19-21,24-26,29-32,34-35,38-39,42-43,46,50, /
\r
20 // 52-54,56-59,61-62,64-65,68-80,83-84,87-91, /
\r
21 // 94-95,98-100,103-110,112-126 /
\r
22 // Enabled MISRA C rules = 5-9,11-12,14,16-17,19-21,24-26,29-32,34-35, /
\r
23 // 38-39,42-43,46,50,52-54,56-59,61-62,64-65, /
\r
24 // 68-80,83-84,87-91,94-95,98-100,103-110,112-126 /
\r
25 // Checked = 5,7-9,11-12,14,17,19-21,24,29-32,34-35,38-39, /
\r
26 // 42,46,50,52-54,56-59,61-62,64,68-69,71-80, /
\r
27 // 83-84,87-89,91,94-95,98,100,104-105,108-109, /
\r
28 // 112-115,118-126 /
\r
29 // Not checked = 6,16,25-26,43,65,70,90,99,103,106-107,110, /
\r
31 // List file = C:\home\kevin\pub\src\bc100\IAR\Release\List\N /
\r
35 ///////////////////////////////////////////////////////////////////////////////
\r
39 RSEG CSTACK:DATA:NOROOT(0)
\r
40 RSEG RSTACK:DATA:NOROOT(0)
\r
42 EXTERN ?SS_DIVMOD_L02
\r
43 EXTERN ?US_DIVMOD_L02
\r
54 EXTERN ConstantCurrent
\r
59 EXTERN ChargeParameters
\r
61 EXTERN HaltParameters
\r
63 // C:\home\kevin\pub\src\bc100\IAR\NIMHcharge.c
\r
64 // 1 /* This file has been prepared for Doxygen automatic documentation generation.*/
\r
65 // 2 /*! \file *********************************************************************
\r
68 // 5 * Charge state function for NiMH batteries
\r
70 // 7 * Contains the charge state function, in which the NiMH charging
\r
71 // 8 * algorithm is, plus the associated functions.
\r
73 // 10 * \par Application note:
\r
74 // 11 * AVR463: Charging NiMH Batteries with BC100 \n
\r
76 // 13 * \par Documentation
\r
77 // 14 * For comprehensive code documentation, supported compilers, compiler
\r
78 // 15 * settings and supported devices see readme.html
\r
81 // 18 * Atmel Corporation: http://www.atmel.com \n
\r
82 // 19 * Support email: avr@atmel.com
\r
86 // 23 * $Revision: 2255 $
\r
88 // 25 * $URL: http://svn.norway.atmel.com/AppsAVR8/avr463_Charging_NiMH_Batteries_with_BC100/trunk/code/IAR/NIMHcharge.c $
\r
89 // 26 * $Date: 2007-08-09 14:47:58 +0200 (to, 09 aug 2007) $\n
\r
90 // 27 ******************************************************************************/
\r
92 // 29 #include <ioavr.h>
\r
94 // 31 #include "enums.h"
\r
95 // 32 #include "structs.h"
\r
97 // 34 #include "battery.h"
\r
98 // 35 #include "charge.h"
\r
99 // 36 #include "chargefunc.h"
\r
100 // 37 #include "main.h"
\r
101 // 38 #include "menu.h"
\r
102 // 39 #include "NIMHspecs.h"
\r
103 // 40 #include "PWM.h"
\r
104 // 41 #include "time.h"
\r
107 // 44 #error NIMH not defined in main.h!
\r
108 // 45 #endif // NIMH
\r
111 // 48 //******************************************************************************
\r
113 // 50 //******************************************************************************
\r
114 // 51 /*! \brief Controls the charging.
\r
116 // 53 * This function contains the charging algorithm itself, divided into stages.\n
\r
117 // 54 * For each stage the PWM may be started/stopped, and the timer,
\r
118 // 55 * halt-requirements and charge parameters may be set.\n
\r
119 // 56 * The charging functions return whatever state is next, and as long as no
\r
120 // 57 * errors occur this is the next charging stage.
\r
122 // 59 * \note If more stages are needed simply define more states in menu.h, include
\r
123 // 60 * them in \ref menu_state[] in menu.c, then add the cases to this function.
\r
125 // 62 * \note This algorithm is for NiMH batteries.
\r
128 RSEG CODE:CODE:NOROOT(1)
\r
129 // 64 unsigned char Charge(unsigned char inp)
\r
132 // 66 unsigned char NextState;
\r
134 // 68 switch (CurrentState) {
\r
135 LDS R16, CurrentState
\r
147 // 69 // First stage is a prequalification. Attempt to charge battery to 1 V,
\r
148 // 70 // using a 0.1 C current, within 2 minutes.
\r
149 // 71 // If this fails, the battery is likely damaged.
\r
150 // 72 // If it succeeds, start a fast charge.
\r
151 // 73 case ST_PREQUAL:
\r
153 // 75 // Set up charge current and next state.
\r
154 // 76 ChargeParameters.Current = BattData.Capacity / 10;
\r
156 LDI R30, LOW(BattData)
\r
157 LDI R31, (BattData) >> 8
\r
162 RCALL ?US_DIVMOD_L02
\r
163 LDI R30, LOW(ChargeParameters)
\r
164 LDI R31, (ChargeParameters) >> 8
\r
167 // 77 ChargeParameters.NextState = ST_FASTCHARGE;
\r
171 // 79 // Halt charge on voltage limit or timeout.
\r
172 // 80 // Timeout means battery exhaustion.
\r
173 // 81 HaltParameters.HaltFlags = (HALT_VOLTAGE_MAX | HALT_TIME |
\r
174 // 82 HALT_FLAG_EXHAUSTION);
\r
175 LDI R30, LOW(HaltParameters)
\r
176 LDI R31, (HaltParameters) >> 8
\r
179 // 84 // Set up voltage limit and temperature limits.
\r
180 // 85 HaltParameters.VoltageMax = BAT_VOLTAGE_PREQUAL;
\r
185 // 86 HaltParameters.TemperatureMin = BAT_TEMPERATURE_MIN;
\r
190 // 87 HaltParameters.TemperatureMax = 35;
\r
195 // 89 // Reset temperature measurement for HaltNow().
\r
196 // 90 HaltParameters.LastNTC = 0;
\r
200 // 92 // Start PWM and charge timer before calling the charge function.
\r
203 // 94 Time_Set(TIMER_CHG, BAT_TIME_PREQUAL, 0, 0);
\r
209 // 96 // Call charge function, get next state.
\r
210 // 97 NextState = ConstantCurrent();
\r
214 // 101 // Second stage is a fast charge. Charge at 1.0 C for at most 1.5 hours,
\r
215 // 102 // until either rate of temperature increase or voltage reaches limit, or
\r
216 // 103 // the voltage drops sufficiently.
\r
217 // 104 // Timeout doesn't mean battery exhaustion now.
\r
218 // 105 case ST_FASTCHARGE:
\r
220 // 107 // Set up charge current and next state.
\r
221 // 108 ChargeParameters.Current = BattData.Capacity;
\r
223 LDI R18, LOW(BattData)
\r
224 LDI R19, (BattData) >> 8
\r
225 MOVW R31:R30, R19:R18
\r
228 LDI R30, LOW(ChargeParameters)
\r
229 LDI R31, (ChargeParameters) >> 8
\r
232 // 109 ChargeParameters.NextState = ST_LOWRATECHARGE;
\r
236 // 111 // Halt charge on voltage limit, timeout, voltage drop or rate of
\r
237 // 112 // temperature increase.
\r
238 // 113 HaltParameters.HaltFlags = (HALT_VOLTAGE_MAX | HALT_TIME |
\r
239 // 114 HALT_VOLTAGE_DROP | HALT_TEMPERATURE_RISE);
\r
240 LDI R30, LOW(HaltParameters)
\r
241 LDI R31, (HaltParameters) >> 8
\r
245 // 116 // Set up limits for voltage, voltage drop, temperature and rate of
\r
246 // 117 // temperature increase (1 degree C per minute).
\r
247 // 118 HaltParameters.VoltageMax = BAT_VOLTAGE_MAX;
\r
252 // 119 HaltParameters.VoltageDrop = BAT_VOLTAGE_DROP;
\r
257 // 120 HaltParameters.TemperatureMax = BAT_TEMPERATURE_MAX;
\r
261 // 121 HaltParameters.TemperatureRise = 1;
\r
266 // 123 // Reset maximum voltage measurement for HaltNow().
\r
267 // 124 HaltParameters.VBATMax = 0;
\r
271 // 126 // Start timer, PWM should still be running.
\r
272 // 127 Time_Set(TIMER_CHG, BattData.MaxTime, 0, 0);
\r
274 MOVW R31:R30, R19:R18
\r
279 // 129 // Call charge function, get next state.
\r
280 // 130 NextState = ConstantCurrent();
\r
284 // 134 // Last stage is a trickle charge. Charge at 0.1 C for at most 30 minutes,
\r
285 // 135 // until either rate of temperature increase or voltage reaches limit.
\r
286 // 136 case ST_LOWRATECHARGE:
\r
288 // 138 // Set up charge current and next state.
\r
289 // 139 ChargeParameters.Current = BattData.Capacity / 10;
\r
291 LDI R30, LOW(BattData)
\r
292 LDI R31, (BattData) >> 8
\r
297 RCALL ?US_DIVMOD_L02
\r
298 LDI R30, LOW(ChargeParameters)
\r
299 LDI R31, (ChargeParameters) >> 8
\r
302 // 140 ChargeParameters.NextState = ST_ENDCHARGE;
\r
306 // 142 // Halt charge on voltage limit, timeout or temperature rise.
\r
307 // 143 // Use the same requirements as during the last stage (ST_FASTCHARGE).
\r
308 // 144 HaltParameters.HaltFlags = (HALT_VOLTAGE_MAX | HALT_TIME |
\r
309 // 145 HALT_TEMPERATURE_RISE);
\r
311 STS HaltParameters, R16
\r
313 // 147 // Start timer, 30 minutes.
\r
314 // 148 Time_Set(TIMER_CHG, 30, 0, 0);
\r
324 // 150 // Call charge function, get next state.
\r
325 // 151 NextState = ConstantCurrent();
\r
326 RJMP ConstantCurrent
\r
330 // 155 // Charging is done!
\r
331 // 156 case ST_ENDCHARGE:
\r
333 // 158 // Stop the PWM output and flag battery as charged.
\r
337 // 160 BattData.Charged = TRUE;
\r
338 LDI R30, LOW(BattData)
\r
339 LDI R31, (BattData) >> 8
\r
344 // 162 // If the other battery is enabled go to ST_BATCON, otherwise
\r
345 // 163 // go to ST_SLEEP.
\r
346 // 164 if (BattControl[(BattActive+1)%2].Enabled) {
\r
347 LDS R16, BattActive
\r
353 RCALL ?SS_DIVMOD_L02
\r
354 LDI R18, LOW(BattControl)
\r
355 LDI R19, (BattControl) >> 8
\r
358 MOVW R21:R20, R19:R18
\r
362 // 165 NextState = ST_BATCON;
\r
366 // 167 NextState = ST_SLEEP;
\r
374 // 172 default: // Shouldn't end up here. Reinitialize for safety.
\r
375 // 173 NextState = ST_INIT;
\r
381 // 177 // Return the next state to main().
\r
382 // 178 return(NextState);
\r
386 ASEGN ABSOLUTE:DATA:NOROOT,01cH
\r
389 ASEGN ABSOLUTE:DATA:NOROOT,01dH
\r
392 ASEGN ABSOLUTE:DATA:NOROOT,01eH
\r
395 ASEGN ABSOLUTE:DATA:NOROOT,01fH
\r
400 // 268 bytes in segment CODE
\r
402 // 268 bytes of CODE memory
\r