> This page is for version 3.0 (Latest) (default).
> For other versions, use one of these documentation indexes:
> - 3.0 (Latest) (default): https://docs.nvidia.com/holoscan/sensor-bridge/3-0/llms.txt
> - 2.7: https://docs.nvidia.com/holoscan/sensor-bridge/2-7/llms.txt
> - Archives: https://docs.nvidia.com/holoscan/sensor-bridge/archives/llms.txt

> For clean Markdown of any page, append .md to the page URL.
> For a complete documentation index, see https://docs.nvidia.com/holoscan/sensor-bridge/llms.txt.
> For AI client integration (Claude Code, Cursor, etc.), connect to the MCP server at https://docs.nvidia.com/holoscan/sensor-bridge/_mcp/server.

# hololink::module::I2cInterfaceV1

> Provides access to I2C controllers instantiated within an HSB device.

Provides access to I2C controllers instantiated within an HSB device.

You can request an immediate I2C transaction (with i2c_transaction) or one that is downloaded and triggered by a specific event (using encode_i2c_request).

In some cases (specifically the default I2C configuration within the HSB IP core) a single I2C controller is muxed between different output pins, providing hardware with different I2C buses, but requiring that the host serialize access to each. When this serialization is required, it's managed automatically within the module– so application code doesn't have to know that.

```cpp showLineNumbers={false}
#include <hololink/module/i2c.hpp>
```

**Inherits from:** `hololink::module::Service< I2cInterfaceV1 >` (public)

---

## Methods

### i2c_transaction \[#i2ctransaction]

```cpp showLineNumbers={false}
virtual hololink_module_status_t hololink::module::I2cInterfaceV1::i2c_transaction(
    uint32_t peripheral_address,
    const std::vector<uint8_t> &write_bytes,
    std::vector<uint8_t> &read_bytes
)
```

Execute an I2C transaction.

Writes `write_bytes` to the peripheral, then reads back as many bytes as `read_bytes` is configured to hold; size it to zero for a write-only transaction.

**Returns:** HOLOLINK_MODULE_OK or an error status.

**Parameters**

**`peripheral_address`** `uint32_t`

Address of the peripheral on this bus.

---

**`write_bytes`** `const std::vector<uint8_t> &`

Bytes sent to the peripheral.

---

**`read_bytes`** `std::vector<uint8_t> &`

Sized by the caller to the number of bytes to read; receives them.

---

**Example**

```cpp showLineNumbers={false}
// Read the four bytes the peripheral holds at register 0x0010.
std::vector<uint8_t> write_bytes { 0x00, 0x10 };
// read_bytes carries the byte count in: size it to what you want to
// read, and the call fills it in place.
std::vector<uint8_t> read_bytes(4);
if (i2c->i2c_transaction(peripheral_address, write_bytes, read_bytes)
    != HOLOLINK_MODULE_OK) {
    // The transaction didn't run; read_bytes holds nothing to use.
} else {
    // read_bytes now holds the four bytes the peripheral returned.
}
```

### encode_i2c_request \[#encodei2crequest]

```cpp showLineNumbers={false}
virtual hololink_module_status_t hololink::module::I2cInterfaceV1::encode_i2c_request(
    SequencerInterfaceV1 &sequencer,
    uint32_t peripheral_i2c_address,
    const std::vector<uint8_t> &write_bytes,
    uint32_t read_byte_count,
    std::vector<unsigned> &out_write_indexes,
    std::vector<unsigned> &out_read_indexes,
    unsigned &out_status_index
)
```

Encode an I2C transaction into a sequencer.

Sequencers cache a list of local bus transactions, after that cache is written to an HSB device, and the trigger activates, the HSB IP will execute that transaction list. This API appends an I2C transaction to the sequencer cache. The bytes to be written to I2C are included in the call (in write_bytes); when reading from I2C, the list of HSB IP local bus addresses where the cached data can be found are put in `out_read_indexes`. Each location has 4 bytes; the last bytes (when read_byte_count isn't an even 32-bits) are undefined.

**Returns:** HOLOLINK_MODULE_OK or an error status.

**Parameters**

**`sequencer`** `SequencerInterfaceV1 &`

Sequencer to encode into.

---

**`peripheral_i2c_address`** `uint32_t`

Address of the peripheral on this bus.

---

**`write_bytes`** `const std::vector<uint8_t> &`

Bytes to send to the peripheral.

---

**`read_byte_count`** `uint32_t`

Bytes to read back from the peripheral.

---

**`out_write_indexes`** `std::vector<unsigned> &`

Where the bytes to send are encoded.

---

**`out_read_indexes`** `std::vector<unsigned> &`

Where the bytes read back are deposited.

---

**`out_status_index`** `unsigned &`

Where the transaction's status is deposited.

---

### module \[#module]

```cpp showLineNumbers={false}
std::shared_ptr<Module> hololink::module::ServiceBase::module() const
```

The [Module](module) that this service was published from.

The service holds no strong reference to its [Module](module), so this does not extend the [Module](module)'s lifetime.

**Returns:** The owning [Module](module), or an empty pointer if the service has not been published or its [Module](module) no longer exists.

---

## Static methods

### get_service \[#getservice]

```cpp showLineNumbers={false}
static std::shared_ptr<I2cInterfaceV1> hololink::module::Service<I2cInterfaceV1>::get_service(
    std::shared_ptr<Module> module,
    const char *instance_id,
    bool allow_null = false
)
```

Type-safe way to fetch a std::shared_ptr to an instance of \<Derived> from a [Module](module).

Note that [Module](module) usually caches instances, it's likely that calls to get_service with the same locator_id will return pointers to the same implementation object.

**Returns:** A shared pointer to the service instance.

**Parameters**

**`module`** `std::shared_ptr<Module>`

Is the shared object that owns the instance we wish to fetch

---

**`instance_id`** `const char *`

Names the specific object, usually expressed as a set of "name=value;..." pairs, as defined by the implementations themselves. This name is normally fetched by calling `Derived::locator_id(enumeration_metadata)`.

---

**`allow_null`** `bool` — default: false

The default value of `false` causes this routine to throw a std::runtime_error if the service cannot be found within the module; this would be expected to terminate the calling program. If the application wants to handle the error, pass in `true` here and get_service will return `nullptr` when this module doesn't provide the requested service.

---

### for_each_type_id \[#foreachtypeid]

```cpp showLineNumbers={false}
static bool hololink::module::Service<I2cInterfaceV1>::for_each_type_id(
    Callback &&cb
)
```

Iterate over every type_id supported by this instance.

The callback signature is `bool(const char*)` — returning false halts the walk; true continues. Iteration is depth-first, so you'll see the most specific implementation types first.