/*
* File: TempSensor.c
* Author: narayan
*
* Created on 15 de Março de 2019, 22:29
*/
#ifndef F_CPU
# define F_CPU 20000000UL / 8
#endif
#include <stdlib.h>
#include <inttypes.h>
#include <avr/io.h>
#include <util/delay.h>
#include <string.h>
#include "usart.h"
/*
*
*/
#define WRITE_OP (0x00 << 0x00)
#define READ_OP (0x01 << 0x00)
//Statuses handling
#define STATUS_NACK 0x01
#define STATUS_ACK 0x00
#define STATUS_OK 0x00
void CPU_Init(void){
// Enable Protected registers write
CPU_CCP = CCP_IOREG_gc;
CLKCTRL_MCLKCTRLA = CLKCTRL_CLKSEL_OSC20M_gc;
// Disable Prescaler
CPU_CCP = CCP_IOREG_gc;
CLKCTRL_MCLKCTRLB = CLKCTRL_PDIV_8X_gc | CLKCTRL_PEN_bm;
}
void TWI_Init(void){
TWI0_CTRLA |= TWI_SDASETUP_4CYC_gc // SDASETUP time of 4 clock cycles
| TWI_SDAHOLD_500NS_gc; // SDA Hold time - Meets SMBus specifications across all corners (0x03) ???
TWI0_CTRLA &= ~TWI_FMPEN_bm; // Fast Mode Plus disabled
// Set MBAUD to get 100KHz for SCL from fSCL = CLK_PER / (10 + 2*BAUD + CLK_PER*tRise)
// fSCL = 104KHz, CLK_PER = 20MHz/8, tRise = 2.5ns (datasheet page 17)
TWI0_MBAUD = 0x07;
TWI0_CTRLA &= ~TWI_TIMEOUT0_bm; // Disable Timeout for TWI operation
TWI0_MSTATUS = TWI_BUSSTATE_IDLE_gc; // Manually set the Bus state to IDLE for TWI operation
TWI0_MCTRLA = TWI_ENABLE_bm; // Enable Master Mode of operation
}
void Start_Bit(void){
// Wait until BUS is IDLE
while( (TWI0_MSTATUS & TWI_BUSSTATE_gm) == TWI_BUSSTATE_BUSY_gc)
/*wait*/;
// Send Start Bit
TWI0_MCTRLB = TWI_MCMD_REPSTART_gc;
}
void Stop_Bit(void){
// Wait until BUS is IDLE
while( (TWI0_MSTATUS & TWI_BUSSTATE_gm) == TWI_BUSSTATE_BUSY_gc)
/*wait*/;
TWI0_MCTRLB = TWI_MCMD_STOP_gc;
}
uint8_t TWI_Read(uint8_t sl_addr, uint8_t* packet){
while((TWI0_MSTATUS & TWI_BUSSTATE_BUSY_gc) == TWI_BUSSTATE_BUSY_gc)
/*wait*/;
// Send Slave address and R operation onto the bus
TWI0_MADDR = (sl_addr << 1) | READ_OP;
// Check Slave device ACK/NACK bit to signal address not/acknowledgment
if(TWI0_MSTATUS & TWI_RXACK_bm){
return STATUS_NACK; // Slave Address NOT received
}
// Data byte is stored into TWI0_DATA register and passed to *packet variable
*packet = TWI0_MDATA;
TWI0_MCTRLB = TWI_ACKACT_ACK_gc;
// Check Master device ACK/NACK bit to signal data not/acknowledgment
//if (TWI0_MSTATUS & TWI_RXACK_bm)
//return STATUS_NACK;
return STATUS_OK;
}
int main(int argc, char** argv) {
uint8_t temperature[256] = {0};
uint8_t sumtemp = 0;
float avgtemp = 0.0;
char message[256];
CPU_Init();
USART2_Init();
TWI_Init();
while(0x01){
for(uint8_t i = 0; i < 256; i++){
TWI_Read(0x18, &temperature[i]);
sumtemp += temperature[i];
}
// Send NACK from Master to signal don't need more data
TWI0_MCTRLB = TWI_ACKACT_NACK_gc;
// Send Stop bit to terminate transaction
TWI0_MCTRLB = TWI_MCMD_STOP_gc;
avgtemp = sumtemp / 256.0;
USART2_SendStr
(itoa(avgtemp
, message
, 10)); USART2_SendChar('\n');
_delay_ms(1000);
}
return (EXIT_SUCCESS);
}