Toggle OC2B pin by using Timer 2 in CTC mode and check it by turning on/off the LED

hi, i want to use TImer 2 in the CTC mode to toggle the OC2B pin, so when its toggled, i will use the External Interrupt INT1 to turn on/off the LED. But the LED doesnt change, can anyone tell me why?

#include <avr/io.h>
#include <avr/interrupt.h>
#include <util/delay.h>

volatile boolean flag = false;

int main(void){
  DDRD &= ~(1 << DDD3) ; //clear PD3 for interrupt 1
  DDRB |= (1 << DDB0);   //set PB0 for the LED
  
  EICRA |= (1 << ISC01); 
  EIMSK |= (1 << INT1); //turn on TNT1
  PORTB &= ~(1<<PORTB0);

  TCCR2B |= (1 << WGM21) | (1 << CS20) | (1 << CS21) | (1 << CS22); //turn on CTC mode and set the prescaler 1024
  TIMSK2 |= (1 << OCIE2A);
  
  OCR2B = 99;
  
  sei(); //turn on global enbal interrupt bit
  while(1){}
}

ISR(TIMER2_COMPB_vect) {
  PORTD ^= (1 << PORTD3);
  flag = true;
}

ISR(INT1_vect){
  sei();
  if (flag) {
    PORTB |= (1 << PORTB0);
    _delay_ms(1000);
    PORTB &= ~(1 << PORTB0);
    _delay_ms(1000);
    flag = false;
  }
 }

Your code is very creative, perfect example how to not use interrupts.

Did you connect the PWM pin to the INT1 pin? If not then nothing will happen. But if you did so you most probably run into a stack overflow with infinite calls of the INT1 interrupt handler.

For further assistance please explain what you really want to achieve or demonstrate.

thanks for your advice (with some mockery but I admit that I lack for knowledge so it's okay), this is what i want to achieve

So you want us to do your homework?

It may work as described with an Uno, not with a Mega or other controllers with different alternate pin functions.

It may work if you only toggle the LED once inside the INT1 ISR without any delay and flip on/off.

It may not work if you toggle PD3 from both the timer and COMPB interrupt.

wait? I did the homework. I got stuck so I just need some help. I'm sorry if my lack of knowledge annoys you, i don't want you to do my homework for me. I need some advice from seniors who have more knowledge than me, not mockery (obviously). Thanks anw

I gave you some general advice. I don't want to dig into bit fiddling with registers, that's up to you.

A piezo may be helpful in detecting fast toggling outputs, LEDs for slow toggling.

Inside an ISR?
No.

Btw, this is strictly speaking not an Arduino question, is it? :wink:

what do you mean? i seriously do not understand why you think that it is not about Arduino?

Arduino compiler convention uses setup() and loop(), and _delay_ms(x) is generally delay(x), suggesting to me you're not using a compiler linked to / packaged with the Arduino IDE. Doesn't matter, I don't think your question is out of place or anything.

What kind of board & microcontroller are you writing this for?

Yes if nested interrupts are enabled. But as I already mentioned this will lead to infinite calls of the ISR.

Exactly; it's 'organize for failure'.

well, my class uses this arduino IDE. I cant do anything about it. i just try to build the code based on the way i was taught.

If you want help from the Arduino forum it would help if you added Arduino comments:
EICRA |= (1 << ISC01); // FALLING int on INT0

Note: This points out a problem since you intended to set INT1.

You are using Waveform Generation Mode 2 (CTC) but you never set the value os OCR2A used for TOP. If TOP is below 99, OCR2B will never trigger.

You are not setting the COM2B0 or COM2B1 bits in TCCR2A so the OC2B pin does nothing. I think you want 0b01 for Toggle OC2B on Compare Match.

this is my code so far:

#include <avr/io.h>
#include <avr/interrupt.h>
#include <util/delay.h>

int main(void){
  DDRD |= (1 << DDD3);
  DDRB |= (1 << DDB0);   //set PB0 for the LED
  
  EICRA |= (1 << ISC11);
  EIMSK |= (1 << INT1); //turn on TNT1

  TCCR2B |= (1 << WGM21) | (1 << CS20) | (1 << CS21) | (1 << CS22); //turn on CTC mode and set the prescaler 1024
  TCCR2A |= (1 << COM2B0);
  TIMSK2 |= (1 << OCIE2A);

  OCR2A = 250;
  OCR2B = 200;
  
  sei(); //turn on global enbal interrupt bit
  while(1){}
}

ISR(INT1_vect){
   PINB = (1 << PORTB0);
}

Isn't PINB the Input register?

huh? Its Output.

DDRB |= (1 << DDB0);

This will set the PB) as output, right?

@thien1602
Are you using Arduino UNO or NANO or MEGA?

Does it do what you want it to do?

Right, but the output register is PORTB, while PINB IMO only reads the pins.