SlideShare a Scribd company logo
Connecting
Raspberry Pi to
Arduino using I2C
Raspberry Pi
This work is licensed under the
Creative Commons Attribution-
ShareAlike 4.0 International License.
To view a copy of this license, visit
http://creativecommons.org/licenses/b
y-sa/4.0/.
Revision 2
Companion Github
What is I2C?
The Inter-IC Bus (I-IC or I2C) standard defines the hardware and
electrical characteristics of the interface between nearby devices using
only two wires (and a third for ground reference).
SMBus was introduced by Intel as a tight subset of I2C, strictly defining
the interface between devices.
It is commonly used in televisions, computer components, and many
ADC and DAC and GPS devices.
The Raspberry Pi most commonly uses an SMBus implementation
in Python 2.x, and this is what we will concentrate on in this
document.
Connecting Devices
Identify SDA, SCL, and GND pins on both Raspberry Pi and the Arduino.
Connect SDA to SDA, SCL to SCL, and GND to GND between the two devices.
It is possible to connect the two devices directly to one another without a level
shifter, but it is not best practice. I2C levels for a low signal is 0.3Vcc and for a
high, 0.7Vcc. With the Raspberry Pi being a 3.3V device and the Arduino requiring
5V for Vcc, a logic level 'high' coming from the 3.3V Raspberry Pi is slightly below
the 0.7*5= 3.5V required for a definite logic 'high' in the Arduino.
Voltage Levels
The Raspberry Pi is a 3.3V device while the Arduino is a 5V device, but because
both devices are connected in open-drain configuration with relatively high pull-up
resistor values, it is unlikely damage will occur. The problem is that the
communication between the two devices is not guaranteed to work well due to the
3.5V minimum logic level 'high' required by the Arduino, and the Raspberry Pi input
is not 5V resistant.
A level shifter isolates the two different
voltages, while transmitting on/off information
in both directions.
Having said that, I have had reliable
communication between the Raspberry Pi and
the Arduino without any loss of data, but I am
worried about the Arduino accidently driving
one of the SDA or SCL pins to 5V as an output
if the program is not written carefully and
damaging the Raspberry Pi. User beware.
I2C Level Shifter
This rather complicated-looking circuit creates a bi-directional bus that can
automatically translate 3.3V bus signals into 5V signals and vice versa at full bus
speed. This is one of the simplest and cheapest level shifters and can easily be built
on a breadboard or soldered in a few minutes on any of the prototyping stripboards
available.
On the next slide, we look at
this circuit in detail
The Level Shifter
Isolating one of the two identical bus lines, we find an
enhancement-mode n-channel MOSFET the star of the
show. It's Gate is tied directly to the low-voltage Vcc. A
pull-up resistor connects the High voltage side to the
Drain, and another pulls the Source up to the Low voltage
side.
S1 and S2 simulate the Open-Drain connection that drives
the bus at the microcontroller.
With both switches open, Gate and Source are at the
same potential so the transistor is turned off. Both sides
are pulled up to their respective Vcc.
With S1 closed and S1 open, the source is pulled down to
0V, taking Vgs (Gate-Source Voltage) above the threshold
and turning the transistor on hard. This pulls the Drain side
down to 0V as well.
With S2 closed and S1 open, Drain is pulled to 0V and the
internal diode is forward-biased by the 3.3V, dropping the
source to around 0.6V. This is enough to pull Vgs again
beyond the threshold, opening the transistor and dragging
the bus down to 0V.
With both switches closed, both sides will be at 0V.
Setting Up Raspberry Pi
Getting the tools for Python2 and/or Python3...
1. Open a terminal window.
Enter “sudo apt-get install python-smbus” (2.x)
Or “sudo apt-get install python3-smbus” (3.x)
And “sudo apt-get install i2c-tools”
Reboot the Pi.
2. Open “Raspberry Pi Configuration” in the GUI or use
a terminal to enter 'sudo raspi-config'.
Enable I2C, save, and reboot.
3. Edit file 'etc/modules' using GUI text editor or
enter “sudo nano etc/modules”
If these two lines are not in there, type them;
i2c-bcm2708
I2c-dev
And save.
4. Edit file 'etc/modprobe.d/raspi-blacklist.comf' using
GUI editor or
Enter “sudo nano etc/modprobe.d/raspi-blacklist.conf”.
If these two lines exist, make sure a '#' is placed before
them, or delete them altogether..
#blacklist spi-bcm2708
#blacklist i2c-bcm2708
And save.
5. Finally, enter “sudo nano /boot/config.txt'. These two
lines should appear:
dtparam=i2c1=on
dtparam=i2c_arm=on
If not, make them so, and save.
Reboot.
Testing Raspberry Pi
Enter “i2cdetect -y 1” in a terminal window to
check that the I2C bus is available and running
on the Pi.
If everything is good, it will show a table of
addresses. If any I2C devices are available, their
addresses will be shown in hexadecimal.
It is worth entering “i2cdetect -F 1” to see which
SMBus calls are supported. It will save hours of
debugging to know that “SMBus Block Read” is
not supported, but “I2C Block Read” is
supported, and that “Block Process Call” is
meaningless as it is also not supported.
Preparing the Raspberry Pi
Start Python, and create a new file.
Import the SMBus library.
Create an SMBus object linked to I2C port 1.
Define the slaves address(es) to connect to.
Collect the data to be transmitted, or prepare the
data variables for reading back from the slave.
These instructions are for Python 2. Python 3 may have small differences.
import smbus
i2c_object = smbus.SMBus(1)
# Link to SMBus(0) on older Pi
addrSlave1 = 8
command = 0
dataList = [1,2,3,4,5]
i2c_object.write_i2c_block_data(addrSlave1,
command,
DataList)
getDataList = i2c_object.read_i2c_block_data(
addrSlave1,
command)
Preparing the Arduino
Start Arduino IDE
Include the Wire.h standard library for Arduino.
Set up the slave address.
Register a Wire function that will run when the
interrupt for receiving information from the Master
triggers.
The event is onReceive(function)
This event will react to information coming from
the master, and prepare for sending data back to
the master, if necessary.
Register a Wire function that will run when the
interrupt for returning data to the Master triggers.
This event is on onRequest(function)
When the interrupt fires, send data to the Master
that was requested.
#include <Wire.h>
const byte slaveAddr = 8;
void setup() {
Wire.begin(slaveAddr);
Wire.onReceive(i2cReceive);
Wire.onRequest(i2cTransmit);
}
void loop() {
}
void i2cReceive(int numBytes) {
byte rxByte;
while Wire.available() {
rxByte = Wire.read();
// Do something with the byte
}
}
Void i2cTransmit() {
Wire.write(...) // send requested data
}
Example Project
Using a Raspberry Pi 2 and an Arduino
Leonardo, we will connect up the I2C bus,
and connect an RGB LED to the Arduino. The
LED color and brightness will be controlled by
a Python program running on the Pi.
We will also simulate analog data to send
back to the Pi from the Arduino, a
temperature sensor and a light-level sensor.
The source code for both Arduino and
Raspberry Pi can be found on github at
mikeochtman.github.io/Pi_Arduino_I2C.
This drawing was created in Fritzing.
Interface Specification
Before we can communicate with the Arduino, we
need an interface specification which describes, in
detail, how and what data should be moved over
the bus from Master to Slave, and from Slave to
Master.
Type Description Access
Byte Command private
Byte Control private
Real Temperature Read Only
Real Light Level Read Only
Byte Brightness Red Read/Write
Byte Brightness Green Read/Write
Byte Brightness Blue Read/Write
Arduino Internal Data Table
Command Action
0x81 Read Temperature. Return int(round(temperature*100))
0x82 Read Light. Return int(round(light*100))
0x0A Write three bytes for brightness RGB
0x0B Write single byte, brightness Red channel
0x0C Write single byte, brightness Green channel
0x0D Write single byte, brightness Blue channel
0x90 Read three bytes brightness RGB
0x91 Read single byte, brightness Red channel
0x92 Read single byte, brightness Green channel
0x93 Read single byte, brightness Blue channel
Read,
no command
Return Slave Address, one Byte
Write,
No command
Master interrogating slave presence. Ignore
Other commands
Ignore. Master software has to deal with communication
exceptions, if any.
Arduino Software//The full software can be found on github at
// https://github.com/MikeOchtman/Pi_Arduino_I2C
//This is a simplified collection of
//the most important parts.
#include <Wire.h>
#define rxFault 0x80
#define txFault 0x40
#define slaveAddress 8
struct {
byte volatile command;
byte volatile control;
float volatile temperature;
float volatile light;
byte volatile brightR;
byte volatile brightG;
byte volatile brightB;
} commsTable;
byte volatile txTable[32];
// prepare data for sending over I2C
Void setup() {
Wire.begin(slaveAddress);
Wire.onReceive(i2cReceive);
Wire.onRequest(i2cTransmit);
}
Void loop() {
}
void i2cReceive(int byteCount) {
if (byteCount == 0) return;
byte command = Wire.read();
commsTable.command = command;
if (command < 0x80) {
i2cHandleRx(command, byteCount - 1);
} else {
i2cHandleTx(command);
}
}
byte i2cHandleRx(byte command, int numBytes) {
switch (command) {
case 0x0A:
if (Wire.available() == 3)
commsTable.brightR = Wire.read();
commsTable.brightG = Wire.read();
commsTable.brightB = Wire.read();
result = 3;
} else {
result = 0xFF;
}
break;
// and so on, one case for each command according to the
Interface Specification
default:
result = 0xFF;
}
if (result == 0xFF) commsTable.control |= rxFault;
return result;
}
Arduino Software, cont'd
byte i2cHandleTx(byte command) {
// If you are here, the I2C Master has requested
information
// If there is anything we need to do before the interrupt
// for the read takes place, this is where to do it.
return 0;
}
void i2cTransmit() {
// byte *txIndex = (byte*)&txTable[0];
byte numBytes = 0;
int t = 0;
switch (commsTable.command) {
case 0x00: // send slaveAddress.
txTable[0] = slaveAddress;
numBytes = 1;
break;
case 0x81: // send temperature
t = int(round(commsTable.temperature*100));
txTable[1] = (byte)(t >> 8);
txTable[0] = (byte)(t & 0xFF);
numBytes = 2;
break;
case 0x91: // send RGB Red channel
txTable[0] = commsTable.brightR;
numBytes = 1;
break;
// Again, create a case statement for each legal command
default:
commsTable.control |= txFault;
}
if (numBytes > 0) {
Wire.write((byte *)&txTable, numBytes);
}
}
Python Softwareimport smbus
import time
i2c = smbus.SMBus(1)
addr = 8 # address of the arduino I2C
##/* Interface Specification
## Data in a table thus:
## byte purpose
## 0: command
## 1: control
## 2-5: Current Temperature (read-only)
## 6-9: Current light level (read only)
## 10: Brightness for RED r/w
## 11: Brightness for GREEN r/w
## 12: Brightness for BLUE r/w
## Commands:
## Write with no command: Ignore
## Read with no command: Return slave address
## Command 0x81: read temperature;
## Integer returned, int(round(temp*100))
## Command 0x82: read light level;
## Integer returned, int(round(lux*100))
## Command 0x0A: Write three bytes to RGB
## Command 0x0B: Write single byte brightness red;
## Command 0x0C: Write single byte brightness green;
## Command 0x0D: Write single byte brightness blue;
## Command 0x90: read three bytes brightness RGB
## Command 0x91: read single byte brightness red;
## Command 0x92: read single byte brightness green;
## Command 0x93: read single byte brightness blue;
##
## All other values are ignored, no data returned.
RGB = [20,200,128]
temperature = 0
light_level = 0
i2c.write_quick(addr) # no data expected back
time.sleep(0.5)
print i2c.read_byte(addr) # expect the slave address
time.sleep(0.5)
print i2c.read_word_data(addr,0x81)/100.0 # temperature
time.sleep(0.5)
print i2c.read_word_data(addr,0x82)/100.0 # light level
time.sleep(0.5)
i2c.write_byte_data(addr, 0x0B, 12) # write Red value
time.sleep(0.5)
print i2c.read_byte_data(addr, 0x91) # write Green value
time.sleep(0.5)
i2c.write_byte_data(addr, 0x0C, 123) # write Blue value
time.sleep(0.5)
print i2c.read_byte_data(addr, 0x92) # get Green value
time.sleep(0.5)
i2c.write_byte_data(addr, 0x0D, 234) # write Blue value
time.sleep(0.5)
print i2c.read_byte_data(addr, 0x93) # get Blue value
time.sleep(0.5)
print i2c.read_i2c_block_data(addr, 0x90, 3) # get RGB
time.sleep(0.5)
i2c.write_i2c_block_data(addr, 0x0A, RGB) # set all RGB
time.sleep(0.5)
print i2c.read_i2c_block_data(addr, 0x90, 3) # get all RGB
time.sleep(0.5)
print i2c.read_i2c_block_data(addr, 0x10, 3) # force error
time.sleep(0.5)
The Python ResultsPython 2.7.9 results.
>>>
8
23.95
6.97
12
123
234
[12, 123, 234]
[20, 200, 128]
[0, 255, 255]
>>>
No event for write_quick()
Got back the slave Address.
Got the simulated temperature
Got the simulated light level
Set and read back Red channel
Set and read back Green channel
Set and read back Blue channel
Got back RGB values as a list.
Set new RGB values from a list
Read back the RGB values as a list
Forced a read error by sending wrong command.
RGB = [20,200,128]
i2c.write_quick(addr) # no data expected back
print i2c.read_byte(addr) # expect the slave address
print i2c.read_word_data(addr,0x81)/100.0 # temperature
print i2c.read_word_data(addr,0x82)/100.0 # light level
i2c.write_byte_data(addr, 0x0B, 12) # write Red value
print i2c.read_byte_data(addr, 0x91) # get Red value
i2c.write_byte_data(addr, 0x0C, 123) # write Green value
print i2c.read_byte_data(addr, 0x92) # get Green value
i2c.write_byte_data(addr, 0x0D, 234) # write Blue value
print i2c.read_byte_data(addr, 0x93) # get Blue value
print i2c.read_i2c_block_data(addr, 0x90, 3) # get RGB
i2c.write_i2c_block_data(addr, 0x0A, RGB) # set all RGB
print i2c.read_i2c_block_data(addr, 0x90, 3) # get all RGB
print i2c.read_i2c_block_data(addr, 0x10, 3) # force error
Instructions in Detail
Master (Rpi, Python) Slave (Arduino
Bus.write_quick(slave)
Used to check presence, or trigger event in slave without data
transfer.
Wire.onReceive() event triggered, but no data is sent.
Bytes received: 0. Bytes returned: 0.
Bus.write_byte(slave, data)
Can be used to instruct the slave to do any of up to 255 different
actions, or to place this byte in one predefined byte variable.
Wire.onReceive() event triggered. Single byte received.
Bytes received: 1. Bytes returned: 0.
ByteValue = Bus.read_byte(addr)
Read slave status or a single predefined value
Wire.onRequest() event triggered only. No data received.
Slave must return one defined byte.
Bytes received: 0. Bytes returned: 1.
Bus.write_byte_data(addr, command, byteValue)
Send slave some information to accompany a command.
Wire.onReceive() event triggered. Two bytes sent. First byte is a
command, second byte is the byte data to accompany it.
Bytes received: 2. Bytes returned: 0.
ByteValue = Bus.read_byte_data(addr, command)
Interrogate a slave about a specific piece of information
Wire.onReceive event triggered. One byte sent, a command for
which byte is requested from slave. Wire.onRequest() then
triggered, and one byte to be returned.
Bytes received: 1. Bytes returned: 1
Instructions in Detail
Master (Rpi, Python) Slave (Arduino
Bus.write_word_data(addr, command, integerVal)
Send slave extra information accompanying a specific command
Wire.onReceive() event triggered, three bytes send. First byte is
command, second is LSB, third is MSB of integer.
Bytes received: 3. Bytes returned: 0.
WordValue = Bus.read_word_data(addr, command)
Retrieve two bytes, first LSB, then MSB of an integer. Python knows
to rebuild the integer. Retrieve integer data from slave.
Wire.onReceive() event triggered. Single byte received, a
command. Wire.onRequest() event triggered, slave must send back
two bytes, first LSB, then MSB, of an integer.
Bytes received: 1. Bytes returned: 2.
Bus.write_block_data(addr, command, [list of bytes])
Sending unstructured data.
Wire.onReceive() event triggered. Several bytes sent. First byte is
command, second is number of following bytes, remainder of bytes
must be processes according to interface list.
Bytes received: > 2. Bytes returned: 0.
Bus.write_i2c_block_data(addr, command, [list of bytes])
Use this to fill a table of related bytes quickly.
Wire.onReceive() event triggered. Several bytes sent. First byte is a
command, remaining bytes to be processed according to interface.
Bytes received: > 1. Bytes returned: 0.
ByteList = Bus.read_i2c_block_data(addr, command)
Use this to read a table of related bytes quickly
Wire.onReceive event triggered. One byte sent, a command for
which byte is requested from slave. Wire.onRequest() then
triggered, requested bytes returned as per interface list.
Bytes received: 1. Bytes returned: > 1
Instructions in Detail
Master (Rpi, Python) Slave (Arduino
List = bus.read_block_data(addr, command, bytes)
will fail. Always returns the empty list. Do not use this function.
Wire.onReceive() event triggered, two bytes send. First byte is
command, second is number of bytes to return. OnRequest() event
is triggered, sending back the correct number of bytes
Bytes received: 2. Bytes returned: > 1.
Bus.block_process_call(addr, command, [vals])
Following the protocol, it reads the correct number of bytes sent
back, but random data appears in the list returned. Do not use.
Wire.onReceive() event triggered. Several bytes received, first
command, then count of bytes in [vals], then vals.
Wire.onRequest() triggered, return first count, then number of bytes
Bytes received: > 2. Bytes returned: > 2.
process_call(addr, command, val) does sent the integer 'val', but
does not trigger the interrupt to return data, so it returns the empty
list
Wire.onReceive() event triggered. Three bytes sent. First byte is
command, second is LSB and last is MSB. SMBus Specification is
to return two byte integer, but onRequest() event never triggered.
Bytes received: 3. Bytes returned: n/a.
Conclusions
Communication over I2C is quite simple to
implement using the SMBus library on the
Raspberry Pi, and the Wire.h library on the
Arduino..
Knowing what each SMBus Write and Read
instruction sends to the Arduino and what data
the Arduino is expected to send back is crucial
to successful implementation of the I2C/SMBus
protocol.
Before coding, have a clear Interface
Specification with a list of commands to be sent
to the Arduino, and clear instructions of what
should happen with the data sent and how to
return requested data.
It is also important to specify the reaction to
bad data.
The SMBus protocol document can be found at
http://smbus.org/specs/smbus20.pdf
The linux Python implementation document can be
found at
https://www.kernel.org/doc/Documentation/i2c/smb
us-protocol
Some of the SMBus protocol is not fully
programmed in the existing SMBus python
libraries, even though the functions are
available to include in the program.
These functions do not appear to work with the
arduino:
● read_block_data(addr, command, bytes)
● block_process_call(addr, command, [vals])
● process_call(addr, command, val)
All the other functions appear to operate
according to the specification.
This work is licensed under the
Creative Commons Attribution-
ShareAlike 4.0 International License.
To view a copy of this license, visit
http://creativecommons.org/licenses/b
y-sa/4.0/.
Compiled by Mike Ochtman.
Find me at
https://za.linkedin.com/in/mikeochtman

More Related Content

What's hot (20)

Vx works RTOS
Vx works RTOSVx works RTOS
Vx works RTOS
Sai Malleswar
 
Chapter1.slides
Chapter1.slidesChapter1.slides
Chapter1.slides
Avinash Pillai
 
test generation
test generationtest generation
test generation
dennis gookyi
 
High Performance Computer Architecture
High Performance Computer ArchitectureHigh Performance Computer Architecture
High Performance Computer Architecture
Subhasis Dash
 
Physical symbol system
Physical symbol systemPhysical symbol system
Physical symbol system
nida unapprochablestair
 
Embedded C - Lecture 1
Embedded C - Lecture 1Embedded C - Lecture 1
Embedded C - Lecture 1
Mohamed Abdallah
 
03_03_Implementing_PCIe_ATS_in_ARM-based_SoCs_Final
03_03_Implementing_PCIe_ATS_in_ARM-based_SoCs_Final03_03_Implementing_PCIe_ATS_in_ARM-based_SoCs_Final
03_03_Implementing_PCIe_ATS_in_ARM-based_SoCs_Final
Gopi Krishnamurthy
 
Synchronous and asynchronous clock
Synchronous and asynchronous clockSynchronous and asynchronous clock
Synchronous and asynchronous clock
Nallapati Anindra
 
04~chapter 02 dft.ppt
04~chapter 02 dft.ppt04~chapter 02 dft.ppt
04~chapter 02 dft.ppt
SandipSolanki10
 
Firefly algorithm
Firefly algorithmFirefly algorithm
Firefly algorithm
supriya shilwant
 
1.ripple carry adder, full adder implementation using half adder.
1.ripple carry adder, full adder implementation using half adder.1.ripple carry adder, full adder implementation using half adder.
1.ripple carry adder, full adder implementation using half adder.
MdFazleRabbi18
 
JAVA APPLET BASICS
JAVA APPLET BASICSJAVA APPLET BASICS
JAVA APPLET BASICS
Shanid Malayil
 
Embedded c
Embedded cEmbedded c
Embedded c
Ami Prakash
 
Vlsi design-styles
Vlsi design-stylesVlsi design-styles
Vlsi design-styles
Praveen kumar Deverkonda
 
ACRi HLSチャレンジ 高速化テクニック紹介
ACRi HLSチャレンジ 高速化テクニック紹介ACRi HLSチャレンジ 高速化テクニック紹介
ACRi HLSチャレンジ 高速化テクニック紹介
Jun Ando
 
AI_Session 29 Graphplan algorithm.pptx
AI_Session 29 Graphplan algorithm.pptxAI_Session 29 Graphplan algorithm.pptx
AI_Session 29 Graphplan algorithm.pptx
Guru Nanak Technical Institutions
 
ASIC vs SOC vs FPGA
ASIC  vs SOC  vs FPGAASIC  vs SOC  vs FPGA
ASIC vs SOC vs FPGA
Verification Excellence
 
Synchronous and asynchronous reset
Synchronous and asynchronous resetSynchronous and asynchronous reset
Synchronous and asynchronous reset
Nallapati Anindra
 
SPI introduction(Serial Peripheral Interface)
SPI introduction(Serial Peripheral Interface)SPI introduction(Serial Peripheral Interface)
SPI introduction(Serial Peripheral Interface)
SUNODH GARLAPATI
 
Anfis (1)
Anfis (1)Anfis (1)
Anfis (1)
TarekBarhoum
 
High Performance Computer Architecture
High Performance Computer ArchitectureHigh Performance Computer Architecture
High Performance Computer Architecture
Subhasis Dash
 
03_03_Implementing_PCIe_ATS_in_ARM-based_SoCs_Final
03_03_Implementing_PCIe_ATS_in_ARM-based_SoCs_Final03_03_Implementing_PCIe_ATS_in_ARM-based_SoCs_Final
03_03_Implementing_PCIe_ATS_in_ARM-based_SoCs_Final
Gopi Krishnamurthy
 
Synchronous and asynchronous clock
Synchronous and asynchronous clockSynchronous and asynchronous clock
Synchronous and asynchronous clock
Nallapati Anindra
 
1.ripple carry adder, full adder implementation using half adder.
1.ripple carry adder, full adder implementation using half adder.1.ripple carry adder, full adder implementation using half adder.
1.ripple carry adder, full adder implementation using half adder.
MdFazleRabbi18
 
ACRi HLSチャレンジ 高速化テクニック紹介
ACRi HLSチャレンジ 高速化テクニック紹介ACRi HLSチャレンジ 高速化テクニック紹介
ACRi HLSチャレンジ 高速化テクニック紹介
Jun Ando
 
Synchronous and asynchronous reset
Synchronous and asynchronous resetSynchronous and asynchronous reset
Synchronous and asynchronous reset
Nallapati Anindra
 
SPI introduction(Serial Peripheral Interface)
SPI introduction(Serial Peripheral Interface)SPI introduction(Serial Peripheral Interface)
SPI introduction(Serial Peripheral Interface)
SUNODH GARLAPATI
 

Viewers also liked (20)

I2C Bus (Inter-Integrated Circuit)
I2C Bus (Inter-Integrated Circuit)I2C Bus (Inter-Integrated Circuit)
I2C Bus (Inter-Integrated Circuit)
Varun Mahajan
 
A seminar report on Raspberry Pi
A seminar report on Raspberry PiA seminar report on Raspberry Pi
A seminar report on Raspberry Pi
nipunmaster
 
Arduino & raspberry pi - Un connubio stimolante
Arduino & raspberry pi - Un connubio stimolanteArduino & raspberry pi - Un connubio stimolante
Arduino & raspberry pi - Un connubio stimolante
Mirco Sbrollini
 
What is Firewall?
What is Firewall?What is Firewall?
What is Firewall?
NetProtocol Xpert
 
Arduino (terminado)
Arduino (terminado)Arduino (terminado)
Arduino (terminado)
Sergio Serrano Calviño
 
NGFW: MARKET GROWTH, DEPLOYMENTS, AND NSS TEST RESULTS
NGFW: MARKET GROWTH, DEPLOYMENTS, AND NSS TEST RESULTSNGFW: MARKET GROWTH, DEPLOYMENTS, AND NSS TEST RESULTS
NGFW: MARKET GROWTH, DEPLOYMENTS, AND NSS TEST RESULTS
NSS Labs
 
I2 c bus
I2 c busI2 c bus
I2 c bus
Akhil Srivastava
 
PR_ALT_28072015_SiConTech_acquisition
PR_ALT_28072015_SiConTech_acquisitionPR_ALT_28072015_SiConTech_acquisition
PR_ALT_28072015_SiConTech_acquisition
Akhil Srivastava
 
Arduino arduino boardnano
Arduino   arduino boardnanoArduino   arduino boardnano
Arduino arduino boardnano
clickengenharia
 
I2C Subsystem In Linux-2.6.24
I2C Subsystem In Linux-2.6.24I2C Subsystem In Linux-2.6.24
I2C Subsystem In Linux-2.6.24
Varun Mahajan
 
Arduino nanomanual23
Arduino nanomanual23Arduino nanomanual23
Arduino nanomanual23
clickengenharia
 
PT Docs on bpm'online English version
PT Docs on bpm'online English versionPT Docs on bpm'online English version
PT Docs on bpm'online English version
ООО "Программные Технологии"
 
Network Security: Protecting SOHO Networks
Network Security: Protecting SOHO NetworksNetwork Security: Protecting SOHO Networks
Network Security: Protecting SOHO Networks
Jim Gilsinn
 
S3 Group on Code Management - RDK Users Conference 2014
S3 Group on Code Management - RDK Users Conference 2014S3 Group on Code Management - RDK Users Conference 2014
S3 Group on Code Management - RDK Users Conference 2014
S3 Group | TV Technology
 
HKG15-506: Comcast - Lessons learned from migrating the RDK code base to the ...
HKG15-506: Comcast - Lessons learned from migrating the RDK code base to the ...HKG15-506: Comcast - Lessons learned from migrating the RDK code base to the ...
HKG15-506: Comcast - Lessons learned from migrating the RDK code base to the ...
Linaro
 
Reverse car-parking
Reverse car-parkingReverse car-parking
Reverse car-parking
Salehin Rahman Khan
 
Решения Cisco для обеспечения кибербезопасности промышленных систем автоматиз...
Решения Cisco для обеспечения кибербезопасности промышленных систем автоматиз...Решения Cisco для обеспечения кибербезопасности промышленных систем автоматиз...
Решения Cisco для обеспечения кибербезопасности промышленных систем автоматиз...
Компания УЦСБ
 
Размещение презентаций в Internet
Размещение презентаций в InternetРазмещение презентаций в Internet
Размещение презентаций в Internet
anxesenpa
 
Годовой отчет Cisco по информационной безопасности за 2016 год
Годовой отчет Cisco по информационной безопасности за 2016 годГодовой отчет Cisco по информационной безопасности за 2016 год
Годовой отчет Cisco по информационной безопасности за 2016 год
Cisco Russia
 
How to Solve Real-Time Data Problems
How to Solve Real-Time Data ProblemsHow to Solve Real-Time Data Problems
How to Solve Real-Time Data Problems
IBM Power Systems
 
I2C Bus (Inter-Integrated Circuit)
I2C Bus (Inter-Integrated Circuit)I2C Bus (Inter-Integrated Circuit)
I2C Bus (Inter-Integrated Circuit)
Varun Mahajan
 
A seminar report on Raspberry Pi
A seminar report on Raspberry PiA seminar report on Raspberry Pi
A seminar report on Raspberry Pi
nipunmaster
 
Arduino & raspberry pi - Un connubio stimolante
Arduino & raspberry pi - Un connubio stimolanteArduino & raspberry pi - Un connubio stimolante
Arduino & raspberry pi - Un connubio stimolante
Mirco Sbrollini
 
NGFW: MARKET GROWTH, DEPLOYMENTS, AND NSS TEST RESULTS
NGFW: MARKET GROWTH, DEPLOYMENTS, AND NSS TEST RESULTSNGFW: MARKET GROWTH, DEPLOYMENTS, AND NSS TEST RESULTS
NGFW: MARKET GROWTH, DEPLOYMENTS, AND NSS TEST RESULTS
NSS Labs
 
PR_ALT_28072015_SiConTech_acquisition
PR_ALT_28072015_SiConTech_acquisitionPR_ALT_28072015_SiConTech_acquisition
PR_ALT_28072015_SiConTech_acquisition
Akhil Srivastava
 
Arduino arduino boardnano
Arduino   arduino boardnanoArduino   arduino boardnano
Arduino arduino boardnano
clickengenharia
 
I2C Subsystem In Linux-2.6.24
I2C Subsystem In Linux-2.6.24I2C Subsystem In Linux-2.6.24
I2C Subsystem In Linux-2.6.24
Varun Mahajan
 
Network Security: Protecting SOHO Networks
Network Security: Protecting SOHO NetworksNetwork Security: Protecting SOHO Networks
Network Security: Protecting SOHO Networks
Jim Gilsinn
 
S3 Group on Code Management - RDK Users Conference 2014
S3 Group on Code Management - RDK Users Conference 2014S3 Group on Code Management - RDK Users Conference 2014
S3 Group on Code Management - RDK Users Conference 2014
S3 Group | TV Technology
 
HKG15-506: Comcast - Lessons learned from migrating the RDK code base to the ...
HKG15-506: Comcast - Lessons learned from migrating the RDK code base to the ...HKG15-506: Comcast - Lessons learned from migrating the RDK code base to the ...
HKG15-506: Comcast - Lessons learned from migrating the RDK code base to the ...
Linaro
 
Решения Cisco для обеспечения кибербезопасности промышленных систем автоматиз...
Решения Cisco для обеспечения кибербезопасности промышленных систем автоматиз...Решения Cisco для обеспечения кибербезопасности промышленных систем автоматиз...
Решения Cisco для обеспечения кибербезопасности промышленных систем автоматиз...
Компания УЦСБ
 
Размещение презентаций в Internet
Размещение презентаций в InternetРазмещение презентаций в Internet
Размещение презентаций в Internet
anxesenpa
 
Годовой отчет Cisco по информационной безопасности за 2016 год
Годовой отчет Cisco по информационной безопасности за 2016 годГодовой отчет Cisco по информационной безопасности за 2016 год
Годовой отчет Cisco по информационной безопасности за 2016 год
Cisco Russia
 
How to Solve Real-Time Data Problems
How to Solve Real-Time Data ProblemsHow to Solve Real-Time Data Problems
How to Solve Real-Time Data Problems
IBM Power Systems
 
Ad

Similar to I2c interfacing raspberry pi to arduino (20)

ELC 2016 - I2C hacking demystified
ELC 2016 - I2C hacking demystifiedELC 2016 - I2C hacking demystified
ELC 2016 - I2C hacking demystified
Igor Stoppa
 
ARDUINO AND ITS PIN CONFIGURATION
 ARDUINO AND ITS PIN  CONFIGURATION ARDUINO AND ITS PIN  CONFIGURATION
ARDUINO AND ITS PIN CONFIGURATION
soma saikiran
 
Using arduino and raspberry pi for internet of things
Using arduino and raspberry pi for internet of thingsUsing arduino and raspberry pi for internet of things
Using arduino and raspberry pi for internet of things
Sudar Muthu
 
M.Tech Internet of Things Unit - III.pptx
M.Tech Internet of Things Unit - III.pptxM.Tech Internet of Things Unit - III.pptx
M.Tech Internet of Things Unit - III.pptx
AvinashAvuthu2
 
IoT Physical Devices and End Points.pdf
IoT Physical Devices and End Points.pdfIoT Physical Devices and End Points.pdf
IoT Physical Devices and End Points.pdf
GVNSK Sravya
 
How to use an Arduino
How to use an ArduinoHow to use an Arduino
How to use an Arduino
AntonAndreev13
 
Raspberry Pi with Java 8
Raspberry Pi with Java 8Raspberry Pi with Java 8
Raspberry Pi with Java 8
javafxpert
 
Arduino Programming - Brief Introduction
Arduino Programming - Brief IntroductionArduino Programming - Brief Introduction
Arduino Programming - Brief Introduction
NEEVEE Technologies
 
Getting Started With Raspberry Pi - UCSD 2013
Getting Started With Raspberry Pi - UCSD 2013Getting Started With Raspberry Pi - UCSD 2013
Getting Started With Raspberry Pi - UCSD 2013
Tom Paulus
 
Taking the hard out of hardware
Taking the hard out of hardwareTaking the hard out of hardware
Taking the hard out of hardware
Ronald McCollam
 
Raspberry Pi - best friend for all your GPIO needs
Raspberry Pi - best friend for all your GPIO needsRaspberry Pi - best friend for all your GPIO needs
Raspberry Pi - best friend for all your GPIO needs
Dobrica Pavlinušić
 
Arduino
ArduinoArduino
Arduino
Jerin John
 
Sensors and Actuators in Arduino, Introduction
Sensors and Actuators in Arduino, IntroductionSensors and Actuators in Arduino, Introduction
Sensors and Actuators in Arduino, Introduction
BibekPokhrel13
 
Arduino spooky projects_class3
Arduino spooky projects_class3Arduino spooky projects_class3
Arduino spooky projects_class3
Anil Yadav
 
Interfacing the Raspberry Pi to the World
Interfacing the Raspberry Pi to the WorldInterfacing the Raspberry Pi to the World
Interfacing the Raspberry Pi to the World
Omer Kilic
 
An hemmanur
An hemmanurAn hemmanur
An hemmanur
Sangeetha Marikkannan
 
Getting Started with Raspberry Pi - USC 2013
Getting Started with Raspberry Pi - USC 2013Getting Started with Raspberry Pi - USC 2013
Getting Started with Raspberry Pi - USC 2013
Tom Paulus
 
Embedded Systems: Lecture 9: The Pi Control ARM
Embedded Systems: Lecture 9: The Pi Control ARMEmbedded Systems: Lecture 9: The Pi Control ARM
Embedded Systems: Lecture 9: The Pi Control ARM
Ahmed El-Arabawy
 
Arduino - Learning.pdf
Arduino - Learning.pdfArduino - Learning.pdf
Arduino - Learning.pdf
KhalilSedki1
 
Raspberry-Pi
Raspberry-PiRaspberry-Pi
Raspberry-Pi
Rehan Fazal
 
ELC 2016 - I2C hacking demystified
ELC 2016 - I2C hacking demystifiedELC 2016 - I2C hacking demystified
ELC 2016 - I2C hacking demystified
Igor Stoppa
 
ARDUINO AND ITS PIN CONFIGURATION
 ARDUINO AND ITS PIN  CONFIGURATION ARDUINO AND ITS PIN  CONFIGURATION
ARDUINO AND ITS PIN CONFIGURATION
soma saikiran
 
Using arduino and raspberry pi for internet of things
Using arduino and raspberry pi for internet of thingsUsing arduino and raspberry pi for internet of things
Using arduino and raspberry pi for internet of things
Sudar Muthu
 
M.Tech Internet of Things Unit - III.pptx
M.Tech Internet of Things Unit - III.pptxM.Tech Internet of Things Unit - III.pptx
M.Tech Internet of Things Unit - III.pptx
AvinashAvuthu2
 
IoT Physical Devices and End Points.pdf
IoT Physical Devices and End Points.pdfIoT Physical Devices and End Points.pdf
IoT Physical Devices and End Points.pdf
GVNSK Sravya
 
Raspberry Pi with Java 8
Raspberry Pi with Java 8Raspberry Pi with Java 8
Raspberry Pi with Java 8
javafxpert
 
Arduino Programming - Brief Introduction
Arduino Programming - Brief IntroductionArduino Programming - Brief Introduction
Arduino Programming - Brief Introduction
NEEVEE Technologies
 
Getting Started With Raspberry Pi - UCSD 2013
Getting Started With Raspberry Pi - UCSD 2013Getting Started With Raspberry Pi - UCSD 2013
Getting Started With Raspberry Pi - UCSD 2013
Tom Paulus
 
Taking the hard out of hardware
Taking the hard out of hardwareTaking the hard out of hardware
Taking the hard out of hardware
Ronald McCollam
 
Raspberry Pi - best friend for all your GPIO needs
Raspberry Pi - best friend for all your GPIO needsRaspberry Pi - best friend for all your GPIO needs
Raspberry Pi - best friend for all your GPIO needs
Dobrica Pavlinušić
 
Sensors and Actuators in Arduino, Introduction
Sensors and Actuators in Arduino, IntroductionSensors and Actuators in Arduino, Introduction
Sensors and Actuators in Arduino, Introduction
BibekPokhrel13
 
Arduino spooky projects_class3
Arduino spooky projects_class3Arduino spooky projects_class3
Arduino spooky projects_class3
Anil Yadav
 
Interfacing the Raspberry Pi to the World
Interfacing the Raspberry Pi to the WorldInterfacing the Raspberry Pi to the World
Interfacing the Raspberry Pi to the World
Omer Kilic
 
Getting Started with Raspberry Pi - USC 2013
Getting Started with Raspberry Pi - USC 2013Getting Started with Raspberry Pi - USC 2013
Getting Started with Raspberry Pi - USC 2013
Tom Paulus
 
Embedded Systems: Lecture 9: The Pi Control ARM
Embedded Systems: Lecture 9: The Pi Control ARMEmbedded Systems: Lecture 9: The Pi Control ARM
Embedded Systems: Lecture 9: The Pi Control ARM
Ahmed El-Arabawy
 
Arduino - Learning.pdf
Arduino - Learning.pdfArduino - Learning.pdf
Arduino - Learning.pdf
KhalilSedki1
 
Ad

Recently uploaded (13)

computer organisation algorithm power point presentation
computer organisation algorithm power point presentationcomputer organisation algorithm power point presentation
computer organisation algorithm power point presentation
rocky
 
8937-14549-2-PB.pdfseeeeerrerrrruuyyyyyyyy
8937-14549-2-PB.pdfseeeeerrerrrruuyyyyyyyy8937-14549-2-PB.pdfseeeeerrerrrruuyyyyyyyy
8937-14549-2-PB.pdfseeeeerrerrrruuyyyyyyyy
AbdullahiMuhammadMus3
 
VisualizationNNNNNNNNNNNNNNNNNNNNNNNNNN_24_25.pptx
VisualizationNNNNNNNNNNNNNNNNNNNNNNNNNN_24_25.pptxVisualizationNNNNNNNNNNNNNNNNNNNNNNNNNN_24_25.pptx
VisualizationNNNNNNNNNNNNNNNNNNNNNNNNNN_24_25.pptx
silviaramosdelgadoua
 
AI_Traffic_Management_Presentation (2).pptx
AI_Traffic_Management_Presentation (2).pptxAI_Traffic_Management_Presentation (2).pptx
AI_Traffic_Management_Presentation (2).pptx
rohitkumbarhall
 
[Back2School] Delay Calculation- Chapter 2
[Back2School] Delay Calculation- Chapter 2[Back2School] Delay Calculation- Chapter 2
[Back2School] Delay Calculation- Chapter 2
Ahmed Abdelazeem
 
578670211-MPMC-8051-Microcontroller.pptx
578670211-MPMC-8051-Microcontroller.pptx578670211-MPMC-8051-Microcontroller.pptx
578670211-MPMC-8051-Microcontroller.pptx
kovurukishore9
 
network-layer-forohhfbjhgvdefhnnmuzan.pdf
network-layer-forohhfbjhgvdefhnnmuzan.pdfnetwork-layer-forohhfbjhgvdefhnnmuzan.pdf
network-layer-forohhfbjhgvdefhnnmuzan.pdf
himanshumis2022
 
美国学历认证范本爱荷华州立大学成绩单底纹防伪ISU在读证明信仿制
美国学历认证范本爱荷华州立大学成绩单底纹防伪ISU在读证明信仿制美国学历认证范本爱荷华州立大学成绩单底纹防伪ISU在读证明信仿制
美国学历认证范本爱荷华州立大学成绩单底纹防伪ISU在读证明信仿制
Taqyea
 
Enhancing EFL Student Participation in Academic Lectures.pdf
Enhancing EFL Student Participation in Academic Lectures.pdfEnhancing EFL Student Participation in Academic Lectures.pdf
Enhancing EFL Student Participation in Academic Lectures.pdf
masoudmasoudpour
 
Bharat Green E waste Recycling Scrap.pdf
Bharat Green E waste Recycling Scrap.pdfBharat Green E waste Recycling Scrap.pdf
Bharat Green E waste Recycling Scrap.pdf
bharatgreenewasterec
 
Melt Flow Index Tester from Perfect Group India
Melt Flow Index Tester from Perfect Group IndiaMelt Flow Index Tester from Perfect Group India
Melt Flow Index Tester from Perfect Group India
perfectgroup india123
 
Case study for students dhsuhayvavvsuh cse (1).pdf
Case study for students dhsuhayvavvsuh cse (1).pdfCase study for students dhsuhayvavvsuh cse (1).pdf
Case study for students dhsuhayvavvsuh cse (1).pdf
ssuserf31e8b
 
Document from Ronit in which discussion about business
Document from Ronit in which discussion about businessDocument from Ronit in which discussion about business
Document from Ronit in which discussion about business
RonitKumar611570
 
computer organisation algorithm power point presentation
computer organisation algorithm power point presentationcomputer organisation algorithm power point presentation
computer organisation algorithm power point presentation
rocky
 
8937-14549-2-PB.pdfseeeeerrerrrruuyyyyyyyy
8937-14549-2-PB.pdfseeeeerrerrrruuyyyyyyyy8937-14549-2-PB.pdfseeeeerrerrrruuyyyyyyyy
8937-14549-2-PB.pdfseeeeerrerrrruuyyyyyyyy
AbdullahiMuhammadMus3
 
VisualizationNNNNNNNNNNNNNNNNNNNNNNNNNN_24_25.pptx
VisualizationNNNNNNNNNNNNNNNNNNNNNNNNNN_24_25.pptxVisualizationNNNNNNNNNNNNNNNNNNNNNNNNNN_24_25.pptx
VisualizationNNNNNNNNNNNNNNNNNNNNNNNNNN_24_25.pptx
silviaramosdelgadoua
 
AI_Traffic_Management_Presentation (2).pptx
AI_Traffic_Management_Presentation (2).pptxAI_Traffic_Management_Presentation (2).pptx
AI_Traffic_Management_Presentation (2).pptx
rohitkumbarhall
 
[Back2School] Delay Calculation- Chapter 2
[Back2School] Delay Calculation- Chapter 2[Back2School] Delay Calculation- Chapter 2
[Back2School] Delay Calculation- Chapter 2
Ahmed Abdelazeem
 
578670211-MPMC-8051-Microcontroller.pptx
578670211-MPMC-8051-Microcontroller.pptx578670211-MPMC-8051-Microcontroller.pptx
578670211-MPMC-8051-Microcontroller.pptx
kovurukishore9
 
network-layer-forohhfbjhgvdefhnnmuzan.pdf
network-layer-forohhfbjhgvdefhnnmuzan.pdfnetwork-layer-forohhfbjhgvdefhnnmuzan.pdf
network-layer-forohhfbjhgvdefhnnmuzan.pdf
himanshumis2022
 
美国学历认证范本爱荷华州立大学成绩单底纹防伪ISU在读证明信仿制
美国学历认证范本爱荷华州立大学成绩单底纹防伪ISU在读证明信仿制美国学历认证范本爱荷华州立大学成绩单底纹防伪ISU在读证明信仿制
美国学历认证范本爱荷华州立大学成绩单底纹防伪ISU在读证明信仿制
Taqyea
 
Enhancing EFL Student Participation in Academic Lectures.pdf
Enhancing EFL Student Participation in Academic Lectures.pdfEnhancing EFL Student Participation in Academic Lectures.pdf
Enhancing EFL Student Participation in Academic Lectures.pdf
masoudmasoudpour
 
Bharat Green E waste Recycling Scrap.pdf
Bharat Green E waste Recycling Scrap.pdfBharat Green E waste Recycling Scrap.pdf
Bharat Green E waste Recycling Scrap.pdf
bharatgreenewasterec
 
Melt Flow Index Tester from Perfect Group India
Melt Flow Index Tester from Perfect Group IndiaMelt Flow Index Tester from Perfect Group India
Melt Flow Index Tester from Perfect Group India
perfectgroup india123
 
Case study for students dhsuhayvavvsuh cse (1).pdf
Case study for students dhsuhayvavvsuh cse (1).pdfCase study for students dhsuhayvavvsuh cse (1).pdf
Case study for students dhsuhayvavvsuh cse (1).pdf
ssuserf31e8b
 
Document from Ronit in which discussion about business
Document from Ronit in which discussion about businessDocument from Ronit in which discussion about business
Document from Ronit in which discussion about business
RonitKumar611570
 

I2c interfacing raspberry pi to arduino

  • 1. Connecting Raspberry Pi to Arduino using I2C Raspberry Pi This work is licensed under the Creative Commons Attribution- ShareAlike 4.0 International License. To view a copy of this license, visit http://creativecommons.org/licenses/b y-sa/4.0/. Revision 2 Companion Github
  • 2. What is I2C? The Inter-IC Bus (I-IC or I2C) standard defines the hardware and electrical characteristics of the interface between nearby devices using only two wires (and a third for ground reference). SMBus was introduced by Intel as a tight subset of I2C, strictly defining the interface between devices. It is commonly used in televisions, computer components, and many ADC and DAC and GPS devices. The Raspberry Pi most commonly uses an SMBus implementation in Python 2.x, and this is what we will concentrate on in this document.
  • 3. Connecting Devices Identify SDA, SCL, and GND pins on both Raspberry Pi and the Arduino. Connect SDA to SDA, SCL to SCL, and GND to GND between the two devices. It is possible to connect the two devices directly to one another without a level shifter, but it is not best practice. I2C levels for a low signal is 0.3Vcc and for a high, 0.7Vcc. With the Raspberry Pi being a 3.3V device and the Arduino requiring 5V for Vcc, a logic level 'high' coming from the 3.3V Raspberry Pi is slightly below the 0.7*5= 3.5V required for a definite logic 'high' in the Arduino.
  • 4. Voltage Levels The Raspberry Pi is a 3.3V device while the Arduino is a 5V device, but because both devices are connected in open-drain configuration with relatively high pull-up resistor values, it is unlikely damage will occur. The problem is that the communication between the two devices is not guaranteed to work well due to the 3.5V minimum logic level 'high' required by the Arduino, and the Raspberry Pi input is not 5V resistant. A level shifter isolates the two different voltages, while transmitting on/off information in both directions. Having said that, I have had reliable communication between the Raspberry Pi and the Arduino without any loss of data, but I am worried about the Arduino accidently driving one of the SDA or SCL pins to 5V as an output if the program is not written carefully and damaging the Raspberry Pi. User beware.
  • 5. I2C Level Shifter This rather complicated-looking circuit creates a bi-directional bus that can automatically translate 3.3V bus signals into 5V signals and vice versa at full bus speed. This is one of the simplest and cheapest level shifters and can easily be built on a breadboard or soldered in a few minutes on any of the prototyping stripboards available. On the next slide, we look at this circuit in detail
  • 6. The Level Shifter Isolating one of the two identical bus lines, we find an enhancement-mode n-channel MOSFET the star of the show. It's Gate is tied directly to the low-voltage Vcc. A pull-up resistor connects the High voltage side to the Drain, and another pulls the Source up to the Low voltage side. S1 and S2 simulate the Open-Drain connection that drives the bus at the microcontroller. With both switches open, Gate and Source are at the same potential so the transistor is turned off. Both sides are pulled up to their respective Vcc. With S1 closed and S1 open, the source is pulled down to 0V, taking Vgs (Gate-Source Voltage) above the threshold and turning the transistor on hard. This pulls the Drain side down to 0V as well. With S2 closed and S1 open, Drain is pulled to 0V and the internal diode is forward-biased by the 3.3V, dropping the source to around 0.6V. This is enough to pull Vgs again beyond the threshold, opening the transistor and dragging the bus down to 0V. With both switches closed, both sides will be at 0V.
  • 7. Setting Up Raspberry Pi Getting the tools for Python2 and/or Python3... 1. Open a terminal window. Enter “sudo apt-get install python-smbus” (2.x) Or “sudo apt-get install python3-smbus” (3.x) And “sudo apt-get install i2c-tools” Reboot the Pi. 2. Open “Raspberry Pi Configuration” in the GUI or use a terminal to enter 'sudo raspi-config'. Enable I2C, save, and reboot. 3. Edit file 'etc/modules' using GUI text editor or enter “sudo nano etc/modules” If these two lines are not in there, type them; i2c-bcm2708 I2c-dev And save. 4. Edit file 'etc/modprobe.d/raspi-blacklist.comf' using GUI editor or Enter “sudo nano etc/modprobe.d/raspi-blacklist.conf”. If these two lines exist, make sure a '#' is placed before them, or delete them altogether.. #blacklist spi-bcm2708 #blacklist i2c-bcm2708 And save. 5. Finally, enter “sudo nano /boot/config.txt'. These two lines should appear: dtparam=i2c1=on dtparam=i2c_arm=on If not, make them so, and save. Reboot.
  • 8. Testing Raspberry Pi Enter “i2cdetect -y 1” in a terminal window to check that the I2C bus is available and running on the Pi. If everything is good, it will show a table of addresses. If any I2C devices are available, their addresses will be shown in hexadecimal. It is worth entering “i2cdetect -F 1” to see which SMBus calls are supported. It will save hours of debugging to know that “SMBus Block Read” is not supported, but “I2C Block Read” is supported, and that “Block Process Call” is meaningless as it is also not supported.
  • 9. Preparing the Raspberry Pi Start Python, and create a new file. Import the SMBus library. Create an SMBus object linked to I2C port 1. Define the slaves address(es) to connect to. Collect the data to be transmitted, or prepare the data variables for reading back from the slave. These instructions are for Python 2. Python 3 may have small differences. import smbus i2c_object = smbus.SMBus(1) # Link to SMBus(0) on older Pi addrSlave1 = 8 command = 0 dataList = [1,2,3,4,5] i2c_object.write_i2c_block_data(addrSlave1, command, DataList) getDataList = i2c_object.read_i2c_block_data( addrSlave1, command)
  • 10. Preparing the Arduino Start Arduino IDE Include the Wire.h standard library for Arduino. Set up the slave address. Register a Wire function that will run when the interrupt for receiving information from the Master triggers. The event is onReceive(function) This event will react to information coming from the master, and prepare for sending data back to the master, if necessary. Register a Wire function that will run when the interrupt for returning data to the Master triggers. This event is on onRequest(function) When the interrupt fires, send data to the Master that was requested. #include <Wire.h> const byte slaveAddr = 8; void setup() { Wire.begin(slaveAddr); Wire.onReceive(i2cReceive); Wire.onRequest(i2cTransmit); } void loop() { } void i2cReceive(int numBytes) { byte rxByte; while Wire.available() { rxByte = Wire.read(); // Do something with the byte } } Void i2cTransmit() { Wire.write(...) // send requested data }
  • 11. Example Project Using a Raspberry Pi 2 and an Arduino Leonardo, we will connect up the I2C bus, and connect an RGB LED to the Arduino. The LED color and brightness will be controlled by a Python program running on the Pi. We will also simulate analog data to send back to the Pi from the Arduino, a temperature sensor and a light-level sensor. The source code for both Arduino and Raspberry Pi can be found on github at mikeochtman.github.io/Pi_Arduino_I2C. This drawing was created in Fritzing.
  • 12. Interface Specification Before we can communicate with the Arduino, we need an interface specification which describes, in detail, how and what data should be moved over the bus from Master to Slave, and from Slave to Master. Type Description Access Byte Command private Byte Control private Real Temperature Read Only Real Light Level Read Only Byte Brightness Red Read/Write Byte Brightness Green Read/Write Byte Brightness Blue Read/Write Arduino Internal Data Table Command Action 0x81 Read Temperature. Return int(round(temperature*100)) 0x82 Read Light. Return int(round(light*100)) 0x0A Write three bytes for brightness RGB 0x0B Write single byte, brightness Red channel 0x0C Write single byte, brightness Green channel 0x0D Write single byte, brightness Blue channel 0x90 Read three bytes brightness RGB 0x91 Read single byte, brightness Red channel 0x92 Read single byte, brightness Green channel 0x93 Read single byte, brightness Blue channel Read, no command Return Slave Address, one Byte Write, No command Master interrogating slave presence. Ignore Other commands Ignore. Master software has to deal with communication exceptions, if any.
  • 13. Arduino Software//The full software can be found on github at // https://github.com/MikeOchtman/Pi_Arduino_I2C //This is a simplified collection of //the most important parts. #include <Wire.h> #define rxFault 0x80 #define txFault 0x40 #define slaveAddress 8 struct { byte volatile command; byte volatile control; float volatile temperature; float volatile light; byte volatile brightR; byte volatile brightG; byte volatile brightB; } commsTable; byte volatile txTable[32]; // prepare data for sending over I2C Void setup() { Wire.begin(slaveAddress); Wire.onReceive(i2cReceive); Wire.onRequest(i2cTransmit); } Void loop() { } void i2cReceive(int byteCount) { if (byteCount == 0) return; byte command = Wire.read(); commsTable.command = command; if (command < 0x80) { i2cHandleRx(command, byteCount - 1); } else { i2cHandleTx(command); } } byte i2cHandleRx(byte command, int numBytes) { switch (command) { case 0x0A: if (Wire.available() == 3) commsTable.brightR = Wire.read(); commsTable.brightG = Wire.read(); commsTable.brightB = Wire.read(); result = 3; } else { result = 0xFF; } break; // and so on, one case for each command according to the Interface Specification default: result = 0xFF; } if (result == 0xFF) commsTable.control |= rxFault; return result; }
  • 14. Arduino Software, cont'd byte i2cHandleTx(byte command) { // If you are here, the I2C Master has requested information // If there is anything we need to do before the interrupt // for the read takes place, this is where to do it. return 0; } void i2cTransmit() { // byte *txIndex = (byte*)&txTable[0]; byte numBytes = 0; int t = 0; switch (commsTable.command) { case 0x00: // send slaveAddress. txTable[0] = slaveAddress; numBytes = 1; break; case 0x81: // send temperature t = int(round(commsTable.temperature*100)); txTable[1] = (byte)(t >> 8); txTable[0] = (byte)(t & 0xFF); numBytes = 2; break; case 0x91: // send RGB Red channel txTable[0] = commsTable.brightR; numBytes = 1; break; // Again, create a case statement for each legal command default: commsTable.control |= txFault; } if (numBytes > 0) { Wire.write((byte *)&txTable, numBytes); } }
  • 15. Python Softwareimport smbus import time i2c = smbus.SMBus(1) addr = 8 # address of the arduino I2C ##/* Interface Specification ## Data in a table thus: ## byte purpose ## 0: command ## 1: control ## 2-5: Current Temperature (read-only) ## 6-9: Current light level (read only) ## 10: Brightness for RED r/w ## 11: Brightness for GREEN r/w ## 12: Brightness for BLUE r/w ## Commands: ## Write with no command: Ignore ## Read with no command: Return slave address ## Command 0x81: read temperature; ## Integer returned, int(round(temp*100)) ## Command 0x82: read light level; ## Integer returned, int(round(lux*100)) ## Command 0x0A: Write three bytes to RGB ## Command 0x0B: Write single byte brightness red; ## Command 0x0C: Write single byte brightness green; ## Command 0x0D: Write single byte brightness blue; ## Command 0x90: read three bytes brightness RGB ## Command 0x91: read single byte brightness red; ## Command 0x92: read single byte brightness green; ## Command 0x93: read single byte brightness blue; ## ## All other values are ignored, no data returned. RGB = [20,200,128] temperature = 0 light_level = 0 i2c.write_quick(addr) # no data expected back time.sleep(0.5) print i2c.read_byte(addr) # expect the slave address time.sleep(0.5) print i2c.read_word_data(addr,0x81)/100.0 # temperature time.sleep(0.5) print i2c.read_word_data(addr,0x82)/100.0 # light level time.sleep(0.5) i2c.write_byte_data(addr, 0x0B, 12) # write Red value time.sleep(0.5) print i2c.read_byte_data(addr, 0x91) # write Green value time.sleep(0.5) i2c.write_byte_data(addr, 0x0C, 123) # write Blue value time.sleep(0.5) print i2c.read_byte_data(addr, 0x92) # get Green value time.sleep(0.5) i2c.write_byte_data(addr, 0x0D, 234) # write Blue value time.sleep(0.5) print i2c.read_byte_data(addr, 0x93) # get Blue value time.sleep(0.5) print i2c.read_i2c_block_data(addr, 0x90, 3) # get RGB time.sleep(0.5) i2c.write_i2c_block_data(addr, 0x0A, RGB) # set all RGB time.sleep(0.5) print i2c.read_i2c_block_data(addr, 0x90, 3) # get all RGB time.sleep(0.5) print i2c.read_i2c_block_data(addr, 0x10, 3) # force error time.sleep(0.5)
  • 16. The Python ResultsPython 2.7.9 results. >>> 8 23.95 6.97 12 123 234 [12, 123, 234] [20, 200, 128] [0, 255, 255] >>> No event for write_quick() Got back the slave Address. Got the simulated temperature Got the simulated light level Set and read back Red channel Set and read back Green channel Set and read back Blue channel Got back RGB values as a list. Set new RGB values from a list Read back the RGB values as a list Forced a read error by sending wrong command. RGB = [20,200,128] i2c.write_quick(addr) # no data expected back print i2c.read_byte(addr) # expect the slave address print i2c.read_word_data(addr,0x81)/100.0 # temperature print i2c.read_word_data(addr,0x82)/100.0 # light level i2c.write_byte_data(addr, 0x0B, 12) # write Red value print i2c.read_byte_data(addr, 0x91) # get Red value i2c.write_byte_data(addr, 0x0C, 123) # write Green value print i2c.read_byte_data(addr, 0x92) # get Green value i2c.write_byte_data(addr, 0x0D, 234) # write Blue value print i2c.read_byte_data(addr, 0x93) # get Blue value print i2c.read_i2c_block_data(addr, 0x90, 3) # get RGB i2c.write_i2c_block_data(addr, 0x0A, RGB) # set all RGB print i2c.read_i2c_block_data(addr, 0x90, 3) # get all RGB print i2c.read_i2c_block_data(addr, 0x10, 3) # force error
  • 17. Instructions in Detail Master (Rpi, Python) Slave (Arduino Bus.write_quick(slave) Used to check presence, or trigger event in slave without data transfer. Wire.onReceive() event triggered, but no data is sent. Bytes received: 0. Bytes returned: 0. Bus.write_byte(slave, data) Can be used to instruct the slave to do any of up to 255 different actions, or to place this byte in one predefined byte variable. Wire.onReceive() event triggered. Single byte received. Bytes received: 1. Bytes returned: 0. ByteValue = Bus.read_byte(addr) Read slave status or a single predefined value Wire.onRequest() event triggered only. No data received. Slave must return one defined byte. Bytes received: 0. Bytes returned: 1. Bus.write_byte_data(addr, command, byteValue) Send slave some information to accompany a command. Wire.onReceive() event triggered. Two bytes sent. First byte is a command, second byte is the byte data to accompany it. Bytes received: 2. Bytes returned: 0. ByteValue = Bus.read_byte_data(addr, command) Interrogate a slave about a specific piece of information Wire.onReceive event triggered. One byte sent, a command for which byte is requested from slave. Wire.onRequest() then triggered, and one byte to be returned. Bytes received: 1. Bytes returned: 1
  • 18. Instructions in Detail Master (Rpi, Python) Slave (Arduino Bus.write_word_data(addr, command, integerVal) Send slave extra information accompanying a specific command Wire.onReceive() event triggered, three bytes send. First byte is command, second is LSB, third is MSB of integer. Bytes received: 3. Bytes returned: 0. WordValue = Bus.read_word_data(addr, command) Retrieve two bytes, first LSB, then MSB of an integer. Python knows to rebuild the integer. Retrieve integer data from slave. Wire.onReceive() event triggered. Single byte received, a command. Wire.onRequest() event triggered, slave must send back two bytes, first LSB, then MSB, of an integer. Bytes received: 1. Bytes returned: 2. Bus.write_block_data(addr, command, [list of bytes]) Sending unstructured data. Wire.onReceive() event triggered. Several bytes sent. First byte is command, second is number of following bytes, remainder of bytes must be processes according to interface list. Bytes received: > 2. Bytes returned: 0. Bus.write_i2c_block_data(addr, command, [list of bytes]) Use this to fill a table of related bytes quickly. Wire.onReceive() event triggered. Several bytes sent. First byte is a command, remaining bytes to be processed according to interface. Bytes received: > 1. Bytes returned: 0. ByteList = Bus.read_i2c_block_data(addr, command) Use this to read a table of related bytes quickly Wire.onReceive event triggered. One byte sent, a command for which byte is requested from slave. Wire.onRequest() then triggered, requested bytes returned as per interface list. Bytes received: 1. Bytes returned: > 1
  • 19. Instructions in Detail Master (Rpi, Python) Slave (Arduino List = bus.read_block_data(addr, command, bytes) will fail. Always returns the empty list. Do not use this function. Wire.onReceive() event triggered, two bytes send. First byte is command, second is number of bytes to return. OnRequest() event is triggered, sending back the correct number of bytes Bytes received: 2. Bytes returned: > 1. Bus.block_process_call(addr, command, [vals]) Following the protocol, it reads the correct number of bytes sent back, but random data appears in the list returned. Do not use. Wire.onReceive() event triggered. Several bytes received, first command, then count of bytes in [vals], then vals. Wire.onRequest() triggered, return first count, then number of bytes Bytes received: > 2. Bytes returned: > 2. process_call(addr, command, val) does sent the integer 'val', but does not trigger the interrupt to return data, so it returns the empty list Wire.onReceive() event triggered. Three bytes sent. First byte is command, second is LSB and last is MSB. SMBus Specification is to return two byte integer, but onRequest() event never triggered. Bytes received: 3. Bytes returned: n/a.
  • 20. Conclusions Communication over I2C is quite simple to implement using the SMBus library on the Raspberry Pi, and the Wire.h library on the Arduino.. Knowing what each SMBus Write and Read instruction sends to the Arduino and what data the Arduino is expected to send back is crucial to successful implementation of the I2C/SMBus protocol. Before coding, have a clear Interface Specification with a list of commands to be sent to the Arduino, and clear instructions of what should happen with the data sent and how to return requested data. It is also important to specify the reaction to bad data. The SMBus protocol document can be found at http://smbus.org/specs/smbus20.pdf The linux Python implementation document can be found at https://www.kernel.org/doc/Documentation/i2c/smb us-protocol Some of the SMBus protocol is not fully programmed in the existing SMBus python libraries, even though the functions are available to include in the program. These functions do not appear to work with the arduino: ● read_block_data(addr, command, bytes) ● block_process_call(addr, command, [vals]) ● process_call(addr, command, val) All the other functions appear to operate according to the specification. This work is licensed under the Creative Commons Attribution- ShareAlike 4.0 International License. To view a copy of this license, visit http://creativecommons.org/licenses/b y-sa/4.0/. Compiled by Mike Ochtman. Find me at https://za.linkedin.com/in/mikeochtman