1
1
from enum import Enum
2
+ import logging
3
+ import os
2
4
import threading
3
5
import time
4
6
5
7
import smbus2
6
8
7
9
from riberry .battery .common import majority_vote
8
10
11
+ # Set up logging
12
+ LOG_LEVEL = os .getenv ('LOG_LEVEL' , 'INFO' ).upper ()
13
+ logging .basicConfig (level = LOG_LEVEL )
14
+ logger = logging .getLogger (__name__ )
9
15
10
16
class ChargeState (Enum ):
11
17
NO_CHARGE = 0
@@ -60,7 +66,7 @@ def print_status_and_fault_register(value):
60
66
continue
61
67
if (value >> bit ) & 1 :
62
68
msg = f"Bit { bit } : { descriptions .get (bit , 'Unknown' )} "
63
- print (msg )
69
+ logger . info (msg )
64
70
status_and_fault_list .append (msg )
65
71
if len (status_and_fault_list ) == 0 :
66
72
return "All green."
@@ -98,29 +104,29 @@ def __init__(
98
104
99
105
self .bus = smbus2 .SMBus (self .bus_number )
100
106
while self .disable_ntc_protection () is None :
101
- print ("[MP2760BatteryMonitor] Try to disable NTC protection." )
107
+ logger . warning ("[MP2760BatteryMonitor] Try to disable NTC protection." )
102
108
time .sleep (1.0 )
103
109
while self .set_adc_continuous_mode (set_bit = True ) is None :
104
- print ("[MP2760BatteryMonitor] Try to enable adc continuous mode." )
110
+ logger . warning ("[MP2760BatteryMonitor] Try to enable adc continuous mode." )
105
111
time .sleep (1.0 )
106
112
while self .set_safety_timer (set_bit = True ) is None :
107
- print ("[MP2760BatteryMonitor] Try to enable safety timer." )
113
+ logger . warning ("[MP2760BatteryMonitor] Try to enable safety timer." )
108
114
time .sleep (1.0 )
109
115
self .limit_charge_current (400 )
110
- print (
116
+ logger . info (
111
117
"[MP2760BatteryMonitor] Charge current limit: " ,
112
118
f"{ self .read_charge_current_limit ()} [mA]" ,
113
119
)
114
120
self .limit_input_current (500 )
115
- print (
121
+ logger . info (
116
122
"[MP2760BatteryMonitor] Input current limit: " ,
117
123
f"{ self .read_input_current_limit ()} [mA]" ,
118
124
)
119
125
self .lock = threading .Lock ()
120
126
self .running = True
121
127
122
128
def __del__ (self ):
123
- print ("[MP2760BatteryMonitor] Object is being deleted, cleaning up..." )
129
+ logger . info ("[MP2760BatteryMonitor] Object is being deleted, cleaning up..." )
124
130
self .stop ()
125
131
self .set_adc_continuous_mode (False )
126
132
self .bus .close ()
@@ -130,10 +136,10 @@ def exists(self, bus_number=3, device_address=0x5C):
130
136
try :
131
137
with smbus2 .SMBus (bus_number ) as bus :
132
138
bus .read_byte (device_address )
133
- print ("[MP2760BatteryMonitor] found." )
139
+ logger . info ("[MP2760BatteryMonitor] found." )
134
140
return True
135
141
except OSError as e :
136
- print (f"[MP2760BatteryMonitor] { e } . Device not found" )
142
+ logger . error (f"[MP2760BatteryMonitor] { e } . Device not found" )
137
143
return False
138
144
139
145
def is_outlier (self , current , history , threshold ):
@@ -151,66 +157,66 @@ def set_adc_continuous_mode(self, set_bit=True):
151
157
try :
152
158
word = self .bus .read_word_data (self .device_address , 0x0E )
153
159
except Exception as e :
154
- print (f"[Battery Monitor] Error reading from I2C: { e } " )
160
+ logger . error (f"[Battery Monitor] Error reading from I2C: { e } " )
155
161
return
156
162
current_bit = (word >> 7 ) & 1
157
163
if current_bit == set_bit :
158
- print (
159
- "[Battery Monitor] 7bit is already set to the desired value. " ,
160
- "No action needed." ,
164
+ logger . info (
165
+ "[Battery Monitor] 7bit is already set to the desired value. "
166
+ + "No action needed."
161
167
)
162
168
return True
163
169
if set_bit :
164
- print ("[Battery Monitor] Set ADC_CONV to Continuous" )
170
+ logger . info ("[Battery Monitor] Set ADC_CONV to Continuous" )
165
171
set_adc_word = word | (1 << 7 )
166
172
else :
167
- print ("[Battery Monitor] Set ADC_CONV to One-shot conversion" )
173
+ logger . info ("[Battery Monitor] Set ADC_CONV to One-shot conversion" )
168
174
set_adc_word = word & ~ (1 << 7 )
169
175
try :
170
176
self .bus .write_word_data (self .device_address , 0x0E , set_adc_word )
171
177
except Exception as e :
172
- print (f"[Battery Monitor] Error writing I2C: { e } " )
178
+ logger . error (f"[Battery Monitor] Error writing I2C: { e } " )
173
179
return
174
180
return True
175
181
176
182
def disable_ntc_protection (self ):
177
183
try :
178
184
word = self .bus .read_word_data (self .device_address , 0x0D )
179
185
except Exception as e :
180
- print (f"[Battery Monitor] Error reading from I2C: { e } " )
186
+ logger . error (f"[Battery Monitor] Error reading from I2C: { e } " )
181
187
return
182
188
current_bit = (word >> 9 ) & 1
183
189
if current_bit == 0 :
184
- print (
185
- "[Battery Monitor] 9bit is already set to the desired value. " ,
186
- "No action needed." ,
190
+ logger . info (
191
+ "[Battery Monitor] 9bit is already set to the desired value. "
192
+ + "No action needed."
187
193
)
188
194
return True
189
- print ("[Battery Monitor] Disable NTC protection" )
195
+ logger . info ("[Battery Monitor] Disable NTC protection" )
190
196
set_word = word & ~ (1 << 9 )
191
197
try :
192
198
self .bus .write_word_data (self .device_address , 0x0D , set_word )
193
199
except Exception as e :
194
- print (f"[Battery Monitor] Error writing I2C: { e } " )
200
+ logger . error (f"[Battery Monitor] Error writing I2C: { e } " )
195
201
return
196
202
return True
197
203
198
204
def set_safety_timer (self , set_bit = True ):
199
205
try :
200
206
word = self .bus .read_word_data (self .device_address , 0x12 )
201
207
except Exception as e :
202
- print (f"[Battery Monitor] Error reading from I2C: { e } " )
208
+ logger . error (f"[Battery Monitor] Error reading from I2C: { e } " )
203
209
return
204
210
if set_bit is True :
205
- print ("[Battery Monitor] sefety timer is enabled." )
211
+ logger . info ("[Battery Monitor] Safety timer is enabled." )
206
212
set_word = word | (1 << 13 )
207
213
else :
208
- print ("[Battery Monitor] sefety timer is disabled." )
214
+ logger . info ("[Battery Monitor] Safety timer is disabled." )
209
215
set_word = word & ~ (1 << 13 )
210
216
try :
211
217
self .bus .write_word_data (self .device_address , 0x12 , set_word )
212
218
except Exception as e :
213
- print (f"[Battery Monitor] Error writing I2C: { e } " )
219
+ logger . error (f"[Battery Monitor] Error writing I2C: { e } " )
214
220
return
215
221
return True
216
222
@@ -224,7 +230,7 @@ def limit_charge_current(self, set_current): # unit: [mA]
224
230
or set_current < 50
225
231
or set_current > 6000
226
232
):
227
- print ("[Battery Monitor] Charge current limit is not proper." )
233
+ logger . error ("[Battery Monitor] Charge current limit is not proper." )
228
234
return
229
235
for digit , current in zip (digits , currents ):
230
236
bit = set_current // current
@@ -233,7 +239,7 @@ def limit_charge_current(self, set_current): # unit: [mA]
233
239
try :
234
240
self .bus .write_word_data (self .device_address , 0x14 , set_word )
235
241
except Exception as e :
236
- print (f"[Battery Monitor] Error writing I2C: { e } " )
242
+ logger . error (f"[Battery Monitor] Error writing I2C: { e } " )
237
243
return
238
244
return True
239
245
@@ -247,7 +253,7 @@ def limit_input_current(self, set_current): # unit: [mA]
247
253
or set_current < 50
248
254
or set_current > 5000
249
255
):
250
- print ("[Battery Monitor] Input current limit is not proper." )
256
+ logger . error ("[Battery Monitor] Input current limit is not proper." )
251
257
return
252
258
for digit , current in zip (digits , currents ):
253
259
bit = set_current // current
@@ -256,24 +262,24 @@ def limit_input_current(self, set_current): # unit: [mA]
256
262
try :
257
263
self .bus .write_word_data (self .device_address , 0x08 , set_word )
258
264
except Exception as e :
259
- print (f"[Battery Monitor] Error writing I2C: { e } " )
265
+ logger . error (f"[Battery Monitor] Error writing I2C: { e } " )
260
266
return
261
267
return True
262
268
263
269
def write_default_value_to_0x10_register (self ):
264
270
try :
265
271
self .bus .write_word_data (self .device_address , 0x10 , 0x0A74 )
266
- print ("[Battery Monitor] Successfully wrote 0x0A74 to register 0x10." )
272
+ logger . info ("[Battery Monitor] Successfully wrote 0x0A74 to register 0x10." )
267
273
return True
268
274
except Exception as e :
269
- print (f"[Battery Monitor] Error writing to register 0x10: { e } " )
275
+ logger . error (f"[Battery Monitor] Error writing to register 0x10: { e } " )
270
276
return False
271
277
272
278
def read_charge_current_limit (self ): # unit: [mA]
273
279
try :
274
280
bits = self .bus .read_word_data (self .device_address , 0x14 )
275
281
except Exception as e :
276
- print (f"[Battery Monitor] Error reading from I2C: { e } " )
282
+ logger . error (f"[Battery Monitor] Error reading from I2C: { e } " )
277
283
return
278
284
current = 0
279
285
current += ((bits & 0x2000 ) >> 13 ) * 6400
@@ -290,7 +296,7 @@ def read_input_current_limit(self): # unit: [mA]
290
296
try :
291
297
bits = self .bus .read_word_data (self .device_address , 0x08 )
292
298
except Exception as e :
293
- print (f"[Battery Monitor] Error reading from I2C: { e } " )
299
+ logger . error (f"[Battery Monitor] Error reading from I2C: { e } " )
294
300
return
295
301
current = 0
296
302
current += ((bits & 0x0040 ) >> 6 ) * 3200
@@ -317,7 +323,7 @@ def read_register(self, register):
317
323
try :
318
324
value = self .bus .read_word_data (self .device_address , register )
319
325
except Exception as e :
320
- print (f"[Battery Monitor] { e } " )
326
+ logger . error (f"[Battery Monitor] { e } " )
321
327
return None
322
328
return value
323
329
@@ -500,25 +506,24 @@ def run(self):
500
506
self .battery_charge_current ,
501
507
) = self .read_sensor_data ()
502
508
if self .input_voltage :
503
- print (f"Input Voltage: { self .input_voltage :.2f} V" )
509
+ logger . info (f"Input Voltage: { self .input_voltage :.2f} V" )
504
510
if self .system_voltage :
505
- print ( "System Voltage: " f" { self .system_voltage :.2f} V" )
511
+ logger . info ( f "System Voltage: { self .system_voltage :.2f} V" )
506
512
if self .battery_voltage :
507
- print ( "Battery Voltage: " f" { self .battery_voltage :.2f} V" )
508
- print ( "Battery charge Current: " f" { self .battery_charge_current :.2f} mA" )
513
+ logger . info ( f "Battery Voltage: { self .battery_voltage :.2f} V" )
514
+ logger . info ( f "Battery charge Current: { self .battery_charge_current :.2f} mA" )
509
515
if self .junction_temperature :
510
- print ( "Junction Temperature: " f" { self .junction_temperature :.2f} " )
516
+ logger . info ( f "Junction Temperature: { self .junction_temperature :.2f} " )
511
517
if percentage is None or is_charging is None :
512
518
time .sleep (0.2 )
513
519
continue
514
520
with self .lock :
515
521
if self .is_outlier (
516
522
percentage , self .percentage_history , self .percentage_threshold
517
523
):
518
- print (
519
- "Percentage outlier detected:" ,
520
- f" { percentage :.2f} , " ,
521
- f"history: { self .percentage_history } " ,
524
+ logger .warning (
525
+ f"Percentage outlier detected: { percentage :.2f} , "
526
+ + f"history: { self .percentage_history } "
522
527
)
523
528
else :
524
529
self .filtered_percentage = (
@@ -533,9 +538,9 @@ def run(self):
533
538
self .charging_history .pop (0 )
534
539
535
540
if self .debug :
536
- print (f"RAW Percentage: { percentage :.2f} " )
537
- print ( "Filtered Percentage:" , f" { self .filtered_percentage :.2f} " )
538
- print (f"Charge Status: { self .charge_status } " )
541
+ logger . debug (f"RAW Percentage: { percentage :.2f} " )
542
+ logger . debug ( f "Filtered Percentage: { self .filtered_percentage :.2f} " )
543
+ logger . debug (f"Charge Status: { self .charge_status } " )
539
544
time .sleep (0.2 )
540
545
finally :
541
546
self .bus .close ()
0 commit comments