// //////////////////////////////////////////////
// ESP (CS 33301-001)
// Project 4: ADC working with timer for internal led
//
// Kent State University
// Dept. of Computer Science
// Ean Dodge
// //////////////////////////////////////////////
//////////////////////////////////////////////////
//////////////////////////////////////////////////
#define BIT5_MASK 0x20 // 0010 0000 --> Pin 5
#define BIT4_MASK 0x10 // 0001 0000 --> Pin 4
#define PORTB_MASK 0x25 //for input port
#define DDRB_MASK 0x24// for the DDRB
#define PINB_MASK 0x23 //for input device
// Registers' Address Setting
unsigned char *ADMUX_ESP;
unsigned char *ADCSRA_ESP;
unsigned char *ADCSRB_ESP;
unsigned char *ADCL_ESP;
unsigned char *ADCH_ESP;
/* Which analog pin we want to read from. The pins are labeled "ADC0"
"ADC1" etc on the pinout in the data sheet. In this case ADC_PIN
being 1 means we want to use ADC1. On the ATmega328P this is also
the same as pin PC1 */
#define ADC_PIN 1
/* This function just keeps the reading code out of the loop itself.
It takes the analog pin number as a parameter and returns the
analog reading on that pin as a result. */
uint16_t adc_read(uint8_t adcx);
// Register Pointer Declaration
unsigned char *TCCR1A_ESP; //0x80
unsigned char *TCCR1B_ESP; //0x81
unsigned char *TCNT1H_ESP; //0x85
unsigned char *TCNT1L_ESP; //0x84
unsigned char *OCR1AH_ESP; //0x89
unsigned char *OCR1AL_ESP; //0x88
unsigned char *TIMSK1_ESP; //0x6F
unsigned char *portDDRB; //declaring DDRB
unsigned char *portB; //declaring port B to use as output D
unsigned char *portPinB; //for input
void MyDelay(unsigned long mSec);
void setup() {
//////////////////////////////////////////////////
// Serial Library
Serial.begin(9600); // open the serial port at 9600 bps:
//////////////////////////////////////////////////
// Registers' Address Setting
ADMUX_ESP = (unsigned char*) 0x7c;
ADCSRA_ESP = (unsigned char*) 0x7a;
ADCSRB_ESP = (unsigned char*) 0x7b;
ADCL_ESP = (unsigned char*) 0x78;
ADCH_ESP = (unsigned char*) 0x79;
TCCR1A_ESP = (unsigned char*) 0x80;
TCCR1B_ESP = (unsigned char*) 0x81;
TCNT1H_ESP = (unsigned char*) 0x85;
TCNT1L_ESP = (unsigned char*) 0x84;
OCR1AH_ESP = (unsigned char*) 0x89;
OCR1AL_ESP = (unsigned char*) 0x88;
TIMSK1_ESP = (unsigned char*) 0x6F;
portDDRB = (unsigned char *) DDRB_MASK; //pointing DDRB to a hardcoded value of 0x24
*portDDRB |= BIT5_MASK; //Configure bit 5 of DDRB as 1, or an output
*portDDRB &= ~BIT4_MASK; //input
portB = (unsigned char *) PORTB_MASK; //pointing PortB to a hardcoded value of 0x25
*portB &= ~BIT5_MASK; //turns off internal LED to initialize it as off
portPinB = (unsigned char *) PINB_MASK;
*TCCR1A_ESP = 0x00;
*TCCR1B_ESP = 0x0C; // CTC mode - BIT 3; 256 prescaler BIT2
*TCNT1H_ESP = 0x00;
*TCNT1L_ESP = 0x00;
*OCR1AH_ESP = 0xF2; //for 1 second changes
*OCR1AL_ESP = 0x24; //for 1 second changes
*TIMSK1_ESP = 0x02; // enable timer compare interrupt - BIT1
}
int flag = 0;
bool done = false;
bool eval = false;
int potpin = 0; // analog pin used to connect the potentiometer
int val; // variable to read the value from the analog pin
void loop() {
/* Enable the ADC */
*ADCSRA_ESP |= 0b10000000;
val = adc_read(ADC_PIN);
if (val <= 270) {
done = true;
}else{
done = false;
*portB &= ~BIT5_MASK; //turns off internal LED to initialize it as off
}
int BETA = 3950;
float newVal = 1 / (log(1 / (1023. / val - 1)) / BETA + 1.0 / 298.15) - 273.15;
//this is on the wokwi reference page for the sensor,
//thought it would be easier to read
//eval = false;
if (!eval){
if (*portPinB == 0x10){
Serial.print ("Temp: ");
Serial.println(newVal);
eval = true;
}
}
}
ISR(TIMER1_COMPA_vect)
{
if(done == true){
if (flag == 0)
{
*portB &= ~0x20; // Internal LED off
flag = 1;
} else {
*portB |= 0x20; // Internal LED on
flag = 0;
}
}
if ((*portPinB) <= 3) {
eval = false;
}
}
uint16_t adc_read(uint8_t adcx) {
/* adcx is the analog pin we want to use. ADMUX's first few bits are
the binary representations of the numbers of the pins so we can
just 'OR' the pin's number with ADMUX to select that pin.
We first zero the four bits by setting ADMUX equal to its higher
four bits. */
*ADMUX_ESP &= 0xf0;
*ADMUX_ESP |= adcx;
/* This starts the conversion. */
*ADCSRA_ESP |= 0b01000000;
/* Finally, we return the converted value to the calling function. */
unsigned char cl = *ADCL_ESP;
unsigned char ch = *ADCH_ESP;
return (cl | (ch << 8));
}