volatile
Original Page : http://blog.naver.com/nsangil82/80031406565

volatile는 C의 키워드중 하나이다. 아마 처음보거나 익숙하지 않은 키워드일 것이다. 이 녀석을 이해하기 위해서는 컴파일러의 옵티마이즈(Optimize)옵션에 대해서 먼저 알아야 한다. 옵티마이즈 옵션은 한마디로 C 컴파일러의 코드 최적화 옵션을 말한다. 아래의 코드를 한번 보자.

예1)
*(unsigned int *)0x70A0 = 0x4001; //0번
*(unsigned int *)0x70A0 = 0x4002; //1번
*(unsigned int *)0x70A0 = 0x4003; //2번
*(unsigned int *)0x70A0 = 0x4004; //3번
*(unsigned int *)0x70A0 = 0x0550; //4번


위 코드를 컴파일러의 입장에서 보면 0~3번은 아무 필요없는 코드가 된다. 따라서 컴파일러는 코드 최적화를 위해 0~3번까지의 코드를 전부 제거하고 4번 코드만 컴파일해서 어셈블리 코드를 만든다. 이것이 컴파일러의 옵티마이즈다.

사실 소프트웨어인 컴파일러의 입장에서 위의 옵티마이즈는 당연한 것이다. 그러나 하드웨어적(임베디드 시스템)인 입장에서 이러한 C 컴파일러의 옵티마이즈는 치명적인 결과를 불러이르킬 수 있다. 만약 위의 예1의 "0x70A0" 라는 주소가 단순한 메모리 주소가 아닌 peripherial에 접근하는 MMR(Memory Mapped Register)이라고 생각해보자. 그렇다면 이 레지스터는 단순히 값을 저장하는 역활이 아닌 peripherial을 제어하는 역활을 한다. 따라서 위 코드의 0~4번 코드 모두는 맡은 바 역활이 다 있다. 따라서 옵티마이즈 당하면 안되는 코드들이다. 바로 이때 쓰는 C키워드가 "volatile"라는 키워드다. volatile 키워드를 써서 올바로 코드를 바꾸면 아래와 같다.

예2)
*(volatile unsigned int *)0x70A0 = 0x4001; //0번
*(volatile unsigned int *)0x70A0 = 0x4002; //1번
*(volatile unsigned int *)0x70A0 = 0x4003; //2번
*(volatile unsigned int *)0x70A0 = 0x4004; //3번
*(volatile unsigned int *)0x70A0 = 0x0550; //4번

즉 hardware 적으로 꼭 필요하나 software 관점에선 불필요한 코드의 옵티마이즈를 막기위해서 "volatile"라는 키워드가 필요한 것이다. 정리해서 volatile 키워드가 필요한 경우는 아래와 같다.

* memory-mapped periherral registers

* 인터럽트 서비스 루틴에 의해 수정되는 전역변수

* 멀티 태스킹 또는 멀티 쓰레드 에서 사용되는 전역변수


임베디드 프로그래밍 관련 서적 집필로 유명한 Michael Barr는 그이 저서 "Programming Embedded Systems in C and C++"에서peripherial을 억세스 할때는 잔말 말고 무조건 volatile 키워드를 사용하라고 우리에게 협박(?)까지 하고 있다고 한다.



신고
Posted by Proneer

댓글을 달아 주세요

  1. ㅡㅡ

    역활 ....... 맞춤법 ..... 역할입니다.

    2015.08.19 15:54 신고 [ ADDR : EDIT/ DEL : REPLY ]


티스토리 툴바