@@ -21,9 +21,12 @@ struct composite_config {
21
21
enum battery_chemistry chemistry ;
22
22
};
23
23
24
- static int composite_read_micro (const struct device * dev , enum sensor_channel chan , int * val )
24
+ struct composite_data {
25
+ k_ticks_t next_reading ;
26
+ };
27
+
28
+ static int composite_fetch (const struct device * dev )
25
29
{
26
- struct sensor_value sensor_val ;
27
30
int rc ;
28
31
29
32
rc = pm_device_runtime_get (dev );
@@ -34,23 +37,41 @@ static int composite_read_micro(const struct device *dev, enum sensor_channel ch
34
37
if (rc < 0 ) {
35
38
return rc ;
36
39
}
37
- rc = sensor_channel_get (dev , chan , & sensor_val );
38
- if (rc < 0 ) {
39
- return rc ;
40
- }
41
- rc = pm_device_runtime_put (dev );
42
- if (rc < 0 ) {
43
- return rc ;
44
- }
45
- * val = sensor_value_to_micro (& sensor_val );
46
- return 0 ;
40
+ return pm_device_runtime_put (dev );
47
41
}
48
42
49
43
static int composite_get_prop (const struct device * dev , fuel_gauge_prop_t prop ,
50
44
union fuel_gauge_prop_val * val )
51
45
{
52
46
const struct composite_config * config = dev -> config ;
53
- int voltage , rc = 0 ;
47
+ struct composite_data * data = dev -> data ;
48
+ k_ticks_t now = k_uptime_ticks ();
49
+ struct sensor_value sensor_val ;
50
+ int64_t voltage ;
51
+ int rc = 0 ;
52
+
53
+ /* Validate at build time that equivalent channel output fields still match */
54
+ BUILD_ASSERT (sizeof (val -> absolute_state_of_charge ) ==
55
+ sizeof (val -> relative_state_of_charge ));
56
+ BUILD_ASSERT (offsetof(union fuel_gauge_prop_val , absolute_state_of_charge ) ==
57
+ offsetof(union fuel_gauge_prop_val , relative_state_of_charge ));
58
+ BUILD_ASSERT (sizeof (val -> current ) == sizeof (val -> avg_current ));
59
+ BUILD_ASSERT (offsetof(union fuel_gauge_prop_val , current ) ==
60
+ offsetof(union fuel_gauge_prop_val , avg_current ));
61
+
62
+ if (now >= data -> next_reading ) {
63
+ /* Trigger a sample on the input devices */
64
+ rc = composite_fetch (config -> battery_voltage );
65
+ if ((rc == 0 ) && config -> battery_current ) {
66
+ rc = composite_fetch (config -> battery_current );
67
+ }
68
+ if (rc != 0 ) {
69
+ return rc ;
70
+ }
71
+ /* Update timestamp for next reading */
72
+ data -> next_reading =
73
+ now + k_ms_to_ticks_near64 (CONFIG_FUEL_GAUGE_COMPOSITE_DATA_VALIDITY_MS );
74
+ }
54
75
55
76
switch (prop ) {
56
77
case FUEL_GAUGE_FULL_CHARGE_CAPACITY :
@@ -66,30 +87,36 @@ static int composite_get_prop(const struct device *dev, fuel_gauge_prop_t prop,
66
87
val -> full_charge_capacity = config -> charge_capacity_microamp_hours / 1000 ;
67
88
break ;
68
89
case FUEL_GAUGE_VOLTAGE :
69
- rc = composite_read_micro (config -> battery_voltage , SENSOR_CHAN_VOLTAGE ,
70
- & val -> voltage );
90
+ rc = sensor_channel_get (config -> battery_voltage , SENSOR_CHAN_VOLTAGE , & sensor_val );
91
+ val -> voltage = sensor_value_to_micro ( & sensor_val );
71
92
break ;
72
93
case FUEL_GAUGE_ABSOLUTE_STATE_OF_CHARGE :
73
94
case FUEL_GAUGE_RELATIVE_STATE_OF_CHARGE :
74
95
if (config -> ocv_lookup_table [0 ] == -1 ) {
75
96
return - ENOTSUP ;
76
97
}
77
- rc = composite_read_micro (config -> battery_voltage , SENSOR_CHAN_VOLTAGE , & voltage );
78
- val -> relative_state_of_charge =
79
- battery_soc_lookup (config -> ocv_lookup_table , voltage ) / 1000 ;
98
+ /* Fetch the voltage from the sensor */
99
+ rc = sensor_channel_get (config -> battery_voltage , SENSOR_CHAN_VOLTAGE , & sensor_val );
100
+ voltage = sensor_value_to_micro (& sensor_val );
101
+ if (rc == 0 ) {
102
+ /* Convert voltage to state of charge */
103
+ val -> relative_state_of_charge =
104
+ battery_soc_lookup (config -> ocv_lookup_table , voltage ) / 1000 ;
105
+ }
80
106
break ;
81
107
case FUEL_GAUGE_CURRENT :
108
+ case FUEL_GAUGE_AVG_CURRENT :
82
109
if (config -> battery_current == NULL ) {
83
110
return - ENOTSUP ;
84
111
}
85
- rc = composite_read_micro (config -> battery_current , SENSOR_CHAN_CURRENT ,
86
- & val -> current );
112
+ rc = sensor_channel_get (config -> battery_current , SENSOR_CHAN_CURRENT , & sensor_val );
113
+ val -> current = sensor_value_to_micro ( & sensor_val );
87
114
break ;
88
115
default :
89
116
return - ENOTSUP ;
90
117
}
91
118
92
- return 0 ;
119
+ return rc ;
93
120
}
94
121
95
122
static DEVICE_API (fuel_gauge , composite_api ) = {
@@ -106,7 +133,9 @@ static DEVICE_API(fuel_gauge, composite_api) = {
106
133
DT_INST_PROP_OR(inst, charge_full_design_microamp_hours, 0), \
107
134
.chemistry = BATTERY_CHEMISTRY_DT_GET(inst), \
108
135
}; \
109
- DEVICE_DT_INST_DEFINE(inst, NULL, NULL, NULL, &composite_##inst##_config, POST_KERNEL, \
136
+ static struct composite_data composite_##inst##_data; \
137
+ DEVICE_DT_INST_DEFINE(inst, NULL, NULL, &composite_##inst##_data, \
138
+ &composite_##inst##_config, POST_KERNEL, \
110
139
CONFIG_SENSOR_INIT_PRIORITY, &composite_api);
111
140
112
141
DT_INST_FOREACH_STATUS_OKAY (COMPOSITE_INIT )
0 commit comments