Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Treating the library like a virtual I2C hub device #16

Open
MikeFair opened this issue Nov 19, 2016 · 0 comments
Open

Treating the library like a virtual I2C hub device #16

MikeFair opened this issue Nov 19, 2016 · 0 comments

Comments

@MikeFair
Copy link

The work on adding a "clock_stretch" and making different devices work at different speeds on the bus gave me lots of ideas; but namely it grounded something I'd been thinking about for a while now; that it should be possible to encode all the configuration required for an I2C Request in a single numeric identifier that can be "reused" and "passed around".

An application would feed in the details into a function and get back a single 32-bit or 64-bit identfier that represented that "request" as a "request_id". Then one mechanism to trigger a request is just to ask for it by request_id. These ids (with certain "fill in the blank" bits masked out) could be sent over a network or other communication lines to have other devices execute them at your request and send back the results. [This is like what slave I2C devices in some chips do, or what an I2C aggregator/hub is doing.]

So I started wondering about using an I2C bus library that acted like a "virtual i2c hub".

I'd register requests, set up precanned fetches/puts, and then interact with it much the same I would an actual device. I'd call a couple "update" functions at the start of "loop()" and a "commitChanges()" at the end; and the library would get the state/values from the preconfigured devices, I'd manipulate/read them inside loop(), and the library would push back the changes.

We could call commitChanges(), or update(), as often as required.

For example:

  • sda_pin (8 bits)+ scl_pin (8 bits) == 16-bit "bus id".
  • Device Address (8 bits) +Time Window (32 bits) == 40-bit "device id"
  • Register Address (8-bits) + Data Length (8-bits) + Flags(8-bits) == 24-bit "Item Id"

"Device Id" + "Item Id" == 64-bit "Request Id"

void setup() {
    I2CBus i2c_bus1(sda, scl);
    uint64_t req_id = i2c_get_request_id(
            device_address, bus_speed, clock_stretch
            , register_address, data_length, is_read, start_repeat, ... 
    );
    i2c_bus1.execRequest(req_id, &data[6]);
    i2c_bus1.setSlaveRequest(slave_id, req_id, (uint8_t*)&the_device_struct);  // Populate data into the_device_struct
}

void loop() {
    i2c_bus1.updateSlaves();

    if (the_device_struct.data_available) {
        Serial.println("Got Value: " + String(the_device_struct.important_value));
    }

    the_device_struct.config_setting = get_new_setting();

    i2c_bus1.commitChanges();
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants