I2c Porting from Arduino

Go To Last Post
5 posts / 0 new
Author
Message
#1
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Atmega 1284A-AU on a custom board, Adafruits MMA8451 accelerometer breakout board

AVR studio 6.2

c/c++

Fleurys i2cmaster code

Adafruits I2c example on how to read the WhoAMI register.

 

I'm trying to port Adafruits example to read a register to use Fleurys C code, It seems pretty simple.

I am using his code to talk to an LED controller just fine.

 

In the init() function I call readRegister8()

* i2c_start_wait returns OK

* i2C_write(reg) fails, with a 0x48, no ack recieved

 

Am I missing something obvious??

TIA

 

Init

bool MMA8451_Init()
{
    /* Check connection */
    uint8_t deviceid = readRegister8(MMA8451_REG_WHOAMI);
    
    if (deviceid != 0x1A)
    {
        /* No MMA8451 detected ... return false */
        //Serial.println(deviceid, HEX);
        return false;
    }
}

 

The original Arduino code

uint8_t Adafruit_MMA8451::readRegister8(uint8_t reg) 
{
    Wire.beginTransmission(_i2caddr);
    i2cwrite(reg);
    Wire.endTransmission(false); // MMA8451 + friends uses repeated start!!

    Wire.requestFrom(_i2caddr, 1);
    if (! Wire.available()) return -1;
    return (i2cread());
}

 

My version

uint8_t MMA8451_readRegister8(uint8_t reg) 
{
    uint8_t resp = 0;

    if(i2c_start_wait(MMA8451_ADDR)) //0x1C or 0x1D
    {
        if(i2c_write(reg)==0)
        {
            if(i2c_rep_start(MMA8451_ADDR + ))
            {
                resp = i2c_readNak();
            }
        }
    }
    
    i2c_stop(); 
    return resp;
}

 

Keith Vasilakes

Firmware engineer

Minnesota

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Fleury uses 8-bit addresses.  <Wire.h> use 7-bit addresses.

 

Assuming you are using hardware 7-bit 0x1C,   Fleury would expect to see 0x38/0x39 (8-bit W/R)

 

I would never use i2c_start_wait()

Use i2c_start() and you get a diagnostic result instead of crashing.

 

Untested.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Gah! 1 dang bit

 

Well cool, I hope it's that simple.

 

Interesting about the start_wait(), not crashing is always better :)

Keith Vasilakes

Firmware engineer

Minnesota

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Most of the time,  you assume that a slave device may or may not be present.    So it is perfectly reasonable to find that a RTC is absent or an EEPROM is busy.

 

If you know that a certain Slave is hard-wired on your pcb,    failure from i2c_start() is unfortunate but at least you can report the problem.

Failure from i2c_start_wait() involves a dead system.

 

David.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Makes sense. I was just following the examples.

I've gotten away for a long time without using i2c, time to learn it I guess!

 

The address fix did it, thanks!

Keith Vasilakes

Firmware engineer

Minnesota