거북이처럼 천천히

8bit Timer / counter - Phase Correct Fast PWM Mode 본문

Embedded Programming/Atmega 128A (실습)

8bit Timer / counter - Phase Correct Fast PWM Mode

유로 청년 2024. 6. 19. 08:25

서론 

 

이번에는 CTC (Clear timer compare match) Mode, Normal Mode, Fast PWM (Pulse Width Modulation) Mode 에 이어 Phase Correct Fast PWM mode에 대해서 공부하겠다. 특히 기존에 다루었던 Fast PWM Mode와 비교하며, 공부하겠다.

 

 

 

본론

💡 1. Dual Slope와 Single Slope의 차이

(위) Single Slope, (아래) Dual Slope

 

  • Single Slope는 TCNT Register 값이 MAX값에 도달하면 0으로 초기화된다.
  • Dual Slope는 TCNT Register 값이 Max값에 도달하면 바로 0으로 초기화되지 않고, MAX값에서부터 시작해서 1씩 줄어가며, Counter의 bottom값이 0으로 카운트한다.
  • 그래서 Dual Slope에서 TCNT Register 값이 1씩 증가하는 카운트를 "Upcounting"이라 하며, 1씩 감소하는 카운트를 "Downcounting"이라 한다.
  • Q) Single slope는 Counter의 Bottom 값부터 counter의 Max 값까지를 1주기로 보는데, Dual slope는 어디서부터 어디까지를 1주기라고 보는가?
    A) Dual slope에서의 1주기는 Counter의 Bottom에서부터 Counter의 Max까지 Upcounting한 뒤, 다시 Counter의 Max에서부터 Counter의 Bottom까지 Downcounting을 하여 왔을 때를 1주기라고 본다. 
    예를 들어 8bit  Timer / Counter 를 본다면 TCNT (Timer/Counter Register) 값이 0부터 시작해서 255까지 갔다가 255부터 다시 0으로 돌아왔을 때를 1주기라고 본다.

 

 

 

💡 2. Phase Correct Fast PWM Mode는 무엇인가?

  • Phase Correct Fast PWM Mode의 Counter의 Count 구조는 Dual Slope를 갖는다.

Timing Diagram of Phase Correct PWM Mode

 

  • Counter는 Counter의 bottom값인 0부터 시작해서 Upcounting을 한다. 
  • TCNT (Timer/Counter Reigster) 값이 OCR (Output Compare Register)와 Match되면 Output Compare Match Interrupt를 발생시키며, OCn signal (Output Compare Signal n)에 영향을 준다.
    - Non-inverting mode : Upcounting에서 Interrupt 발생 시, OCn 을 0으로 Clear한다.
    - Inverting mode : Upcounting에서 Interrupt 발생 시, OCn 을 1으로 Set한다.
  • TCNT (Timer/Counter Register) 값이 Counter의 Max 값에 도달하면 중요한 변화가 생긴다.
          
    1) TCNT Register는 1씩 줄이며, Downcounting한다.
    2) 기존 upcounting에서 Output Compare Match Interrupt 발생 시, OCn 신호 값의 설정이 변한다.
        - Non-inverting mode : Upcounting에서 Interrupt 발생시, OCn을 0으로 Clear 한다.
                                                Downcounting에서 Interrupt 발생시, OCn을 1으로 Set 한다.
        - Inverting mode : Upcounting에서 Interrupt 발생시, OCn을 1으로 Set 한다.
                                        Downcounting에서 Interrupt 발생시, OCn을 0으로 Clear한다.

 

 

 

 

💡 3. Fast PWM Mode와 Phase Correct Fast PWM Mode의 차이점은 뭐가 있는가?

- Fast PWM Mode와 Phase Correct Fast PWM Mode에는 여러가지의 차이점을 갖는다. 

 

 

1) Interrupt가  2번 발생하지만, 발생하는 Interrupt의 종류가 다르다. 

  • Fast PWM Mode는 2번의 Interrupt가 발생하는데, Output Compare Match Interrupt Overflow Interrupt가 발생한다.
  • 하지만, Phase Correct Fast PWM Mode에서도 2번의 Interrupt가 발생한다. 그러나 Fast PWM Mode와 달리 2번의 Interrupt 모두 Output Compare Match Interrupt가 발생한다.

 

 

2) OCn (Output Compare n) Signal의 대칭적

  • Fast PWM Mode는 single slope를 사용하기 때문에 출력 펄스파형이 비대칭적인 구조를 갖는다.
  • 하지만, Phase Correct Fast PWM mode는 dual slope를 사용하기 때문에 upcounting할 때와 downcounting할 때, 동일한 Timing에 Toggle이 발생하여 출력 펄스파형이 대칭적 구조를 갖는다.

 

 

3) Phase Correct Fast PWM Mode에서의 Overflow Interrupt는 OCn signal에 영향이 없다.

  • Fast PWM Mode에서는 Overflow Interrupt 발생시 설정에 따라 다르지만, OCn signal에 영향을 준다.
  • Phase Correct Fast PWM Mode도 Counter 값이 주기마다 Overflow Interrupt를 발생시키지만, Phase Correct Fast PWM Mode에서는 Overflow Interrupt가 발생하여도 OCn signal에 아무런 영향이 없다.

 

