Skip to content

Commit c81b029

Browse files
Shreehari-AlifSemicfriedt
authored andcommitted
drivers: i3c: configure open-drain speed
Add support for configuring I3C open-drain speed modes to handle different timing requirements during bus initialization and operation. Implementation: - Fetch current controller configuration - Invoke configure api inside bus_init to configure I3C open-drain high period for proper bus initialization and device compatibility. The slow speed mode is essential for the first broadcast address transmission to ensure visibility to all devices on the I3C bus, particularly those in I2C mode that need to disable their spike filters when switching to I3C mode. This requirement is specified in "Table 49 I3C Basic Open Drain Timing Parameters" of the MIPI ALLIANCE Specification for I3C Basic Version 1.2. Signed-off-by: Shreehari HK <[email protected]>
1 parent 4d6673b commit c81b029

File tree

1 file changed

+34
-0
lines changed

1 file changed

+34
-0
lines changed

drivers/i3c/i3c_common.c

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1350,6 +1350,32 @@ int i3c_bus_init(const struct device *dev, const struct i3c_dev_list *dev_list)
13501350
bool need_daa = true;
13511351
bool need_aasa = true;
13521352
struct i3c_ccc_events i3c_events;
1353+
struct i3c_config_controller ctrl_cfg;
1354+
uint32_t prev_od_high_ns;
1355+
1356+
/* Retrieve the active controller configuration */
1357+
ret = i3c_config_get_controller(dev, &ctrl_cfg);
1358+
if (ret != 0) {
1359+
LOG_ERR("%s: Failed to retrieve controller configuration", dev->name);
1360+
return ret;
1361+
}
1362+
1363+
/* Set OD high period for first broadcast message.
1364+
* The Controller uses this timing to send the
1365+
* first Broadcast Address, in order to disable the
1366+
* I2C Spike Filter for applicable I3C Basic Target Devices.
1367+
* Ref Section 4.3.2.2.2 and Table 49 of
1368+
* MIPI ALLIANCE Specification for I3C Basic Version 1.2
1369+
*/
1370+
prev_od_high_ns = ctrl_cfg.scl_od_min.high_ns;
1371+
ctrl_cfg.scl_od_min.high_ns = MAX(I3C_OD_FIRST_BC_THIGH_MIN_NS,
1372+
ctrl_cfg.scl_od_min.high_ns);
1373+
1374+
ret = i3c_configure_controller(dev, &ctrl_cfg);
1375+
if (ret != 0) {
1376+
LOG_ERR("%s: Open Drain Slow speed set failed", dev->name);
1377+
return ret;
1378+
}
13531379

13541380
#ifdef CONFIG_I3C_INIT_RSTACT
13551381
/*
@@ -1380,6 +1406,14 @@ int i3c_bus_init(const struct device *dev, const struct i3c_dev_list *dev_list)
13801406
LOG_DBG("Broadcast RSTDAA was NACK.");
13811407
}
13821408

1409+
/* Set previously stored OD high period back */
1410+
ctrl_cfg.scl_od_min.high_ns = prev_od_high_ns;
1411+
ret = i3c_configure_controller(dev, &ctrl_cfg);
1412+
if (ret != 0) {
1413+
LOG_ERR("%s: Open Drain Normal speed set failed", dev->name);
1414+
return ret;
1415+
}
1416+
13831417
/*
13841418
* Disable all events from targets to avoid them
13851419
* interfering with bus initialization,

0 commit comments

Comments
 (0)