Code Vison AVR C ATmega 8535 RS232 시리얼통신 컨넥터와신호선 RS232 통신을위한컨넥터는 9핀과 25핀컨넥터가있으나, 최근에는 9핀컨넥터를많이사용한다. 실제데이터가송수신되는핀은 TXD(3) 와 RXD(2) 이고기능은다음과같다. 9 핀컨넥터의모습 TXD - Transmit Data 비동기식직렬통신장치가외부장치로데이터를보낼때, 직렬통신데이터가나오는신호선 RXD - Receive Data 외부장치에서들어오는직렬통신데이터를입력받는신호선케이블을만들때에는반대쪽커넥터에연결하기전에한번교차시켜야한다. (Rx ->Tx, Tx->Rx) ATmega8535 에서의 RXD, TXD
MAX232 MAXIM사에서생산되는 RS-232통신을가능토록해주는송수신 IC이다. 송수신드라이브를각각 2개씩가지고있다. AVR과컴퓨터가인식하는 0과 1의값이다르기때문에.. 마이컴컴퓨터 이차이를해결해주는것이다. 0 0V -10V 1 5V 10V TTL IC 의전원단자와다르게 15 번핀이 GND, 16 번이 VCC 이므로주의하자 IC 내부에는 VOLTAGE DOUBLER와 VOLTAGE INVERTER가있다. DOUBLER는 5V를 10V로증폭 INVERTER는증폭된신호를반전내부에 5V를충전했다 10V로보내기위한콘덴서가있다. MAX232 는전압을바꾸어주는역할만을하며통신을하는것은아님에주의!
프레임형식 직렬데이터프레임은동기비트 ( 스타트, 스톱비트 ) 와에러검사를위한패리티비트 ( 선택가능 ) 와데이터비트를포함하는 1문자를의미한다. 컴퓨터쪽에서는다음과같이설정한다. 보레이트 9600 데이터비트는 8 비트패리티비트사용안함 STOP 비트는 1 로설정한모습
시리얼통신을위한레지스터 ATmega8535에는시리얼통신용컨트롤러가포함되어있다. CPU 내부에서 CPU의코어부분과시리얼통신용컨트롤러가데이터를주고받고, 컨트롤러는 RxD, TxD의핀을통해외부와통신을하고있다. 시리얼통신을위한레지스터에는설정용레지스터와데이터통신용레지스터가있고설정용레지스터를이용해설정을하고통신용레지스터를이용해실제통신을한다 UDR RXB (Read) TXB (Write) UDR레지스터는데이터를입력하면설정한값에맞게데이터를전송하는레지스터이다. UDR레지스터를읽으면수신데이터버퍼레지스터 (RXD) 의내용을볼수있다. 즉, 송신데이터를 UDR레지스터에쓰기하면송신데이터버퍼 (TXB) 에저장하고, 수신데이터를 UDR 레지스터에쓰기하면수신데이터버퍼 (RXB) 에수신되어있는값이읽혀진다. UCSR 레지스터 UCSR 은 A,B,C 세개로구성되어있고, 상태설정과제어의기능을한다. UCSRA RXC TXC UDRE FE DOR PE U2X MPCM 7. RXC : 수신완료표시비트 6. TXC : 송신완료표시비트 5. UDRE : 송신데이터레지스터준비완료표시비트 4. FE : 프레임에러표시비트 3. DOR : 데이터오버런에러표시비트 2. PE : 패리티에러표시비트 1. USX : 송신속도 2배설정 0. MPCM : 멀티프로세서통신모드 *1번과 0번을설정하고나머지는읽기전용이다. ( 사용할때 1 아닐때 0)
UCSRB RXCIE TXCIE UDRIE RXEN TXEN UCSZ2 RXB8 TXB8 7. RXCIE 수신완료인터럽트인에이블비트 6. TXCIE 송신완료인터럽트인에이블비트 5. UDRIE 송신데이터레지스터준비완료인터럽트인에이블비트 4. RXEN 수신기인에이블 3. TXEN 송신기인에이블 2. UCSZ2 전송데이터길이선택비트 1. RXB8 수신데이터비트 8 0. TXB8 송신데이터비트 8 UCSRC URSEL UMSEL UPM1 UPM0 USBS UCSZ1 UCSZ0 UCPOL 7. UREL 레지스터선택비트 6. UMSEL 시리얼통신모드설정비트 5. UPM1 패리티모드설정비트 4. UPM0 패리티모드설정비트 3. USBS 정지비트선택 2. UCSZ1 전송데이터비트수설정 1. UCSZ0 전송데이터비트수설정 0. UCPOL 클럭극성선택 보레이트속도설정관련레지스터 보레이트 - 신호하나의속도보레이트속도를조절하는레지스터는 UBRRH와 UBRRL 2개로이루어져있다. UBRRH의 4비트와 UBRRL의 8비트를합친 12비트를이용하여속도를설정한다. UBBRH URSEL 사용하지않음 ( 0 ) UBRR의값 (11 ~8 비트 ) UBBRL UBRR의값 (7 ~0 비트 )
UBRRH는 UCSRC레지스터와같은번지를사용하고있다. 그렇기때문에 UCSRC로사용할것인지 UBRRH로사용할것인지선택을해야하는데, 이기능을하는것이 7번 URSEL비트이다. URSEL이 0일때 UBRRH의기능을갖고 1일때 UCSRC의기능을갖는다. UBRR 의값은보레이트와시스템클럭을이용하여계산한다. UBRR 시스템클럭 16 보레이트 1 예를들어시스템클럭이 16Mhz 이고보레이트를 9600 bps로잡았을때 UBRR 16000000 1 103.1666 16 9600 UBRR의값은 103.1666... 이된다. 여기서소수점이하를버리고 103을 2진수로변환하면 1100111이된다. 결국 UBRRH의 4 비트에는모두 0이들어가고 UBRRL에는 01100111이들어가므로, 다음과같이입력한다. UBRRH=0; UBRRH=103; // 물론 0b01100111으로도입력가능하다. 데이터전송레지스터 직렬통신에사용하는입출력함수 void puts(char *str) 외부로 SRAM의문자열을출력하는기능을가진다. 문자열의끝부분에는 null(0x0a) 를추가하여출력한다. null 문자는터미널화면에서줄바꾸기를한다. 하지만줄의맨앞이아닌최종출력지점의바로다음줄로출력된다. Ex) Hello NClab! Hello NClab! 터미널의제일첫줄로줄바꿈을하기위해서는제어문자인 "\r"=>"0x0d+0x0a" 를끝부분에첨가하거나다음문장에 "0x0D" 를출력하여커서를맨앞으로이동시킨다. void putsf(char flash *str) 외부로 Flash의문자열을출력하는기능을가진다. 줄바꿈형식은 puts와동일
void printf(char flash *fmtstr [,arg1,arg2,...]) fmtstr 문자열에있는문자열을출력하는기능을가진다. 특히, fmtstr은상수이며 Flash 메모리에위치해있어야한다. Ex) int_val = 112; printf("interger value =%5i", int_val); // %5i 는 5칸에정수를출력하라는뜻 직렬통신프로그램 출력함수들을사용해보자 #include <mega8535.h> #include <stdio.h> void rs232_putchar(void) putchar('i'); putchar(' '); putchar('l'); putchar('o'); putchar('v'); putchar('e'); putchar(' '); putchar('n'); putchar('c'); putchar(0x0a); putchar(0x0d); } // 한글자씩출력하는 putchar() 을사용한함수 // 줄바꿈 // 커서제일앞으로 void main(void) char data[] = "I LOVE NC 2"; //SRAM 의문자열을출력하기위한문자열배열 // USART initialization // Communication Parameters: 8 Data, 1 Stop, No Parity // USART Receiver: On
// USART Transmitter: On // USART Mode: Asynchronous // USART Baud Rate: 9600 UCSRA=0x00; UCSRB=0x18; UCSRC=0x86; UBRRH=0x00; UBRRL=0x33; rs232_putchar(); // 한글자씩출력하는함수호출 puts(data); putchar(0x0d); //SRAM의문자열출력 // 줄바꿈 } putsf("i LOVE NC 3 \r"); //Flash 의문자열출력 ( 줄바꿈문자 \r) 포함 결과 I LOVE NC I LOVE NC 2 I LOVE NC 3 입력은어떻게받는지알아보자 #include <mega8535.h> #include <stdio.h> unsigned char rx_data; // 수신된문자를받기위한전역변수 void led_control(void) rx_data = getchar(); //getchar() 은수신데이터를받는함수이다 (UDR). putchar(rx_data); // 받은문자를출력함으로써에코효과 switch (rx_data) // 받은문자에따라행동 case 0x30: PORTA = 0x00; //0X30은 '0' 에해당하는 ASCII코드임 //'0' 일때 PORTA에 0을출력 case 0x31: PORTA = 0x01; //0X31은 '1' 에해당하는 ASCII코드임
} case 0x32: PORTA = 0x02; //0X32은 '2' 에해당하는 ASCII코드임 case '3': PORTA = 0x03; // 직접 '3' 이라는문자를적어줄수있음 case '4' :PORTA = 0x04; case '5': PORTA = 0x05; case '6': PORTA = 0b00110011; // 물론출력은 2진수로도쓸수있다. default: PORTA = 0x00; }; void main(void) PORTA=0x00; DDRA=0xFF; //PORTA 는모두출력모드 // USART initialization // Communication Parameters: 8 Data, 1 Stop, No Parity // USART Receiver: On // USART Transmitter: On // USART Mode: Asynchronous // USART Baud Rate: 9600 UCSRA=0x00; UCSRB=0x18; UCSRC=0x86; UBRRH=0x00; UBRRL=0x33; while (1) // 무한루프로입력을감지한다. led_control(); // 함수호출 }; } 결과 0~6까지의입력에따라 LED가반응한다.
응용프로그램 : 입력을받아 LCD에표시해보자 #include <mega8535.h> #asm.equ lcd_port=0x15 #endasm #include <lcd.h> #include <stdio.h> unsigned char getdata; // 입력된 ASCII 코드를담을변수 void char_input (void) // 입력받은문자에따라행돌할함수 getdata = getchar(); // 입력된문자를받고 switch (getdata) case 0x0D: //Enter키 lcd_gotoxy(0,1); //2행 1열로커서옮김 ( 줄바꿈 ) case 0x1B: //Esc키 _lcd_ready(); //LCD 데이터수신준비 _lcd_write_data(0b00000001); // 클리어명령 case 0x09: //TAB키 _lcd_ready(); _lcd_write_data(0b00011000); // 전체화면왼쪽으로쉬프트 case 0x08: _lcd_ready(); //BackSpace키 _lcd_write_data(0b00010000); // 커서를왼쪽으로한칸옮김 lcd_putchar(0x20); // 공백문자입력 _lcd_ready(); _lcd_write_data(0b00010000); // 커서를왼쪽으로한칸옮김 default: lcd_putchar(getdata); // 받은문자를 LCD로출력 putchar(getdata); // 컴퓨터화면에출력 ( 에코 ) PORTA = getdata; //LED로출력 (ASCII code를볼수있다.) }; }
void main(void) PORTA=0x00; DDRA=0xFF; //LED로 ASCII code출력을위해모두출력모드로 // USART initialization // Communication Parameters: 8 Data, 1 Stop, No Parity // USART Receiver: On // USART Transmitter: On // USART Mode: Asynchronous // USART Baud rate: 9600 UCSRA=0x00; UCSRB=0x18; UCSRC=0x86; UBRRH=0x00; UBRRL=0x33; lcd_init(16); _lcd_ready(); _lcd_write_data(0b00001111); // 표시 ON/OFF제어표시, 커서, 점멸모두 ON printf("enter : "); // 입력하라는안내문표시 while (1) // 무한루프로입력을감지 char_input(); // 함수호출 }; } /********************************************* This program was produced by Talsu RS232시리얼통신을이용하여키보드의입력을받아 LCD화면에표시해주는프로그램입니다. 키입력이자유롭게되고. Enter키 = 줄바꿈 Backspace = 한글자지우기 space = 띄우기 TAB = 화면쉬프트 *********************************************/