레이블이 Ubuntu인 게시물을 표시합니다. 모든 게시물 표시
레이블이 Ubuntu인 게시물을 표시합니다. 모든 게시물 표시

월요일, 1월 09, 2017

[Linux/C] dup 명령어

월요일, 1월 09, 2017
dup는 사용중인 파일 디스크립터 (File Descriptor, 이하 fd)를 복사해주는 명령어이다.

unistd.h에 정의되어 있으며, 다음과 같이 두 가지 형태가 있다.
#include <unistd.h>
int dup (int filedes);
int dup2 (int filedes1, int filedes2);
filedes (또는 filedes1)에 복사하고자 하는 fd를 인자로 넣어준다.

dup() 함수는 open() 함수와 마찬가지로 할당 가능한 fd 값 중 가장 작은 번호를 return한다. 이미 예약되어 있는 0, 1, 2는 제외하고 3번부터 할당이 시작된다.

dup2() 함수는 filedes1가 참조하고 있는 파일에 대해 새로운 fd를 생성하는데, filedes2에 사용자가 인자로 제공한 값으로 생성을 한다. 즉, filedes1을 filedes2로 복사하는 것이다. 사용자가 원하는 숫자로 fd를 할당할 수 있다는 점에서 dup() 함수와 차이가 있다.

예제와 함께 살펴보자.
  1 #include <stdio.h>
  2 #include <fcntl.h>
  3 #include <unistd.h>
  4
  5 int main(void) {
  6   char *fname = "result.txt";
  7   int fd1, fd2;
  8
  9   if((fd1 = creat(fname, 0666)) < 0) {
 10     printf("creat error\n");
 11     return 1;
 12   }
 13
 14   printf("First one is on the screen.\n");
 15   fd2 = dup2(fd1, 1);
 16   printf("Second one is in this file.\n");
 17   printf("fd2:%d\n", fd2);
 18   return 0;
 19 }
15행을 보면 dup2() 함수를 사용해 result.txt 파일의 fd를 1로 복사한다. 1번 fd는 표준출력 (stdout)을 뜻하기 때문에 이후에 printf를 통해 문자열을 출력할 경우 콘솔창이 아니라 result.txt 파일로 출력이 될 것이다. 따라서 위 코드를 실행시켜보면, 콘솔창에 "First one is on the screen"이 출력될 것이고, 새로 생성된 result.txt라는 파일에 "Second one is in this file", 그리고 "1"이 출력되어 있을 것이다.

목요일, 9월 29, 2016

VirtualBox 게스트 확장 (Guest Additions) 설치

목요일, 9월 29, 2016

VirtualBox에서는 가상머신의 성능을 높이고 다양한 기능을 제공하기 위해서 게스트 확장 (Guest Additions) 설치라는 것을 제공한다. 이는 일종의 추가적인 드라이브로서, VirtualBox에서 운영체제별로 제공한다.

VirtualBox에 처음 Ubuntu를 설치하였을 때 필요한 기초 세팅 중 하나이기 때문에 반드시 숙지해두어야 한다. 화면 해상도 설정이나 공유 폴더 설정 등 편리한 기능들을 사용하기 위해서 꼭 필요하다.

우선 Guest를 구동시킨 뒤 메뉴에서 장치 - 게스트 확장 CD 이미지 삽입을 클릭한다.


그러면 아래와 같은 링크가 뜨는데, 자동으로 설치해주겠다는 소리이니 Run을 선택하면 된다.


그러면 자동으로 터미널이 열리면서 설치가 진행된다.


설치가 완료되었다면 엔터를 쳐서 터미널을 빠져나오자.

그런데, 만약 다른 설정과 꼬여서 게스트 확장 설치가 정상적으로 완료되지 않았다면, 바탕화면 혹은 좌측의 메뉴 바에 생성된 마운트 파일을 열어서 autorun.sh 라는 파일을 실행시켜주면 된다.


실행 방법은 해당 위치에서 오른쪽 클릭 후 현재 위치에서 터미널을 연다음,
sh autorun.sh
이렇게 입력해주면 된다. 그러면 똑같은 설치 절차가 진행된다. 혹은 만약 원래 버전보다 높은 새 버전의 게스트 확장 설치를 할 경우 이전 버전을 삭제한 뒤 새 버전을 설치해준다.

만약 그래도 제대로 설치가 안된다면, 터미널에
sudo apt-get install dkms
sudo /etc/init.d/vboxadd setup
을 입력하면 된다.

화요일, 9월 27, 2016

VirtualBox Ubuntu 공유폴더 설정

화요일, 9월 27, 2016
VirtualBox를 사용하여 작업을 하다보면, Host와 상호작용할 일이 많다. 특히 파일을 공유해야 할 경우가 생기는데, 여러 방법 중 하나인 공유폴더 설정에 대해 알아보도록 하겠다.

이 과정은 VirtualBox의 게스트 확장 설치가 선행되어야 하므로, 게스트 확장 설치가 완료된 상태가 아니라면 먼저 아래의 링크를 참고하여 게스트 확장 설치를 진행해야 한다.


준비가 완료되었다면 우선 VirtualBox를 실행했을 때 나타나는 화면에서 원하는 Guest를 선택하고 하단의 공유폴더를 선택한다.
그러면 다음과 같은 화면이 나타나는데, 우측의 추가 버튼을 클릭한다.
이어서 뜨는 팝업창에 Host PC에서 공유 폴더로 사용할 폴더의 경로를 입력해주고, 자동 마운트 항목에 체크를 해준다. 이때, C:\share나 D:\share와 같이 비교적 간단한 경로에 폴더를 생성하길 권장한다. 경로의 길이가 길어지면 Protocol Error가 발생하곤 한다.
자동 마운트 옵션을 활성화했기 때문에 Guest PC를 부팅하고 파일 탐색기를 열면 Device 목록에 자동으로 공유 폴더 정보가 나타나는 것을 확인할 수 있다.
이제 사용자 계정에 권한 설정만 해주면 된다. 터미널을 열고 자신이 사용하는 사용자 계정을 username부분에 포함하여 다음 명령어를 입력하면 된다.
sudo usermod -aG vboxsf username
vboxsf는 VirtualBox에서 사용되는 파일시스템의 이름으로, 신경쓰지 않아도 된다.

여기까지 하면 Host PC와 Guest PC 사이의 공유 폴더 설정은 완료된 것이다. 그러나, 만약 자동으로 생성된 경로가 아닌, 다른 임의의 경로에 공유 폴더를 직접 만들고 싶다면 어떻게 해야 하는지 알아보자.

먼저 Guest PC를 구동시킨 다음 터미널에서 /mnt/share라는 디렉터리를 관리자 계정 권한으로 생성한다. 다른 경로와 디렉터리명을 사용하고 싶다면 이 부분을 임의대로 바꿔도 된다.
sudo mkdir /mnt/share
그 다음 관리자 계정 권한으로 vboxsf라는 파일시스템을 활용해 마운트를 한다.
sudo mount -t vboxsf share /mnt/share
share이라고 적힌 부분에는 Host에서 설정해둔 폴더 이름을 넣어주면 된다. 그런데, 만약 vboxsf가 알 수 없는 파일시스템이라며 오류 메시지가 뜰 경우에는 게스트 확장 설치가 제대로 되어 있지 않은 것이기 때문에 설치를 진행한 뒤 다시 시도하면 된다.

마운트가 완료되었다면 vim 에디터를 통해 test.txt라는 파일을 만들어보자.
저장한 뒤에 Host에서 공유 폴더로 지정해둔 경로(C:\share)에 가보면 정상적으로 파일이 공유되고 있음을 확인할 수 있다.
mount를 해제하고자 한다면, umount 명령어를 사용하면 된다.
umount /mnt/share
mount를 해제할 경우 해당 디렉터리에서는 기존에 동기화되어 있던 모든 파일과 디렉터리들이 없어지게 되지만, 실제 공유 폴더에는 여전히 모든 정보들이 보존된다.

일요일, 9월 11, 2016

System Project: CPU Scheduling Simulator

일요일, 9월 11, 2016

