거북이처럼 천천히

8bit Timer / counter - Normal Mode 본문

Embedded Programming/Atmega 128A (실습)

8bit Timer / counter - Normal Mode

유로 청년 2024. 6. 3. 20:12

서론 

 

이전 게시글에서 8bit Timer / Counter CTC Mode를 활용하여 1kHz 주파수를 갖으며, Output Compare Match Interrupt가 발생하면 Toggle이 발생하도록 하는 출력신호를 만들었다. 이번에는 8bit Timer / Counter Normal Mode를 활용하여 새로운 출력 신호를 만들 것이며, 이를 통해 Normal Mode에 대해서 알아보도록 하겠다.

 

 

 

본론 (Normal Mode에 대한 이론)

 

💡 Q) Normal Mode란 무엇인가?

 

이전 게시글에서 정리한 CTC Mode (Clear Time on Compare Match Mode)는 OCRn(Output Compare Register n)을 설정함으로서 Counter의 Count 값(=TCNT)이 OCRn(Output Compare Register n)에 도달하면 Output Compare Match Interrupt을 발생킨다.

 

하지만, OCRn (Output Compare Regsiter n)을 설정하는 것이 Counter의 Bottom 값을 조절함으로서 Counter가 카운트 할 수 있는 값을 조절하게 된다. 

 

이를 그림으로 표현하면 다음과 같다.

Noraml Mode의 Time Diagram

 

 

위 그림을 보면 알 수 있 듯이 Normal Mode는 CTC Mode와 달리 0이 아닌 5부터 Counter가 count하기 시작하며, 반대로 OCRn (Output Compare Register n) 까지만 Count하는 것이 아닌 MAX값이 255까지 Count하게 된다. 

 

 

💡 Q) CTC Mode (Clear Time on Compare Match Mode)와 Normal Mode 를

           비교하면 Counter의 카운트 값을 제어하는 측면에서 무엇이 다른가?

 

 

CTC Mode (Clear Time on Compare Match Mode)는 Counter의 Top 이라고 할 수 있는 OCRn (Output Compare Register n)를 설정함으로서 Counter가 카운트할 수 있는 상한선을 설정하게 된다. 이로 인해 Counter의 count한 값인 TCNT(Timer/Counter Register)가 OCNn에 도달하게 되면 더 이상 카운트를 하지 못하고, Output Compare Match Interrupt를 발생시키고, 다시 0부터 카운트를 시작한다.

 

 

하지만, 그와 반대로 Normal Mode는 TCNT Register를 특정 값으로 초기화함으로서 Counter가 0부터 카운트하는 것이 아닌 특정 값부터 카운트를 시작하게 되며, Counter가 Count한 값(=TCNT)이 MAX(= 8bit Timer/Counter인 경우 MAX값은 255 이다.)에 도달하면 Overflow Interrupt를 발생시키며, 초기화한다.

 

 

하지만, CTC Mode 경우 Output Compare Match Interrupt가 발생하고, Normal Mode 경우 Overflow Interrupt가 발생하지만, 두 경우 모두 Interrupt가 발생한 뒤, Counter가 Count한 값 (= TCNT Register)이 0으로 초기화하는 과정에서 세팅 값도 초기화 된다. 

 

 

따라서 CTC Mode 경우에는 OCRn (Output Compare Register n)을 재새팅해야 하며, Normal Mode 경우에는 TCNT Register 값을 재새팅해야 한다.

 

 

 

 

 

본론 (CTC Mode에 대한 실습)

 

이번에는 ATmega 128의 기본 클럭 주파수(16MHz)와 8bit timer/counter, Normal mode를 이용하여 250Hz 주파수를 가는 출력 신호를 만들어 보도록 하겠다. 또한 초기 출력 값은 0으로 세팅한 뒤, Overflow Interrupt가 발생하면 Toggle이 발생하도록 설계하겠다.

 

●  ATmega 128의 기본 클럭 주파수 (16MHz), 8bit Timer/Counter, Normal Mode 활용
●  출력 신호는250Hz 주파수를 갖는다.
●  Overflow Interrupt가 발생시 출력 신호에서 Toggle 발생

 

 

 

