Post Go back to editing

ADuCM355 I2C connection to Raspberry PI

Category: Software
Software Version: M355_I2C_Slave example

Hi, I'm want to use a Raspberry Pi to talk to the ADuCM355 over I2C, as we want to communicate with multiple targets 355's to run several electrochemical measurements (OCP, CV, CA...) at the same time. We have already written the code for the 355 to work over UART so that when the 355 receives f.ex. "<start@ocp>" it will run an OCP measurement, and send the data over UART, and my job is to add functionality so that we can do the same thing, just over I2C, so that we can control multiple 355's from a RPI controller.


My setup: 
ADuCM355 on our own PCB layout, which we have already used to successfully run measurements over UART. Connected the I2C to I2C 1 on a RaspberryPI, and I can detect the ADuCM355 by using i2cdetect -y 1 in the terminal f.ex., it shows up as address 0x45.

Using a DS3231 to test, I managed to write a python script that read multiple values from the DS3231, using the smbus python module.


So I have several questions:
1. How do I change the I2C address on the ADuCM355? I tried changing the values in  I2C0SIDCfg ( 0xA0 , 0xA6 , 0xA8 , 0xA0 ); on line 62 of  M355_I2C_Slave.c, but that didn't change the I2C address, it is still 0x45. Tried reading the I2C section on page226 of the hardware reference manual, but I'm left none the wiser.

2. What's the best way to send and receive data on the RPI over I2C? I've been using python-smbus, are there any better ways?

3. I tried reading the values in register 0x40003040, 0x40003044, 0x40003048, 0x4000304C to test if I could read the target ID0...ID3 (as described on p.231 of manual), but I only read 0x0, what am I doing wrong? I was expecting to read 0xA0, 0xA6, 0xA8, 0xA0.

This is the code I used:

import smbus

bus = smbus.SMBus(1)
addressRtc = 0x68
#addressAducm = 0x45

def getTemp(address):
    byte_tmsb = bus.read_byte_data(address,0x11)
    byte_tlsb = bin(bus.read_byte_data(address,0x12))[2:].zfill(8)
    return byte_tmsb+int(byte_tlsb[0])*2**(-1)+int(byte_tlsb[1])*2**(-2)
    
#print getTemp(address)
Celsius = getTemp(addressRtc)
print (Celsius, "*C")

ByteYear = bus.read_byte_data(0x68,0x06)
Year = hex(ByteYear)[2:]
ByteMonth = bus.read_byte_data(0x68,0x05)
Month = hex(ByteMonth)[2:]
ByteDate = bus.read_byte_data(0x68,0x04)
Date = hex(ByteDate)[2:]
ByteDay = bus.read_byte_data(0x68,0x03)
Day = hex(ByteDay)[2:]
ByteHour = bus.read_byte_data(0x68,0x02)
Hour = hex(ByteHour)[2:]
ByteMin = bus.read_byte_data(0x68,0x01)
Min = hex(ByteMin)[2:]

days = ("Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday")
print(
    "The date is {} {}/{}/{}".format(
        days[int(Day)], Year, Month, Date)
    )
print(
    "The time is {}.{}".format(
        Hour, Min)
    )

AducmByte = bus.read_byte(0x45)
AducmId0 = bus.read_byte_data(0x45,0x40003040)
AducmId1 = bus.read_byte_data(0x45,0x40003044)
AducmId2 = bus.read_byte_data(0x45,0x40003048)
AducmId3 = bus.read_byte_data(0x45,0x4000304C)

print(hex(AducmId0), hex(AducmId1), hex(AducmId2), hex(AducmId3))

Thanks in advance!

Best

  • Hi,

     Could you share the definition of bus.read_byte_data()?

    If you have done 

    AD5940_Initialize();
    ClockInit();
    I2CInit();

    on M355 side,

    for reading data from M355 slave, 

    I2C Slave Rx IRQ interrupt must be asserted by RPI controller.

    ( P0.4 of AduCM355: I2C SCL pin
       P0.5 of AduCM355 : I2C SDA pin)