Browse Source

drivers: i3c: specify start addr when searching for a free addr

For example, if a driver needed to reserve address before it does a
ENTDAA, it would need to get free address in a loop, but the get
free address func would return the same address everytime. It needs
the start address, which would be the last free address it go, to
be passed in to get the next free address.

Signed-off-by: Ryan McClelland <ryanmcclelland@meta.com>
pull/65012/head
Ryan McClelland 2 years ago committed by Carles Cufí
parent
commit
9ddc94e0d4
  1. 2
      drivers/i3c/i3c_cdns.c
  2. 10
      drivers/i3c/i3c_common.c
  3. 3
      include/zephyr/drivers/i3c/addresses.h

2
drivers/i3c/i3c_cdns.c

@ -703,7 +703,7 @@ static void cdns_i3c_program_controller_retaining_reg(const struct device *dev) @@ -703,7 +703,7 @@ static void cdns_i3c_program_controller_retaining_reg(const struct device *dev)
if (!i3c_addr_slots_is_free(&data->common.attached_dev.addr_slots, controller_da)) {
controller_da =
i3c_addr_slots_next_free_find(&data->common.attached_dev.addr_slots);
i3c_addr_slots_next_free_find(&data->common.attached_dev.addr_slots, 0);
LOG_DBG("%s: 0x%02x DA selected for controller", dev->name, controller_da);
}
sys_write32(prepare_rr0_dev_address(controller_da), config->base + DEV_ID_RR0(0));

10
drivers/i3c/i3c_common.c

@ -157,13 +157,13 @@ bool i3c_addr_slots_is_free(struct i3c_addr_slots *slots, @@ -157,13 +157,13 @@ bool i3c_addr_slots_is_free(struct i3c_addr_slots *slots,
return (status == I3C_ADDR_SLOT_STATUS_FREE);
}
uint8_t i3c_addr_slots_next_free_find(struct i3c_addr_slots *slots)
uint8_t i3c_addr_slots_next_free_find(struct i3c_addr_slots *slots, uint8_t start_addr)
{
uint8_t addr;
enum i3c_addr_slot_status status;
/* Addresses 0 to 7 are reserved. So start at 8. */
for (addr = 8; addr < I3C_MAX_ADDR; addr++) {
for (addr = MAX(start_addr, 8); addr < I3C_MAX_ADDR; addr++) {
status = i3c_addr_slots_status(slots, addr);
if (status == I3C_ADDR_SLOT_STATUS_FREE) {
return addr;
@ -252,7 +252,7 @@ int i3c_determine_default_addr(struct i3c_device_desc *target, uint8_t *addr) @@ -252,7 +252,7 @@ int i3c_determine_default_addr(struct i3c_device_desc *target, uint8_t *addr)
} else {
/* address is not free, get the next one */
*addr = i3c_addr_slots_next_free_find(
&data->attached_dev.addr_slots);
&data->attached_dev.addr_slots, 0);
}
} else {
/* Use the init dynamic address as it's DA, but the RR will need to
@ -281,7 +281,7 @@ int i3c_determine_default_addr(struct i3c_device_desc *target, uint8_t *addr) @@ -281,7 +281,7 @@ int i3c_determine_default_addr(struct i3c_device_desc *target, uint8_t *addr)
} else {
/* pick a DA to use */
*addr = i3c_addr_slots_next_free_find(
&data->attached_dev.addr_slots);
&data->attached_dev.addr_slots, 0);
}
}
} else {
@ -488,7 +488,7 @@ int i3c_dev_list_daa_addr_helper(struct i3c_addr_slots *addr_slots, @@ -488,7 +488,7 @@ int i3c_dev_list_daa_addr_helper(struct i3c_addr_slots *addr_slots,
/*
* Find the next available address.
*/
dyn_addr = i3c_addr_slots_next_free_find(addr_slots);
dyn_addr = i3c_addr_slots_next_free_find(addr_slots, 0);
if (dyn_addr == 0U) {
/* No free addresses available */

3
include/zephyr/drivers/i3c/addresses.h

@ -113,10 +113,11 @@ bool i3c_addr_slots_is_free(struct i3c_addr_slots *slots, @@ -113,10 +113,11 @@ bool i3c_addr_slots_is_free(struct i3c_addr_slots *slots,
* assigned to a new device.
*
* @param slots Pointer to the address slots structure.
* @param start_addr Where to start searching
*
* @return The next free address, or 0 if none found.
*/
uint8_t i3c_addr_slots_next_free_find(struct i3c_addr_slots *slots);
uint8_t i3c_addr_slots_next_free_find(struct i3c_addr_slots *slots, uint8_t start_addr);
/**
* @brief Mark the address as free (not used) in device list.

Loading…
Cancel
Save