Interrupt for USART RX on Atmega328p seems not to fire

I just want to toggle an LED when the USART finishes receiving, so I wrote the following for the USART_RX_vect, but the LED never changes. However, the LED does toggle if move the code from the ISR into the main loop and precede it with while ( !(UCSR0A & (1<<UDRE0)) );

Can anyone describe my error to me?

#define F_CPU 16000000UL
#define UBRR_VALUE 416 // baudrate 2400
#include <avr/io.h>
#include <avr/interrupt.h>
#include <util/delay.h>

  char data = UDR0;
  PORTB ^= (1 << PB0); // Toggle the LED

int main()
  DDRB |= (1 << PB0); // Set LED as output 

  // Set baud rate
  UBRR0H = (uint8_t)(UBRR_VALUE>>8);
  UBRR0L = (uint8_t)UBRR_VALUE;
  // Set frame format to 8 data bits, no parity, 1 stop bit
  UCSR0C |= (1<<UCSZ01)|(1<<UCSZ00);
  //enable reception and RC complete interrupt
  UCSR0B |= (1<<RXEN0)|(1<<RXCIE0);
  //  Enable global interrupts 
  while (1)

Thank you for your assistance.

You are calling delay in an interrupt routine - nothing can happen during that delay and you’ll muck up
the millis() clock completely.

Never call delay() in an interrupt routine.

Thanks. That’s instructive.

Is there some other issue I'm failing to recognize?

(As before, if I put this code in the main loop instead of in an ISR, it executes as I expect: the LED is illuminated.)

(That was going to be my first question - is the port manipulation coded correctly? Seems you have proved it is.)

Have you proved that the interrupt handler is executing? (For example you could change a volatile global and then detect and report that change in loop.)

Hardware issue. My jumper wire was not quite seated in the breadboard!

Thank you much.

Dear Sir, I’d red your post of “Interrupt for USART RX on Atmega328p seems not to fire”, and i can understand the things you do with your code. But sir, Do you use this code with Arduino IDE ? i.e: Is Arduino support main() function? and another thing is that, inside the main function what you do with sei() funtion?

 UCSR0C |= (1<<RXEN0) | (1<<RXCIE0);

There is no definition for sei(); function in your code. Do you have the definition for this function in other file. Or else is it a pre-defined One? Please explain what this function do? Thanks in advance.

sei() is the opposite of cli(). sei() sets the interrupt enable bit in order to allow interrupts to work. It's a built in function.