I2C MasterSlave
Esp32 I2C Slave code
#include <Wire.h>
#define SLAVE_ADDR 0x04 // Define the I2C Slave address
// Data to send to the I2C master
String dataToSend = "Hello, master!";
// This function is called when the master requests data from the slave.
void onRequest() {
Wire.write(dataToSend.c_str()); // Send data as a string (char array)
}
// This function is called when the master sends data to the slave.
// We're not expecting any specific commands, but you can expand this
// function to handle any data you receive from the master.
void onReceive(int howMany) {
while (Wire.available()) { // loop through all but the last
char c = Wire.read(); // receive byte as a character
Serial.print(c); // print the character
}
}
void setup() {
Serial.begin(115200); // Start serial communication at 115200 baud
Wire.begin(SLAVE_ADDR); // Join i2c bus with the defined slave address
Wire.onRequest(onRequest); // Register the onRequest event handler
Wire.onReceive(onReceive); // Register the onReceive event handler
}
void loop() {
delay(100); // Delay to slow down the loop for stability
}
PIC16F18877 Interrupt based I2C Master Read Code
#include <xc.h>
// Define system frequency
#define _XTAL_FREQ 32000000 // 32 MHz, adjust as per your clock settings
// Configuration bits (set according to your needs)
#pragma config FEXTOSC = HS // External Oscillator mode
#pragma config RSTOSC = EXTOSC // Power-up default value for COSC
#pragma config CLKOUTEN = OFF // Clock out disabled
#pragma config CSWEN = ON // Clock switch enabled
#pragma config FCMEN = ON // Fail-safe clock monitor enabled
// I2C baud rate
#define I2C_BAUDRATE 100000 // 100 kHz
void I2C_Master_Init(void);
void I2C_Master_Read_Request(uint8_t slaveAddress);
void __interrupt() I2C_ISR(void);
volatile uint8_t receivedData = 0;
int main(void) {
// Initialize I2C Master
I2C_Master_Init();
// Enable global and peripheral interrupts
INTCONbits.PEIE = 1;
INTCONbits.GIE = 1;
// Example: Read from slave device at address 0x50
I2C_Master_Read_Request(0x50);
while (1) {
// Main loop
// Can implement other logic or enter sleep mode
}
return 0;
}
void I2C_Master_Init(void) {
// Set SDA and SCL as input (required for MSSP module to drive lines)
TRISCbits.TRISC3 = 1; // SCL
TRISCbits.TRISC4 = 1; // SDA
// I2C Master mode, clock = FOSC/(4 * (SSP1ADD + 1))
SSP1CON1 = 0x28; // SSPEN enabled, Master mode
SSP1ADD = (_XTAL_FREQ / (4 * I2C_BAUDRATE)) - 1;
// Enable SSP (Synchronous Serial Port)
SSP1CON1bits.SSPEN = 1;
// Enable MSSP interrupt
PIE1bits.SSP1IE = 1;
PIR1bits.SSP1IF = 0; // Clear MSSP interrupt flag
}
void I2C_Master_Read_Request(uint8_t slaveAddress) {
SSP1BUF = (slaveAddress << 1) | 1; // Send slave address with read bit
SSP1CON2bits.RCEN = 1; // Enable receive mode for master
}
void __interrupt() I2C_ISR(void) {
if (PIR1bits.SSP1IF) {
if (SSP1CON2bits.RCEN) {
// If receive is enabled and data is ready to read
receivedData = SSP1BUF; // Read data from buffer
SSP1CON2bits.ACKDT = 0; // Send ACK
SSP1CON2bits.ACKEN = 1; // Start Acknowledge sequence
}
PIR1bits.SSP1IF = 0; // Clear the MSSP interrupt flag
}
}
Comments
Post a Comment