임베디드 개발(before)/IoT 임베디드 SW 개발자 양성과정

[19일차] 임베디드 C 프로그래밍 실습(시계 만들기)

주운녕 2020. 8. 6. 17:28

오늘은 C언어로 배웠던 기능들을 활용하여 시계를 만드는 실습활동을 했다.

사실 인터넷에 워낙 많이 나와있는 예제가 많아서, 평가항목에 맞게 배운 기능들을 활용하는데 중점으로 코드를 작성했다.

가장 의미 있게 새로 알게 된 것은, 디버그 모드와 릴리즈 모드를 설정하여 디버그 모드에서 print를 통해 오류를 검출하는 코드를 작성한 것이다.


- 모드를 1과 2로 나누어, 입력하는 모드에 따라 스톱워치 또는 현재시각을 출력하는 프로그램을 만들었다.

- 각각의 모드는 함수로 만들었다. 배열과 포인터를 사용하기 위해 필요이상으로 사용했다.

#include <stdio.h>
#include <time.h>
//디버그 모드 설정 
#ifdef DEBUG
#define DPRINTF(fmt,...) printf( "%s:%d: " fmt, __FUNCTION__, __LINE__)
#else
#define DPRINTF  //코드내의 이 함수를 제거 하여 출력하지 않는다.
#endif

#define	msec 10 //sleep 시간 단위 = 10ms

void stop_watch(int sw[]);	//스탑 와치 함수 선언
void get_dt(void);			//현재시각 함수 선언

int main(void){
	DPRINTF("main문 실행\n");
	int mode; //모드를 입력받는 변수
	int sw[4]={0}; // 인덱스0부터 micro sec, sec, min, h 
	
	time_t t = time(NULL); // 현재 시각을 초 단위로 얻기
	struct tm tm = *localtime(&t); // 초 단위의 시간을 분리하여 구조체에 넣기
	DPRINTF("현재시각 획득함\n");
	printf("=====================================\n");
 	printf("오늘은 %d년 %d월 %d일 입니다.\n", tm.tm_year+1900, tm.tm_mon+1, tm.tm_mday);
 	printf("- 모드를 선택해주세요\n- 스탑워치 : 1 / 현재시각 : 2\n");
 	scanf("%d", &mode);	//모드 입력
 	DPRINTF("모드입력 실행\n");
 	//모드 선택
	switch(mode){
		case 1:
	 		stop_watch(sw);	//스탑워치 함수 실행
			break;
		case 2:
			get_dt(); 		//현재시각 함수 실행
			break;
	}
	return 0;
}
//스탑 와치 함수 정의
void stop_watch(int sw[]){ 
	DPRINTF("스탑워치 모드 들어감\n");
	while(1){
	int *p=sw; //배열 주소 포인터 변수에 저장
 	printf("\r%dh %dm %d.%ds", *(p+3), *(p+2), *(p+1), (*p)++); //주소로 접근하여 배열값 수정 및 출력
 	Sleep(msec); 			//10ms(0.01초)간 Sleep
 	if(*p>99){				//1000ms (1초) 지날시 
 		(*(p+1))++; 		//초단위 +1
 		*p=0;				//10ms단위 0으로 초기화
 		DPRINTF("1초 경과\n");
	 }else if(*(p+1)>59){	//60초 지날시
	 	(*(p+2))++;			//분(m)단위 +1
	 	*(p+1)=0;			//초(s)단위 0으로 초기화
	 	DPRINTF("1분 경과\n");
	 }else if(*(p+2)>59){	//60분 지날시
	 	(*(p+3))++;			//시간(h)단위 +1
	 	*(p+2)=0;			//분(m)단위 0으로 초기화
	 	DPRINTF("1시간 경과\n");
	 }
	 if(*(p+3)>23)	break;	//24시간 경과시 프로그램 종료.
	}
}
//현재시각 함수 정의
void get_dt(){
	DPRINTF("현재시각모드 들어감\n");
	while(1){
	static int sec;
	time_t t = time(NULL); 			// 현재 시각을 초 단위로 얻기
	struct tm tm = *localtime(&t);	// 초 단위의 시간을 분리하여 구조체에 넣기
	//이전 초가 현재 초랑 다르면(1초가 흐르면) 시간 출력
	if(tm.tm_sec!=sec){
		//\r 를 이용하여 동일 줄에 시각 표시
		DPRINTF("1초 경과\n");		
		printf("\r현재 시각은 : %d시 %d분 %d초 입니다.", tm.tm_hour, tm.tm_min, tm.tm_sec); 
	}
	//이전 초 저장
	sec=tm.tm_sec;
	}
}

 

- 디버그 모드 설정 방법 (DEV-C++)

 

컴파일 시 원하는 모드를 선택 할 수 있다.

 

debug 모드일 경우 , -DDEBUG 명령을 추가하였다.

#include <stdio.h>
#include <time.h>
//디버그 모드 설정 
#ifdef DEBUG
#define DPRINTF(fmt,...) printf( "%s:%d: " fmt, __FUNCTION__, __LINE__)
#else
#define DPRINTF  //코드내의 이 함수를 제거 하여 출력하지 않는다.
#endif

- 디버그 모드에서 DEBUG 명령을 넣었기 때문에 디버그 모드 실행시 DPRINTF로 재정의된 printf 문을 출력할 수 있다. 코드의 원하는 부분에 DPRINTF("원하는 출력문장"); 을 추가하면 디버그 모드에서 해당 문장과 위치한 함수, 줄번호가 함께 출력된다. 

 

- 실행 화면

  Release 모드 Debug 모드
스탑워치
현재 시각

 

 

 

 

 


* 개인적인 학습 목적으로 작성한 글이기에 내용에 잘못된 정보가 있을 수 있습니다.