📌 1단계) 8bit Timer/Counter에는 Timer/Counter 0/2가 있는데, 어떤 것을 사용할 것인가?

 

경험담

생선된 파형을 출력하기 위해 "어느 포트에 출력을 발생시킬까?"에 대해서 고민하던 중 아래와 같은 문장을 보고, 혼란(?)을 겪었다.

TCCR (Timer/Counter Control Register) 요소의 값을 정하기 위해 Compare Output Mode 를 보던 중 "OC0 disconnected"을 보았다.

 

 "OC0 disconnected." 라는 문장에 대해서 "Normal Mode를 사용할 경우, OC0 핀을 사용할 수 없고, 다른 핀을 사용해야 한다."고 생각했다. 이는 잘못된 해석이였고, 정확한 해석은 다음과 같다.

 

CTC Mode와 Fast PWM Mode에서 적용되었던 출력핀 (OC0, OC2)의 제한 사항이
Normal Mode에서는 적용되지 않는다.

 

 

즉, Normal Mode를 통해 새로운 파형을 출력할 때에는 꼭 OC0나 OC2 핀을 출력할 필요없이 다른 핀에서도 Normal Mode로 생성된 파형을 출력시킬 수 있음을 의미한다.

 

 

 

    

Q) 그럼, 만약 2개이상의 핀을 출력으로 설정하고, 1개의 핀에서는 생성된 파형을 출력시키고, 나머지 핀에는 LED를 연결한다면 ATmega는 어느 핀이 파형을 출력시키는 핀이 어떻게 아는가?

 

A) 이 경우에는 어느 핀이든 상관 없이 출력으로 설정된 모든 핀에서 파형을 출력시킨다. 따라서 Normal Mode인 경우에는 4개 이상의 동일한 파형을 동시에 출력시켜야 할 경우 등 특수한 경우에만 사용하는 경우가 많다.

 

 

 

이번 Normal Mode에서는 출력핀을 OC0 (PORT B의 4핀, PB4)로 설정하겠으며, 이외에는 출력으로 설정하지 않을 것이다.

 

 

 

 

📌 2단계) 분주비 (Prescaler, N)과 OCRn (Output Comapre Register n) 을 설정

 

 

●  TCNTn (Timer / Counter Register n) : Counter가 count한 값
●  N : Prescaler\
●  OCn : Output Compare n
●  62.5 * 10 ^ -9 (ns) : ATmega 128의 주파수의 주기 

 

         

Q) 어떻게 위 식이 나오게 되었으며, 위 식이 의미하는 것은 무엇인가?

A) 아래 그림과 같이 TCNT (Timer / Counter Register) 값이 2번의 싸이클이 돌아야 출력 파형인 OCn에서 1주기가 출력되게 된다.

 

이는 즉, TCNTn에서 2번의 Overflow Interrupt가 발생해야 출력 파형인 OCn에서 한 주기가 나온다.

 

위 그림은 직접 그렸기 때문에 부정확하지만, TCNTn에서 2번의 Overflow Interrupt가 발생해야 OCn에서 한 주기를 갖는다는 것을 표현했다.

 

 

 그런데, 분주비(Prescaler)는 ATmega 128A의 16MHz 주파수의 여러 주기를 한 묶음으로 묶었음을 의미하기 때문에 TCNTn (Timer/Counter Register n)에서 1번 카운트했더라도 실제로느 분주비 만큼 카운트한 것이다. 

 

 

 

그래서 위 내용들을 토대로 분모의 식을 정리하면 다음과 같다.

 

 

TCNTn (= Counter가 카운트한 값)가 2번 싸이클 카운트 한 값은 실제로 2 * TCNTn * N 만큼 카운트한 것과 같고, 여기에 원래 16MHz 주파수의 주기인 62.5ns를 곱함하게 되면 다음과 같은 의미를 같는다.

 

TCNTn이 분주비를 하지 않았을 때, 2싸이클 카운트하는 데, 소요된 시간과 같다.

 

 

이는 우리가 구하고자 하는 250Hz의 주파수의 한 주기와 동일하며, 위 식을 역수로 취해줌으로서 우리가 ATmega 128의 기본 클럭인 16MHz와 Normal Mode를 통해 만들고 하였던 출력 신호의 주파수인 250Hz가 되는 것이다. 

 

 

 

