fuel_gauge: Add fuel_guage_set_props()

The fuel_gauge_set_prop() function prototype declares a function that sets
multiple fuel gauge properties at once. The naming suggests it ought to
fetch a singular property at a time. Moreso, some clients may just want to
set properties one at a time and may feel uncomfortable using a prototype
for fetching multiple properties when wanting to fetch them one at a time.

Modify fuel_gauge_set_prop() to fetch a single property and add
fuel_gauge_set_props() to support fetching multiple properties. Modify
existing tests/drivers/samples.

This is part of #61818 work.

Signed-off-by: Aaron Massey <aaronmassey@google.com>
This commit is contained in:
Aaron Massey 2023-09-20 16:16:41 -06:00 committed by Carles Cufí
commit bddd88955d
5 changed files with 84 additions and 54 deletions

View file

@ -260,22 +260,6 @@ static int bq27z746_set_prop(const struct device *dev, struct fuel_gauge_propert
return rc; return rc;
} }
static int bq27z746_set_props(const struct device *dev, struct fuel_gauge_property *props,
size_t len)
{
int err_count = 0;
for (int i = 0; i < len; i++) {
int ret = bq27z746_set_prop(dev, props + i);
err_count += ret ? 1 : 0;
}
err_count = (err_count == len) ? -1 : err_count;
return err_count;
}
static int bq27z746_init(const struct device *dev) static int bq27z746_init(const struct device *dev)
{ {
const struct bq27z746_config *cfg; const struct bq27z746_config *cfg;
@ -292,7 +276,7 @@ static int bq27z746_init(const struct device *dev)
static const struct fuel_gauge_driver_api bq27z746_driver_api = { static const struct fuel_gauge_driver_api bq27z746_driver_api = {
.get_property = &bq27z746_get_prop, .get_property = &bq27z746_get_prop,
.set_property = &bq27z746_set_props, .set_property = &bq27z746_set_prop,
.get_buffer_property = &bq27z746_get_buffer_prop, .get_buffer_property = &bq27z746_get_buffer_prop,
}; };

View file

@ -45,24 +45,40 @@ static inline int z_vrfy_fuel_gauge_get_props(const struct device *dev,
#include <syscalls/fuel_gauge_get_props_mrsh.c> #include <syscalls/fuel_gauge_get_props_mrsh.c>
static inline int z_vrfy_fuel_gauge_set_prop(const struct device *dev, static inline int z_vrfy_fuel_gauge_set_prop(const struct device *dev,
struct fuel_gauge_property *props, struct fuel_gauge_property *prop)
size_t props_len) {
struct fuel_gauge_property k_prop;
Z_OOPS(Z_SYSCALL_DRIVER_FUEL_GAUGE(dev, set_property));
Z_OOPS(z_user_from_copy(&k_prop, prop, sizeof(struct fuel_gauge_property)));
int ret = z_impl_fuel_gauge_set_prop(dev, &k_prop);
Z_OOPS(z_user_to_copy(prop, &k_prop, sizeof(struct fuel_gauge_property)));
return ret;
}
#include <syscalls/fuel_gauge_set_prop_mrsh.c>
static inline int z_vrfy_fuel_gauge_set_props(const struct device *dev,
struct fuel_gauge_property *props, size_t props_len)
{ {
struct fuel_gauge_property k_props[props_len]; struct fuel_gauge_property k_props[props_len];
Z_OOPS(Z_SYSCALL_DRIVER_FUEL_GAUGE(dev, set_property)); Z_OOPS(Z_SYSCALL_DRIVER_FUEL_GAUGE(dev, set_property));
Z_OOPS(z_user_from_copy(k_props, props, Z_OOPS(z_user_from_copy(k_props, props, props_len * sizeof(struct fuel_gauge_property)));
props_len * sizeof(struct fuel_gauge_property)));
int ret = z_impl_fuel_gauge_set_prop(dev, k_props, props_len); int ret = z_impl_fuel_gauge_set_props(dev, k_props, props_len);
Z_OOPS(z_user_to_copy(props, k_props, props_len * sizeof(struct fuel_gauge_property))); Z_OOPS(z_user_to_copy(props, k_props, props_len * sizeof(struct fuel_gauge_property)));
return ret; return ret;
} }
#include <syscalls/fuel_gauge_set_prop_mrsh.c> #include <syscalls/fuel_gauge_set_props_mrsh.c>
static inline int z_vrfy_fuel_gauge_get_buffer_prop(const struct device *dev, static inline int z_vrfy_fuel_gauge_get_buffer_prop(const struct device *dev,
struct fuel_gauge_buffer_property *prop, struct fuel_gauge_buffer_property *prop,

View file

@ -274,22 +274,6 @@ static int sbs_gauge_get_buffer_prop(const struct device *dev,
return rc; return rc;
} }
static int sbs_gauge_set_props(const struct device *dev, struct fuel_gauge_property *props,
size_t len)
{
int err_count = 0;
for (int i = 0; i < len; i++) {
int ret = sbs_gauge_set_prop(dev, props + i);
err_count += ret ? 1 : 0;
}
err_count = (err_count == len) ? -1 : err_count;
return err_count;
}
/** /**
* @brief initialize the fuel gauge * @brief initialize the fuel gauge
* *
@ -311,7 +295,7 @@ static int sbs_gauge_init(const struct device *dev)
static const struct fuel_gauge_driver_api sbs_gauge_driver_api = { static const struct fuel_gauge_driver_api sbs_gauge_driver_api = {
.get_property = &sbs_gauge_get_prop, .get_property = &sbs_gauge_get_prop,
.set_property = &sbs_gauge_set_props, .set_property = &sbs_gauge_set_prop,
.get_buffer_property = &sbs_gauge_get_buffer_prop, .get_buffer_property = &sbs_gauge_get_buffer_prop,
.battery_cutoff = &sbs_gauge_do_battery_cutoff, .battery_cutoff = &sbs_gauge_do_battery_cutoff,
}; };

View file

@ -231,7 +231,7 @@ typedef int (*fuel_gauge_get_property_t)(const struct device *dev,
* See fuel_gauge_set_property() for argument description * See fuel_gauge_set_property() for argument description
*/ */
typedef int (*fuel_gauge_set_property_t)(const struct device *dev, typedef int (*fuel_gauge_set_property_t)(const struct device *dev,
struct fuel_gauge_property *props, size_t props_len); struct fuel_gauge_property *prop);
/** /**
* @typedef fuel_gauge_get_buffer_property_t * @typedef fuel_gauge_get_buffer_property_t
@ -325,6 +325,30 @@ static inline int z_impl_fuel_gauge_get_props(const struct device *dev,
return err_count; return err_count;
} }
/**
* @brief Set a battery fuel-gauge property
*
* @param dev Pointer to the battery fuel-gauge device
* @param prop pointer to fuel_gauge_property struct where the property struct
* field is set by the caller to determine what property is written to the fuel gauge device from
* the fuel_gauge_property struct's value field.
*
* @return 0 if successful, negative errno code if failure.
*/
__syscall int fuel_gauge_set_prop(const struct device *dev, struct fuel_gauge_property *prop);
static inline int z_impl_fuel_gauge_set_prop(const struct device *dev,
struct fuel_gauge_property *prop)
{
const struct fuel_gauge_driver_api *api = dev->api;
if (api->set_property == NULL) {
return -ENOSYS;
}
return api->set_property(dev, prop);
}
/** /**
* @brief Set a battery fuel-gauge property * @brief Set a battery fuel-gauge property
* *
@ -337,20 +361,23 @@ static inline int z_impl_fuel_gauge_get_props(const struct device *dev,
* @return return=0 if successful, return < 0 if setting all properties failed, return > 0 if some * @return return=0 if successful, return < 0 if setting all properties failed, return > 0 if some
* properties failed where return=number of failing properties. * properties failed where return=number of failing properties.
*/ */
__syscall int fuel_gauge_set_prop(const struct device *dev, struct fuel_gauge_property *props, __syscall int fuel_gauge_set_props(const struct device *dev, struct fuel_gauge_property *props,
size_t props_len); size_t props_len);
static inline int z_impl_fuel_gauge_set_prop(const struct device *dev, static inline int z_impl_fuel_gauge_set_props(const struct device *dev,
struct fuel_gauge_property *props, struct fuel_gauge_property *props, size_t props_len)
size_t props_len)
{ {
const struct fuel_gauge_driver_api *api = (const struct fuel_gauge_driver_api *)dev->api; int err_count = 0;
if (api->set_property == NULL) { for (int i = 0; i < props_len; i++) {
return -ENOSYS; int ret = fuel_gauge_set_prop(dev, props + i);
err_count += ret ? 1 : 0;
} }
return api->set_property(dev, props, props_len); err_count = (err_count == props_len) ? -1 : err_count;
return err_count;
} }
/** /**

View file

@ -90,7 +90,7 @@ ZTEST_USER_F(sbs_gauge_new_api, test_set_all_props_failed_returns_negative)
}, },
}; };
int ret = fuel_gauge_set_prop(fixture->dev, props, ARRAY_SIZE(props)); int ret = fuel_gauge_set_props(fixture->dev, props, ARRAY_SIZE(props));
zassert_equal(props[0].status, -ENOTSUP, "Setting bad property %d has a good status.", zassert_equal(props[0].status, -ENOTSUP, "Setting bad property %d has a good status.",
props[0].property_type); props[0].property_type);
@ -118,7 +118,7 @@ ZTEST_USER_F(sbs_gauge_new_api, test_set_some_props_failed_returns_failed_prop_c
}; };
int ret = fuel_gauge_set_prop(fixture->dev, props, ARRAY_SIZE(props)); int ret = fuel_gauge_set_props(fixture->dev, props, ARRAY_SIZE(props));
zassert_equal(props[0].status, -ENOTSUP, "Setting bad property %d has a good status.", zassert_equal(props[0].status, -ENOTSUP, "Setting bad property %d has a good status.",
props[0].property_type); props[0].property_type);
@ -178,7 +178,7 @@ ZTEST_USER_F(sbs_gauge_new_api, test_set_prop_can_be_get)
}, },
}; };
zassert_ok(fuel_gauge_set_prop(fixture->dev, set_props, ARRAY_SIZE(set_props))); zassert_ok(fuel_gauge_set_props(fixture->dev, set_props, ARRAY_SIZE(set_props)));
for (int i = 0; i < ARRAY_SIZE(set_props); i++) { for (int i = 0; i < ARRAY_SIZE(set_props); i++) {
zassert_ok(set_props[i].status, "Property %d writing %d has a bad status.", i, zassert_ok(set_props[i].status, "Property %d writing %d has a bad status.", i,
set_props[i].property_type); set_props[i].property_type);
@ -308,7 +308,7 @@ ZTEST_USER_F(sbs_gauge_new_api, test_set_props__returns_ok)
}, },
}; };
int ret = fuel_gauge_set_prop(fixture->dev, props, ARRAY_SIZE(props)); int ret = fuel_gauge_set_props(fixture->dev, props, ARRAY_SIZE(props));
for (int i = 0; i < ARRAY_SIZE(props); i++) { for (int i = 0; i < ARRAY_SIZE(props); i++) {
zassert_ok(props[i].status, "Property %d writing %d has a bad status.", i, zassert_ok(props[i].status, "Property %d writing %d has a bad status.", i,
@ -371,4 +371,23 @@ ZTEST_USER_F(sbs_gauge_new_api, test_charging_5v_3a)
current.value.current, expected_uA); current.value.current, expected_uA);
} }
ZTEST_USER_F(sbs_gauge_new_api, test_set_get_single_prop)
{
/* Validate what props are supported by the driver */
uint16_t test_value = 0x1001;
struct fuel_gauge_property mfr_acc_set = {
.property_type = FUEL_GAUGE_SBS_MFR_ACCESS,
.value.sbs_mfr_access_word = test_value,
};
struct fuel_gauge_property mfr_acc_get = {
.property_type = FUEL_GAUGE_SBS_MFR_ACCESS,
};
zassert_ok(fuel_gauge_set_prop(fixture->dev, &mfr_acc_set));
zassert_ok(fuel_gauge_get_prop(fixture->dev, &mfr_acc_get));
zassert_equal(mfr_acc_get.value.sbs_mfr_access_word, test_value);
}
ZTEST_SUITE(sbs_gauge_new_api, NULL, sbs_gauge_new_api_setup, NULL, NULL, NULL); ZTEST_SUITE(sbs_gauge_new_api, NULL, sbs_gauge_new_api_setup, NULL, NULL, NULL);