cputtyadcatmega32

How to build up a C code for avr atmega32 microcontroller to capture light intensity through photodiode and transmit data through serial communication


I am planning to construct a spectrometer. My aim is to rotate the grating and capture light intensity using a 3pin photodiode(S9055 series) and to plot a graph of Intensity Vs rotation angle using python. To construct the system I use avr ATMega32a microcontroller and I connect a MG995 servo motor to rotate the grating.

The proposed flow of the program as follows:

I am already okay with the rotating of the motor however there seems an error in the ADC part. The following is my code to capture light and convert the values.

#define F_CPU 8000000UL
#include <avr/io.h>
#include <util/delay.h>
#include <stdlib.h>
#include <stdio.h>

//#define USART_BAUDRATE 9600
#define BAUD_PRESCALE (((F_CPU / (USART_BAUDRATE * 16UL))) - 1)


void UART_init(long USART_BAUDRATE)
{
    UCSRB |= (1 << RXEN) | (1 << TXEN);   /* Turn on the transmission and reception */
    UCSRC |= (1 << URSEL) | (1 << UCSZ0) | (1 << UCSZ1); /* Use 8-bit character sizes */

    UBRRL = BAUD_PRESCALE;                  /* Load lower 8-bits of the baud rate value */
    UBRRH = (BAUD_PRESCALE >> 8);           /*Load upper 8-bits*/
}



void UART_TxChar(char ch)
{
    while (! (UCSRA & (1<<UDRE))); /*Wait for empty transmit buffer*/
    UDR = ch ;
}

void UART_SendString(char *str)
{
    unsigned char j=0;
    
    while (str[j]!=0)   /*send string up to null */
    {
        UART_TxChar(str[j]);    
        j++;
    }
}

void adc_init() // Initialize ADC
{
    ADMUX = (1<<REFS0); // AVCC as reference voltage
    ADCSRA = (1<<ADEN) | (1<<ADPS2) | (1<<ADPS1) | (1<<ADPS0); // Enable ADC and set prescaler to 128
}

// Function to read the ADC value
// Read ADC value from a channel
uint16_t adc_read(uint8_t channel)
{
    channel &= 0x07; // Select channel from 0 to 7
    ADMUX = (ADMUX & 0xF8) | channel; // Clear the lower 3 bits and set the channel
    ADCSRA |= (1<<ADSC); // Start conversion
    while(ADCSRA & (1<<ADSC)); // Wait for conversion to complete
    return ADC; // Return the ADC value
}

int main()
{
    uint16_t adc_value; // Variable to store the ADC value
    //DDRB = 0xFF; // Set PORTB as output for LED display
    adc_init(); // Initialize ADC
    
    char c="5";
    UART_init(9600);
    
    UART_SendString("\nInitializing....\n ");   
    while(1)
    {
         adc_value = adc_read(0); // Read ADC value from channel 0 (connected to photodiode)

        // Print the ADC value to the Putty terminal
        printf("ADC value: %d\n", adc_value);
        UART_SendString(c );        
        UART_SendString(adc_value );

        // Wait for a millisecond
        _delay_ms(1000);



    }   
    return 0;
}
}

The output shows in the PuTTy terminal as: click to view the image I got the snip after I removed the serial communication cable.

So as you see, this cannot be definitely the output so can someone help me to figure out where I have gone wrong?


Solution

  • May be it would help

    int main()
    {
        uint16_t adc_value; // Variable to store the ADC value
        adc_init(); // Initialize ADC
        
        char c[]="5";
        UART_init(9600);
        
        UART_SendString("\nInitializing....\n ");   
        while(1)
        {
             adc_value = adc_read(0); // Read ADC value from channel 0 (connected to photodiode)
    
            // Print the ADC value to the Putty terminal
            char buf[20];
    
            sprintf(buf,"ADC value: %d\n", adc_value);
            UART_SendString(c );        
            UART_SendString(buf);
    
            // Wait for a millisecond
            _delay_ms(1000);
    
        }   
        return 0;
    }