위 관계식을 통해 적절한 TCNTn 값과 N (= Prescaler)을 구하면 TCNTn 값은 6이고, N (=Prescaler)는 128분주가 된다.

 

●  TCNTn (Timer/Counter Register) 의 초기 설정값 : 6
●  N (Prescaler) : 128
●  OCn (Output Compare n)의 주파수 : 250Hz

 

 

 

 

📌  3단계) TCCRn (Timer/Counter Control Register n)을 설정

 

TCCRn (= Timer / Counter Control Register n)

 

● WGM01, WGM00 (Waveform Generation Mode) : 0, 0
● COM01, COM00 (Compare Output Mode) : 0, 0
● CS02, CS01, CS00 (Clock Selcet Bit Description) : 1, 0, 1
● TCCRn (Timer/Counter Control Register) : ob0000 0101

 

 

 

 

본론 (Source Code)

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

int main(void)
{
    // PORTB 의 4핀을 출력 설정
	// Q) Compare Output Mode를 보게 되면 "OC0 disconnected." 라는 문장이 있는데, 
	//    이는 "Normal Mode 에서는 OC0를 사용할 수 없고, 다른 핀을 사용하라."는 의미 아닌가?
	//
	// A) 그것은 잘못된 해석이다."OC0 disconnected." 의미는 CTC Mode나 Fast PWM Mode에서는 OC0나 OC2 핀에서만 출력
	//    을 발생시킬 수 있었는데, "Normal Mode 에서는 해당 제한 사항이 사라졌다."는 의미이다.
	//    이는 즉, "Normal Mode에서는 OC0, OC2 뿐만 아니라 다른 핀에서도 출력 시키도록 할 수 있다."라는 의미이다.
	DDRB |= (1<<DDRB4); 
	PORTB &= ~(1<<PORTB4);
	
	// TCCR0 = Timer/Counter Control Register 0
	// Normal Mode의 Compare Output Mode 값은 0, 0이여야 한다.
	// 출력 신호의 주파수는 250Hz이며, 이를 위해 128분주를 사용.
	TCCR0 |= (1<<CS02 | 1<<CS00); 
	
	// TCNT0 = Timer/Counter Register 0
	//       = 초기 세팅
	TCNT0 = 255 - 249;
	 
    while (1) 
    {
		// Overflow Interrupt가 발생하기 전까지 
		while((TIFR & (1<<TOV0))==0);
		
		// Overflow Interrupt가 발생하면 출력 신호에 Toggle 발생
		PORTB ^= (1<<PORTB4);
		// TIFR (=Timer/Counter Interrupt Flag Register)
		// TIFR를 수동 초기화
		TIFR |= (1<<TOV0);
		
		// Overflow Interrupt로 인해 세팅 값 정보 사라짐.
		// TCNT0 값 재새팅
		TCNT0 = 6;
    }
}

  • Oscilloscope를 통해 확인한 결과, 예상했던 바와 같이 250Hz 주파수를 갖는 출력 신호를 확인할 수 있었고, 
    Overflow Interrupt가 발생할 때, 출력신호가 Toggle되는 것까지 확인할 수 있었다.
  • 한 눈금 당 5V이기 때문에 출력 신호의 1의 값이 5V인 점도 확인할 수 있었다.

 

 

정리

 

  1. CTC (Clear Timer on Compare Match) Mode는 OCRn (Output Compare Register n)을 설정함으로서 TCNTn Register의 값이 0부터 OCRn까지만 카운트할 수 있기 때문에 OCRn 값을 통해 컨트롤 했다.
  2. Normal Mode는 CTC Mode와 달리 TCNTn Register 값을 초기 설정함으로서 0부터가 아닌 특정 값부터 카운트를 시작하여 MAX 값에 도달하게 되면 Overflow Interrupt를 발생하게 된다. 즉, TCNTn 값을 통해 컨트롤 했다.

 

 

여담

Q) 정말 OC0와 OC2가 아닌 다른 포트에서도 생성된 파형을 출력시킬 수 있는가?

 

  • PORT B의 7번 핀, PORT E의 2번 핀에 통해 다른 핀에서도 생성된 파형 출력이 가능함을 확인