Skip to content

14. Networking and communications

Group assignment:

  • Send a message between two projects
  • Document your work to the group work page and reflect on your individual page what you learned

Individual assignment:

  • Design, build and connect wired or wireless node(s) with network or bus addresses and a local interface

What is I2C?

I2C, or inter-integrated circuit, is a communication protocol that uses 2 pins, SDA and SCL, to send and receive data between master and node boards. SDA stands for “serial data pin”, and, like its name says, it facilitates the transfer of data between individual (or many) master and node boards. On the other hand, SCL stands for “serial clock pin”, which carries the clock signal and pulses high or low at regular intervals.

PCB Design

I began this week by designing PCBs for the networking individual assignment, and I decided to use I2C. For much of the early stages of this week, I referenced Adrian Torres’s documentation. In the end, I created 2 distinct boards (the node and bridge boards) and milled out 3 PCBs (2 nodes, 1 bridge). The designs of the PCBs are shown below.

bridge pcb design shown above

node pcb design shown above

After designing both boards, I exported the gerber files used to mill them and sent them to the desktop in our lab which was connected to the milling machine. These files will be linked at the bottom of this page.

Milling

I decided to mill the 2 node boards first mainly with a 1/64 bit. I would have preferred to use a 1/32 bit because it is faster, but there were a few details which were too small for that. In the end, I used a 1/64 inch bit for the details and a 1/32 bit for the outline and text. The image below shows what the boards looked like after being milled out.

Soldering both boards took a bit over an hour, but they both appeared to work fine (I did have to cut one trace close to the 4 pin connector on the bottom of the board).

Programming (failed)

After milling out the boards, I began to try programming them. However, I encountered some problems here when trying to network with two node boards and one bridge board, so I ended up deciding to network with only one node board.

Even after spending over 2 hours trying to program these two boards, though, I was still unable to make them network with each other using SDA and SCL for I2C. Because of this, I decided to start again from scratch using different microcontrollers. Instead of using 2 ATTiny412s, I decided to switch to using 2 Xiao RP2040s. I believed that these new microcontrollers would make networking much easier. Although my previous board designs didn’t work, I still decided to keep using I2C.

Note from the future: As pointed out by my global evaluator (thank you Ivan!), I did not add any pull-up resistors on the PCB for the ATtiny412 boards. This was because I believed that the 412s already had built-in pull-up resistors, and I therefore thought that I didn’t need to add anymore. Looking back, I probably should have added them anyways, and this might have been the reason that my boards didn’t work. I did a bit of research of the 412s, and most sources that I could find (like this arduino forum post) recommend adding your own pull-up resistors.

New Plan: Xiao RP2040

The first thing I did when beginning from scratch was to look at the Xiao’s pinout, of which I have added an image below.

As you can see from this image, the Xiao’s SDA and SCL pins are pins 6 and 7, respectively. This means that I will have the connect pin 6 on both Xiaos together, and pin 7 on both Xiaos together. Then, the only other connection that is necessary between the two Xiao’s is the GND pin. They do not have to share 5V or 3.3V power, as they can be powered by two separate power supplies, but I decided to have them share the same power because I felt that it would be more convenient for my purposes, as I only have 1 USB A port on my laptop which I will be connecting one of the Xiaos to.

Programming the Xiaos

I knew that I wanted to send signals from the master board to the node board in order to change the color of the built-in LED on the Xiao, so I began writing code for this purpose. I also asked ChatGPT to write some code for this part of the assignment, and I ended up using a modified version of ChatGPT’s code. The code that I used for the master and node boards are shown below.

Master board code

#include <Wire.h>

#define SLAVE_ADDRESS 0x08

void setup() {
  Wire.begin(); // Join I2C bus as master
  Serial.begin(9600);
}

void loop() {
  Wire.beginTransmission(SLAVE_ADDRESS); // Start communication with slave
  Wire.write('A'); // Send a signal
  Wire.endTransmission(); // Stop communication
  Serial.println("Signal sent to slave");
  delay(1000); // Wait for a second before sending next signal
}

Node board code

#include <Wire.h>

#define LED_BUILTIN 25 // Pin number for built-in LED

void setup() {
  pinMode(LED_BUILTIN, OUTPUT); // Initialize the built-in LED pin as an output
  Wire.begin(0x08); // Join I2C bus as slave with address 0x08
  Wire.onReceive(receiveEvent); // Register event for receiving data
}

void loop() {
  // Main loop does nothing, all action happens in receiveEvent
}

void receiveEvent(int howMany) {
  while (Wire.available()) { // Loop through all available bytes
    char c = Wire.read(); // Receive byte as a character
    if (c == 'A') {
      blinkLED(); // Blink the LED if the signal is 'A'
    }
  }
}

void blinkLED() {
  digitalWrite(LED_BUILTIN, HIGH);
  delay(500); // Wait for 500 milliseconds
  digitalWrite(LED_BUILTIN, LOW);
}

The way the master/node code works is that the master board begins by sending a signal (‘A’) to the node board. Since the node board uses Wire.available(), it knows when that signal is sent. Once it receives the signal, it blinks the LED if the signal it received was ‘A’.

Testing

After uploading the master and node codes to their respective Xiaos, I connected all the pins I needed to each other using jumper wires and plugged in one of the Xiaos to power. The code worked! The video below shows the color of the LED on the node board changing according to a signal from the master board.

PCB Design/Milling

Now that I knew my code worked, I moved onto creating a board for the master and node Xiaos. I used the same board for both, as they both needed the same connections/pins for networking between them to work. The schematic and PCB layout of the board that I made are shown below. This board was pretty simple to make as it only includes the Xiao RP2040 and a vertical male conn header.

After designing the PCB, I milled 2 of these boards, which took around 20 minutes. I then soldered all of the components on them (while making sure to cover the bottom of the Xiaos with electrical tape). The picture below shows what they looked like after having all of the components soldered on.

Running the Code

Now that I had my boards soldered, I connected them using jumper wires and tested the same code as what I used previously. the video below shows the code working as intended and shows the two Xiao boards communicating using I2C.

Group Assignment

Our group assignment this week was to send a message between two projects, so that is what I and my partner, Kabir, did. Our group assignment documentation for this week can be found here.

Reflection

Overall, I felt disappointed at first when I failed to make 2 ATTiny412s communicate with each other using I2C, but I was happy that I resolved this issue by instead using Xiao RP2040s. I definitely learned a lot this week about networking and hope to use I2C more in the future. My files for this week can be found here.


Last update: June 28, 2024