Skip to content

Commit d683315

Browse files
author
Amanda Butler
authored
Merge pull request #1103 from maciejbocianski/i2c_hal_porting_guide_update
Add porting guide for HAL I2C API
2 parents cdfe7d8 + ccdbaac commit d683315

File tree

1 file changed

+120
-0
lines changed

1 file changed

+120
-0
lines changed

docs/porting/target/i2c.md

Lines changed: 120 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,120 @@
1+
# Inter-integrated circuit (I2C)
2+
3+
I2C is a serial protocol for two-wire interface to connect low-speed devices in embedded systems. The I2C API allows control and configuration of this interface.
4+
5+
The interface is made up of two lines for all communication:
6+
7+
- Serial Clock (SCL).
8+
- Serial Data (SDA).
9+
10+
<span class="warnings">**Warning:** We are introducing the I2C API in an upcoming release of Mbed OS. This page documents code that exists on a feature branch of Mbed OS. You can find details on how it may affect you in the [implementing the I2C API](#implementing-the-i2c-api) section.
11+
12+
## Defined behaviors
13+
14+
- `i2c_init`:
15+
- Initializes the peripheral pins specified in the input parameters.
16+
- Initializes the peripheral in master mode if `is_slave` is false.
17+
- Initializes the peripheral in slave mode if `is_slave` is true and `supports_slave_mode` is true.
18+
- Initializes all `i2c_t` object fields.
19+
- `i2c_free`:
20+
- Resets the pins used to initialize the peripheral to their default state.
21+
- Disables the peripheral clock.
22+
- `i2c_get_capabilities`:
23+
- Fills the contents of the `i2c_capabilities_t` parameter.
24+
- `i2c_frequency`:
25+
- Sets the frequency to use for the transfer.
26+
- Returns the actual frequency used.
27+
- Must leave all other configuration unchanged.
28+
- `i2c_set_clock_stretching`:
29+
- Enables or disables clock stretching for the peripheral when in slave mode.
30+
- Does nothing when called in master mode.
31+
- `i2c_timeout`:
32+
- Sets the transmision timeout to use for the following blocking transfers.
33+
- If the timeout is not set, the default timeout is used.
34+
- Default timeout value is based on I2C frequency and computed as triple the amount of time it takes to send data over I2C.
35+
- `i2c_write`:
36+
- Writes `length` number of symbols to the bus.
37+
- Returns the number of symbols sent to the bus.
38+
- Returns an error code if transfer fails.
39+
- Generates a stop condition on the bus at the end of the transfer if `stop` parameter is true.
40+
- Handles transfer collisions and loss of arbitration if the platform supports multimaster in hardware.
41+
- The transfer times out and returns `I2C_ERROR_TIMEOUT ` if the transfer takes longer than the configured timeout duration.
42+
- `i2c_read`:
43+
- Reads `length` symbols from the bus.
44+
- Returns the number of symbols received from the bus.
45+
- Returns an error code if transfer fails.
46+
- Generates a stop condition on the bus at the end of the transfer if `stop` parameter is true.
47+
- Handles transfer collisions and loss of arbitration if the platform supports multimaster in hardware.
48+
- The transfer times out and returns `I2C_ERROR_TIMEOUT ` if the transfer takes longer than the configured timeout duration.
49+
- `i2c_start`:
50+
- Generates I2C START condition on the bus in master mode.
51+
- Does nothing if called when the peripheral is configured in slave mode.
52+
- `i2c_stop`:
53+
- Generates I2C STOP condition on the bus in master mode.
54+
- Does nothing if called when the peripheral is configured in slave mode.
55+
- `i2c_slave_status`:
56+
- Indicates in which mode the peripheral has been addressed.
57+
- Returns not addressed when called in master mode.
58+
- `i2c_slave_address`:
59+
- Sets the address of the peripheral to the `address` parameter.
60+
- Does nothing if called in master mode.
61+
- `i2c_transfer_async`:
62+
- Returns immediately with a `bool` indicating whether the transfer was successfully scheduled.
63+
- The callback given to `i2c_transfer_async` is invoked when the transfer finishes or error occurs.
64+
- Must save the handler and context pointers inside the `obj` pointer.
65+
- The context pointer is passed to the callback on transfer completion.
66+
- The callback must be invoked on completion unless the transfer is aborted.
67+
- May handle transfer collisions and loss of arbitration if the platform supports multimaster in hardware and enabled in API.
68+
- `i2c_async_event_t` must be filled with the number of symbols sent to the bus during transfer.
69+
- `i2c_abort_async`:
70+
- Aborts any ongoing async transfers.
71+
72+
## Undefined behaviors
73+
74+
- Use of a `null` pointer as an argument to any function.
75+
- Calling any `I2C` function before calling `i2c_init` or after calling `i2c_free`.
76+
- Initializing the `I2C` peripheral with invalid `SDA` and `SCL` pins.
77+
- Initializing the peripheral in slave mode if slave mode is not supported, indicated by `i2c_get_capabilities`.
78+
- Operating the peripheral in slave mode without first specifying and address using `i2c_slave_address`.
79+
- Setting an address using `i2c_slave_address` after initializing the peripheral in master mode.
80+
- Setting an address to an `I2C` reserved value.
81+
- Setting an address larger than the 7-bit supported maximum if 10-bit addressing is not supported.
82+
- Setting an address larger than the 10-bit supported maximum.
83+
- Setting a frequency outside the supported range given by `i2c_get_capabilities`.
84+
- Using the device in a multimaster configuration when `supports_multimaster_mode` is false.
85+
- Specifying an invalid address when calling any `read` or `write` functions.
86+
- Setting the length of the transfer or receive buffers to larger than the buffers are.
87+
- Passing an invalid pointer as `handler` to `i2c_transfer_async`.
88+
- Calling `i2c_transfer_abort` when no transfer is currently in progress.
89+
90+
## Notes
91+
92+
You can find more details about the design choices in the [HAL code design document](https://github.com/ARMmbed/mbed-os/blob/feature-i2c/docs/design-documents/hal/0001-i2c-overhaul.md).
93+
94+
## Dependencies
95+
96+
Hardware I2C capabilities.
97+
98+
## Implementing the I2C API
99+
100+
You can find the API and specification for the I2C API in the following class reference:
101+
102+
[![View code](https://www.mbed.com/embed/?type=library)](https://os.mbed.com/docs/mbed-os/development/feature-i2c-doxy/classmbed_1_1_i2_c.html)
103+
104+
To enable I2C support in Mbed OS, add the `I2C` label in the `device_has` option of the target's section in the `targets.json` file.
105+
106+
You can also add the `I2C_ASYNCH` label in the `device_has` option to enable the asynchronous API,
107+
and `I2CSLAVE` to enable the I2CSlave API.
108+
109+
## Testing
110+
111+
The Mbed OS HAL provides a set of conformance tests for I2C. You can use these tests to validate the correctness of your implementation. To run the I2C HAL tests, use the following command:
112+
113+
```
114+
mbed test -t <toolchain> -m <target> -n "tests-mbed_hal_fpga_ci_test_shield-i2c"
115+
```
116+
117+
You can read more about the test cases:
118+
119+
[![View code](https://www.mbed.com/embed/?type=library)](https://os.mbed.com/docs/mbed-os/development/feature-i2c-doxy/group__hal__i2c__tests.html)
120+

0 commit comments

Comments
 (0)