Arduino I2C sends unexpected NACK

33

I am using a development board of microchip (explorer 16) with pic24f128ga010 as Master and Arduino as Slave . The PIC is sending everything right, but for some reason arduino sends NACK to all date , only sends ACK at the beginning when sending the Address .

PIC (Master) Code:

/* 
* File: main.c
* Author: SusanaEca
*
* Created on 26 de Março de 2015, 19:26
*/
//Libraries
#include "p24fxxxx.h"
#include "i2c.h"
#include "leds.h"

//Calculate baud rate of I2C
/*
* I2CxBRG = (FCY/FSCL - FCY/10,000,000) - 1
* Based on FCY = FOSC/2; Doze mode and PLL are disabled.
*/
#define Fosc (8000000) // crystal
#define Fcy (Fosc*4/2) // w.PLL (Instruction Per Second)
#define Fsck 400000 // 400kHz I2C
#define I2C1_BRG ((Fcy/2/Fsck)-1)

int main(void)
{
    //Variable declaration
    char SlaveAddress = 0x4;
    unsigned char *letras;
    unsigned char tx_data[] = {'P', 'I', '
// Wire Slave Receiver
// by Nicholas Zambetti <http://www.zambetti.com>

// Demonstrates use of the Wire library
// Receives data as an I2C/TWI slave device
// Refer to the "Wire Master Writer" example for use with this

// Created 29 March 2006

// This example code is in the public domain.


#include <Wire.h>

void setup()
{
    Wire.begin(4); // join i2c bus with address #4
    Wire.onReceive(receiveEvent); // register event
    Serial.begin(9600); // start serial for output
}

void loop()
{
    delay(100);
}

// function that executes whenever data is received from master
// this function is registered as an event, see setup()
void receiveEvent(int howMany)
{
    while(1 < Wire.available()) // loop through all but the last
    {
        char c = Wire.read(); // receive byte as a character
        Serial.print(c); // print the character
    }
    int x = Wire.read(); // receive byte as an integer
    Serial.println(x); // print the integer
}
'}; // char c='M'; //Get your pointer to a variable letras = tx_data; //Set-up LEDs LED_Enable(LED_D6); LED_Enable(LED_D3); //Initialize I2C1 OpenI2C1(I2C_ON, I2C1_BRG); while(1) { //Start I2C1 condition StartI2C1(); //Send the Start Bit IdleI2C1(); //Wait to complete //Write-to-Slave Address MasterWriteI2C1((SlaveAddress<<0)|0); //Send device advice adress byte to the slave with the write indication IdleI2C1(); //Wait to complete //If ACK is received... if (I2C1STATbits.ACKSTAT == 0) { LED_On(LED_D6); //Light up LED #6 MasterputsI2C1(letras); //Send your string :) IdleI2C1(); //Wait to complete //If NACK (erro)... if (I2C1STATbits.ACKSTAT == 1) { LED_On(LED_D3); //Light up LED #3 } } } }

Arduino code (Slave):

/* 
* File: main.c
* Author: SusanaEca
*
* Created on 26 de Março de 2015, 19:26
*/
//Libraries
#include "p24fxxxx.h"
#include "i2c.h"
#include "leds.h"

//Calculate baud rate of I2C
/*
* I2CxBRG = (FCY/FSCL - FCY/10,000,000) - 1
* Based on FCY = FOSC/2; Doze mode and PLL are disabled.
*/
#define Fosc (8000000) // crystal
#define Fcy (Fosc*4/2) // w.PLL (Instruction Per Second)
#define Fsck 400000 // 400kHz I2C
#define I2C1_BRG ((Fcy/2/Fsck)-1)

int main(void)
{
    //Variable declaration
    char SlaveAddress = 0x4;
    unsigned char *letras;
    unsigned char tx_data[] = {'P', 'I', '
// Wire Slave Receiver
// by Nicholas Zambetti <http://www.zambetti.com>

// Demonstrates use of the Wire library
// Receives data as an I2C/TWI slave device
// Refer to the "Wire Master Writer" example for use with this

// Created 29 March 2006

// This example code is in the public domain.


#include <Wire.h>

void setup()
{
    Wire.begin(4); // join i2c bus with address #4
    Wire.onReceive(receiveEvent); // register event
    Serial.begin(9600); // start serial for output
}

void loop()
{
    delay(100);
}

// function that executes whenever data is received from master
// this function is registered as an event, see setup()
void receiveEvent(int howMany)
{
    while(1 < Wire.available()) // loop through all but the last
    {
        char c = Wire.read(); // receive byte as a character
        Serial.print(c); // print the character
    }
    int x = Wire.read(); // receive byte as an integer
    Serial.println(x); // print the integer
}
'}; // char c='M'; //Get your pointer to a variable letras = tx_data; //Set-up LEDs LED_Enable(LED_D6); LED_Enable(LED_D3); //Initialize I2C1 OpenI2C1(I2C_ON, I2C1_BRG); while(1) { //Start I2C1 condition StartI2C1(); //Send the Start Bit IdleI2C1(); //Wait to complete //Write-to-Slave Address MasterWriteI2C1((SlaveAddress<<0)|0); //Send device advice adress byte to the slave with the write indication IdleI2C1(); //Wait to complete //If ACK is received... if (I2C1STATbits.ACKSTAT == 0) { LED_On(LED_D6); //Light up LED #6 MasterputsI2C1(letras); //Send your string :) IdleI2C1(); //Wait to complete //If NACK (erro)... if (I2C1STATbits.ACKSTAT == 1) { LED_On(LED_D3); //Light up LED #3 } } } }

    
asked by anonymous 29.03.2015 / 18:43

1 answer

2

I found the answer to this: link

The NACK is signaled by a confirmation slot in which SDA remains high while the SCL cycles are controlled by the master.

Since the high is the uncontrolled state of the pulled bus, in the absence of a peripheral in the address selected to positively confirm by pulling it down, a NACK condition will result passively.

    
21.09.2017 / 19:05