4) 최대 동작 주파수측면에서 Dual slope가 Single slope보다 낮을 수 있다.

  • Single slope의 동작 주파수는 Upcounting만 존재하기 때문에 1주기가 상대적으로 Dual slope보다 짧아 동작 주파수가 낮을 수 도 있다.
  • Dual slope의 동작 주파수는 Upcounting과 Downcounting하기 때문에 1주기가 상대적으로 Single slope보다 길며, 이로 인해 동작 주파수가 높을 수 도 있다.

 

 

💡 4. Phase Correct Fast PWM Mode 을 통한 PWM 생성 및 출력

 

환경) 

  • PB4 (OC0)를 출력핀으로 설정
  • Prescaler, N : 256
  • Output Compare Signal 0, foc0 : 122.549019607Hz

equation of relation between CLK signal and Output Compare Signal

 

소스 코드)

#define F_CPU 16000000
#include <avr/io.h>
#include <util/delay.h>

#define SIGNAL_DDR		DDRB
#define SIGNAL_PORT		PORTB

int main(void)
{
	// PB4(OC0)를 출력핀으로 설정
	SIGNAL_DDR |= (1<<DDB4);
	
	// PB4(OC0) 출력핀의 초기 전압을 0V으로 초기 설정
	SIGNAL_PORT &= ~(1<<PORTB4);
	
	// 8bit Timer/Counter 0 사용
	// Prescaler, N = 256
	// foc0 = 122.549019607Hz
	TCCR0 |= (1<<WGM00 | 1<<CS01 | 1<<CS02 | 1<<COM01 | 1<<COM00);
		
	// TCNT0 (Timer/Counter Register 0)을 0부터 카운터하도록 설정.
	TCNT0 = 0;
	
	// Duty ratio = 50%
	OCR0 = 127;
	
    while (1) 
    {	
    }
}

 

  • 주의)       
    Fast PWM Mode에서는 TCNT (Timer/Counter Register) 값은 사용자 임의대로 설정할 수 없었고, 자동적으로 카운터가 0부터 시작해서 Up-counting을 하였다. 하지만, Phase correct Fast PWM Mode는 OCR 값은 물론,  TCNT값도 사용자 임의대로 수정할 수 있다. 
  • 따라서 초기 세팅할 시, OCR (Output Compare Register)와 TCNT (Timer/Counter Register) 값을 모두 명시해줘야 한다.
  • 경험담이지만, TCNT 값을 초기 세팅하지 않아서 한 번 Toggle이 발생한 뒤, 다시는 Toggle이 발생하지 않아서 원인을 찾는데, 고생(?)을 조금 했다.

 

구현)

Oscilloscope of Phase Correct Fast PWM Mode
회로도

 

 

 

 

 

💡 5.  Phase Correct Fast PWM Mode를 공부하면서 개인적으로 얻은 내용

 

1. Fast PWM Mode가 Phase Correct Fast PWM Mode보다 duty ratio를 세세하게 컨트롤 가능하다?

  • DataSheet나 수치적으로 보았을 때에는 Duty ratio를 세세하게 컨트롤할 수 있을지 몰라도 현실에서는 Fast PWM Mode를 통해 duty ratio를 세세하게 컨트롤 하는 것 보다 16bit timer/counter를 통해 Duty ratio를 조절하는 것이 더 편하고, 더 세세하게 컨트롤 할 수 있다.
  • 즉, 8bit timer/counter mcu나 16bit timer/counter mcu나 가격 차이가 크게 없다.

 

 

2. Phase Correct Fast PWM Mode가 Fast PWM Mode보다 안정성이 있다?

  • 이 또한 DataSheet나 수치적으로 보았을 때에는 안정성이 있을 수 있어도 현실에서는 Fast PWM Mode나 Phase Correct Fast PWM Mode나 안정성 측면에서 큰 차이 없다.
  • 따라서 현실은 Phase Correct Fast PWM Mode보다는 Fast PWM Mode가 이해하기 쉽고, 직관적이기 때문에 Fast PWM Mode를 주로 사용한다.

 

 

💡 또 다른 실험) 8bit Timer/Counter 2와 Phase Correct Fast PWM Mode를 사용해서 파형 생성

 

환경)

  • PB7 (OC2)를 출력핀으로 설정
  • Prescaler, N = 64
  • Output Compare Signal 2, foc2 = 490.1960784Hz

 

코드)

#define F_CPU 16000000UL
#include <avr/io.h>
#include <util/delay.h>

// Substitute Constant
#define WAVE_DDR			DDRB
#define WAVE_PORT			PORTB

// Function prototype.
void init_PORT();

// Main method
int main(void)
{
   // Initialization.
   init_PORT();
   
   // TCCR2 = Timer/Counter Control Register 2
   // Prescaler, N = 64
   // Output Compare Signal 2, foc2 = 490.1960784Hz
   TCCR2 |= (1<<WGM20 | 1<<COM21 | 1<<CS21 | 1<<CS20);
   
   // TCNT2, Timer/Counter Register 2
   TCNT2 = 0;
   
   // Duty Ratio 25%
   OCR2 = (256/4);
   
    while (1) 
    {
    }
}

// Initialization.
void init_PORT() {
	WAVE_DDR |= (1<<DDB7);
	WAVE_PORT |= (1<<PORTB7);
}

 

 

출력)

Oscilloscope of Phase Correct Fast PWM Mode