• 검색 결과가 없습니다.

응용 프로그램에서 I/O 제어

문서에서 GettingStarted-with-HBE-EMPOSII (페이지 69-73)

6. 응용 프로그램 작성

6.2. 응용 프로그램에서 I/O 제어

리눅스 시스템에서 파일이나 장치 디바이스를 메모리에 대응시키는 여러 방법을 제공하고 있으며. 그 중에 하나가 mmap함수이다 이 함수는 열린 파일 기술자를 통해 액세스 되는 파일의 내용과 관련된 메모리의 구역에 대한 포인터를 생성한다. 즉 이것을 이용하여 특 정 메모리 어드레스에 접근 하여 그 곳의 값을 변경할 수 있다.

mmap함수와 munmap함수의 원형은 다음과 같다.

#include <sys/mman.h>

void *mmap(void *start, size_t length, int prot, int flags, int fd, off_t offset);

int munmap(void *start, size_t length);

mmap함수는 fd로 지정된 파일(또는 다른 객체)에서 offset을 시작으로 length 바이트만큼 을 start 주소로 대응 시킨다. 이 주소는 단지 지정된 해당 주소로 했으면 좋겠다는 의미 이며, 보통 “0”으로 지정한다. mmap함수는 지정된 영역에 대응된 실제 시작위치의 포인 터를 반환한다.

port 인자는 원하는 메모리 보호모드를 설정한다. 해당 비트는 아래와 같다.

PROT_READ : 페이지 읽기 허락

PROT_WRITE : 페이지 쓰기 허락

PROT_EXEC : 페이지 실행

PROT_NONE : 페이지 접근 불가

flags 인자는 대응된 객체의 타입, 대응 옵션과 대응된 페이지 복사본에 대한 수정이 해당 프로세스에만 보일 것인지, 아니면 다른 참조하는 프로세스와 공유 할 것 인지를 설정한 다.

MAP_FIXED : 지정된 주소 이외의 다른 주소를 선택하지 않는다.

MAP_SHARED : 객체에 대응 시키는 다른 모든 프로세스와 대응 영역을 공

유한다.

MAP_PRIVATE : 다른 프로세스와 대응 영역을 공유하지 않는다.

mmap함수로 지정된 주소 공간의 사용이 완료되었으면, 대응된 주소 공간을 헤제 해 주 어야 하는데 munmap함수가 이 부분을 담당하게 된다.

6.2.1 mmap함수를 이용한 I/O제어

led와 push button을 제어 하기 위해 다음과 같이 소스 파일을 생성한다.

- led.c

/* ************************************************************ */

/* Test program of 8 bits LED output and button input */

/* Hanback Electronics */

/* Date: march 2003 */

/* ************************************************************ */

#include <stdlib.h>

#include <unistd.h>

#include <sys/mman.h>

#include <asm/fcntl.h>

#include <stdio.h>

#define ADDRESSOFLED 0x10600000

#define ADDRESSOFPUSHBUTTON 0x10500000

int main(void) {

int fd;

unsigned char *addr_led, *addr_button;

unsigned char go,dir;

unsigned char val, val2;

dir = 'l';

if ((fd=open("/dev/mem",O_RDWR|O_SYNC)) < 0) { perror("mem open fail n");

exit(1);

if(((int)addr_led < 0) | ((int)addr_button < 0)){

addr_led=NULL;

addr_button = NULL;

close(fd);

printf("mmap error n");

return -1;

printf(" n8bit LED IO Interface Procedure n");

printf("--- n");

printf(" push the sw0, then right shift n");

printf(" push the sw7, then left shift n");

printf(" otherwise exit n");

printf("--- n");

*addr_led = 0;

val = 0;

val2 = 0;

while(dir != 'q'){

if(dir == 'l') {

val2 = ( (val >> 7)) & 0x1;

val = (val << 1) | val2;

else if( dir == 'r') {

val2 = ( (val << 7)) & 0x80;

val = (val >> 1) | val2;

*addr_led = val;

go = (*addr_button);

if( go != 0x0)

usleep(100000);

*addr_led = 0x00;

munmap(addr_led, 1);

munmap(addr_button,1);

close(fd);

return 0;

- Makefile

# 8bits - LED Display Makefile

# Hanback Electronics

CC = arm-linux-gcc

led: led.c

$(CC) $(CFLAGS) -o $@ $^

clean:

rm -f led

위의 프로그램은 존슨 카운트 로직을 이용하여 led의 비트의 값을 쉬프트 하면서 푸쉬 버 튼 값을 읽어 들여 led의 쉬프트 방향을 바꾸어주는 예 이다. 우선 open()을 이용하여 메 모리 드라이버의 파일 기술자를 얻어 내고 이것과 mmap함수를 사용하여 led와 푸쉬 버 튼의 주소를 접근할 어드레스를 얻는다. 이 어드레스가 바로 addr_led와 addr_button이고

*addr_led와 *addr_button은 그 어드레스에 있는 값이다. 이로써 우리는 *addr_led에 값 을 쓰므로 led가 끄거나 켤 수 있고 *addr_button의 값을 읽어드리므로 버튼 스위치가 눌 려 있는지 그렇지 않은지를 알 수 있다. 그리고 while 루프를 돌면서 led를 존슨 카운트 로직에 따라 쉬프트 시키면서 push button 값을 읽어 들여 조건에 따라 led의 쉬프트 방 향을 바꿀 수 있고 또한 while루프를 빠져나갈 수도 있다. 그 다음에 munmap함수를 이 용하여 각각의 어드레스를 해제하고 파일을 닫고 프로그램을 마친다.

7. 웹 서버 포팅

EMPOSⅡ에 웹 서버를 포팅 하여 웹 서비스가 가능하다. 우리가 선택한 웹 서버는 goahead이며 소스는 http://www.goahead.com에 가서 간단한 신상명세를 등록만 하면 무료로 다운 받을 수 있다. 이 웹 서버는 임베디드 시스템용으로 디자인되어 있어 모듈이 작고 적은 양의 ram으로도 운용이 가능하며 다양한 기능들을 – ‘액티브 서버 페이지, 임 베디드 자바스크립트, in-process CGI forms, SSL, Digest Acess Authentication, User Management, and standard CGI’ - 지원하고 있다.

문서에서 GettingStarted-with-HBE-EMPOSII (페이지 69-73)