Skip to content

Commit 3dec52e

Browse files
committed
add example for onRequestMore event
1 parent bea4180 commit 3dec52e

File tree

1 file changed

+104
-0
lines changed

1 file changed

+104
-0
lines changed
+104
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,104 @@
1+
// Wire Slave "256-Byte Memory" Device
2+
// by Jan Wagner
3+
4+
// Demonstrates use of the Wire library to emulate a 256-byte memory device,
5+
// with sequential continued read and sequential continued write access.
6+
// Operates as an I2C/TWI slave device.
7+
//
8+
// The protocol used in this example emulates typical small EEPROMs,
9+
// or i2c-addressible register banks. The master controls the I2C transaction,
10+
// doing one of two things within a single transaction:
11+
//
12+
// 1) master sends an address-byte and sends optional data-byte(s) that the
13+
// slave shall store into memory starting from the given address,
14+
//
15+
// or
16+
//
17+
// 2) master sends an address-byte and immediately changes into receive
18+
// mode, receiving data-byte(s) from slave memory starting from that address.
19+
//
20+
// The number of data bytes in the transaction is not known in advance.
21+
// The master can at any time stop sending (1) or reading (2) data bytes.
22+
// Either mode, (1) or (2), is carried out as a single multi-byte I2C transaction.
23+
//
24+
// Starting from a base address (between 0 and 255) sent by the master,
25+
// the slave auto-increments the address for each byte sent or read.
26+
// When the end of address space is reached it wraps back to 0.
27+
28+
// Master writing address, then writing data (case 1) is handled simply in the
29+
// onReceive event - receives starting address plus data bytes from master
30+
31+
// Master writing address, then reading data (2) is handled in the
32+
// onReceive event - receives starting address from master, no other data
33+
// onRequest event - sends the first requested data to master
34+
// onRequestMore event - sends more, continually reinvoked while master keeps reading
35+
36+
// Created 18 December 2023
37+
38+
// This example code is in the public domain.
39+
40+
#include <Wire.h>
41+
42+
static volatile byte shared_memory[256];
43+
static volatile unsigned int memory_addr = 0;
44+
45+
void setup() {
46+
unsigned int i;
47+
48+
// initialize memory with a simple pattern
49+
for(i=0; i<sizeof(shared_memory); i++) {
50+
shared_memory[i] = i;
51+
}
52+
memory_addr = 0;
53+
54+
// initialise Wire
55+
Wire.begin(8); // join I2C bus with address #8
56+
Wire.onReceive(receiveEvent); // register event
57+
Wire.onRequest(requestEvent); // register event
58+
Wire.onRequestMore(requestMoreEvent); // register event
59+
}
60+
61+
void loop() {
62+
delay(100);
63+
}
64+
65+
// Helper to get next address within array bounds
66+
unsigned int next_addr(unsigned int curr_addr) {
67+
return (curr_addr + 1) % (sizeof(shared_memory) + 1);
68+
}
69+
70+
// Function that executes whenever data is sent to slave by master
71+
// This function is registered as an event, see setup()
72+
void receiveEvent(int nbytes) {
73+
if(nbytes > 0) {
74+
75+
// receive the memory address that the master wants to access
76+
memory_addr = Wire.read();
77+
memory_addr = memory_addr % (sizeof(shared_memory) + 1);
78+
nbytes--;
79+
80+
// receive optional data that master might be pushing into client memory
81+
while(nbytes > 0) {
82+
shared_memory[memory_addr] = Wire.read();
83+
memory_addr = next_addr(memory_addr);
84+
nbytes--;
85+
}
86+
}
87+
}
88+
89+
// Function that executes whenever data is first requested by master
90+
// This function is registered as an event, see setup()
91+
void requestEvent() {
92+
// master started reading: send back the first data byte
93+
Wire.write(shared_memory[memory_addr]);
94+
memory_addr = next_addr(memory_addr);
95+
}
96+
97+
// Function that executes each time the master in the current transaction
98+
// tries to read more than initially provided in the onRequest handler above.
99+
// This function is registered as an event, see setup()
100+
void requestMoreEvent() {
101+
// master continues reading: send back the next data byte
102+
Wire.write(shared_memory[memory_addr]);
103+
memory_addr = next_addr(memory_addr);
104+
}

0 commit comments

Comments
 (0)