1. Introduction
2016년 1학기 운영체제 수업에서 텀프로젝트로 진행했던 CPU Scheduling Simulator이다. 프로세스의 생명주기를 실제와 유사하게 표현하였고, 다양한 스케줄링 알고리즘들을 구현하여 각각의 알고리즘마다 어떤식으로 스케줄링이 이루어지며, 성능은 어떤지 비교분석을 해준다.
원활한 시뮬레이션을 위해 프로세스마다 CPU Burst Time을 예측할 수 있다는 전제를 바탕으로 하며, 조금 더 현실에 가깝게 하기 위해 I/O 작업을 수행하는 프로세스도 구현하였고, 역시 I/O 작업을 수행하는데 걸리는 시간도 예측할 수 있다고 전제하였다.
시뮬레이션을 하기 위한 프로세스의 갯수와, 그 중에서 I/O 작업을 수행할 프로세스의 갯수를 사용자로부터 입력받아서 여러 알고리즘들을 통해 시뮬레이션한 결과를 출력해준다.

2. Demo

3. 개발 환경
Ubuntu 16.04 LTS 환경에서 C언어로 작성하였으며, 컴파일러는 gcc 5.4.0 버전을 사용하였다. 콘솔 기반의 프로그램이기 때문에 입력과 출력이 모두 콘솔상에서 이루어진다.

4. 구현 알고리즘
FCFS (First Come First Served)
- 가장 먼저 Job Queue에 도착한 프로세스가 가장 먼저 수행되는 알고리즘이다.

SJF (Shortest Job First)
- CPU Burst Time이 가장 적게 남은 프로세스가 먼저 수행되는 알고리즘이다. Preemptive와 Non-preemptive 방식 총 두 가지로 구현하였다.

Priority
- 미리 설정된 Priority값을 기준으로 프로세스의 수행 순서를 결정해주는 알고리즘이다. 이 프로그램에서는 Priority값이 낮은 프로세스가 더 우선권을 가진다. SJF 알고리즘과 마찬가지로 Preemptive와 Non-preemtive 방식 두 가지를 모두 구현하였다.

Round Robin
- 시스템에 설정된 Time Quantum을 기준으로 일정 시간마다 수행될 프로세스를 변경해주는 방식이다. Time Quantum이 만약 무한대라면, 특정 프로세스가 먼저 리소스를 점거할 경우 종료가 될 때까지 다른 프로세스들이 수행되지 않기 때문에, FCFS 방식과 동일해진다.

LIF (Longest I/O First)
- I/O 작업을 수행하는 시간이 긴 프로세스가 후반부에 스케줄링될 경우 CPU의 유휴상태가 발생할 확률이 높아진다는 점에 착안하여 가장 I/O Burst Time이 큰 프로세스부터 우선적으로 스케줄링해주는 방식이다. Preemptive / Non-preemptive 방식 둘 다 구현하였다.

LISC (Longest I/O & Shortest CPU First)
- LIF가 CPU Burst Time을 고려해주지 않는다는 단점을 보완하여 CPU Burst Time도 스케줄링에 반영한 알고리즘이다. Preemptive / Non-preemptive 방식 둘 다 구현하였다.

5. 사용법
Github에서 실행파일(CPUScheduler)을 다운받아서 콘솔에서 실행시키면 된다. 이때 인자로 두 개의 정수를 넘겨주어야 하는데, 첫 번째는 전체 프로세스의 갯수, 두 번째는 그중에서 I/O 작업을 수행할 프로세스의 갯수이다. I/O 작업을 수행할 프로세스가 전체 프로세스의 수보다 많을 경우 실행되지 않는다. 나머지 여러 속성들은 프로그램 내에서 자동으로 임의적으로 설정된다.
출력되는 내용이 비교적 긴 편이기 때문에 외부 파일에 출력내용을 저장해서 보는 것을 추천한다. 예를 들어 다음과 같이 콘솔창에 입력하면 된다.
./CPUScheduler 10 3 >> result.txt

6. Source Code
자세한 사항은 Github에서 확인할 수 있다. 전체 소스코드와 실행파일 및 보고서가 포함되어 있다.
https://github.com/arkainoh/CPU-Scheduling-Simulator