2017년 1월 16일 월요일

[ Linux ] linux 환경 C 컴파일 과정 & make 의 이해





linux 컴파일 과정 & make의 이해




Name
Author
박은탁
Current Status
1.1
Date
2014-02-27














Version
Updates
Author
Date
1.0
초안
박은탁
2014-02-26
1.1
3.3.4 확장자 규칙 추가
3.3.4 와일드 카드 매칭 기법과 대입 참조 기법 추가

2014-02-27























1.1.              컴파일이란?

흔히 말하기를 컴파일은 인간이 이해할 수 있는 형식언어로 작성된 소스 코드를 CPU가 이해할 수 있는 기계어로 번역하는 과정. 결국, 컴파일이라는 것은 결국 컴파일러를 이용해 인간이 만든 코드를 CPU가 이해할 수 있는 코드로 변경하는 과정이다.

1.1.1.            기계어

기계어를 다른  말로 머신 인스트럭션(machine instruction) 이라고 한다.
이런 인스트럭션은 01010101 같은 이진수로 이뤄진 숫자로 cpu종류마다 고유하며, cpu가 특정 행동을 취하게 하기 위한 코드를 말한다.
각각의 인스트럭션은 어셈블리 코드와 1:1 대응하므로 숫자로 이뤄진 인스트럭션을 역어셈블해 어셈블리언어로 표현할 수 있고, 어셈블리 언어를 어셈블해 인스트럭션으로 표현할 수 있다..

1.1.2.            용어

*전처리기
원시파일 내의 모든 전처리기 지시자를 컴파일 할 수 있는 C의 문장으로 전개하는 작업을 담당.
*어셈블러
어셈블러는 기본 컴퓨터 명령어들을, 컴퓨터 프로세서가 기본 연산을 수행하는데 사용할 수 있는 비트 패턴으로 변환시키는 프로그램이다.
*링크(Linking)
오브젝트 파일을 필요한 라이브러리와 연결시켜(링크) 컴퓨터가 알 수 있는 기계어로 바꾼다. 그러면 실제로 실행 가능한 파일을 생성하게 된다

2.    C 소스 Complie 과정

2.1.              gcc 컴파일러

gcc GNU Compiler Collection C컴파일러인 gcc C++, 자바등의 컴파일러들을 포함하는 컴파일러의 묶음을 의미한다.
소문자 gcc GNU C Compiler를 의미하고 대문자 GCC GNU Compiler Collection의 약자로 C컴파일러인 gcc C++, 자바 등의 컴파일러들을 포함하는 컴파일러의 묶음을 의미한다.
usr/bin/gcc는 내부적으로 전처리기인 cpp0(C++ 전처리기)또는 cc1 –E(C 전처리기)명령을 호출해 전처리 과정을 수행하고, 진짜 C컴파일러인 cc1(C언어 컴파일러)또는 cc1plus(C++ 컴파일러)를 호출해 컴파일한 후 어셈블러인 as를 호출해 목적 코드를 만들고, 마지막으로 링커를 호출하는 collect2를 호출하여 collect2가 내부적으로 링커인 id를 호출해 라이브러리와 링크해 실행 파일로 만들어낸다.
gcc는 실제 컴파일 과정을 담당하지 않고, 전처리기와 C컴파일러, 어셈블러, 링커를 각각 호출해 주는 역할만 담당한다. 이렇게 각각의 컴파일 과정에 필요한 명령을 순차적으로 호출해 주는 것을 컴파일러 드라이버라고 부른다.
Gcc 컴파일러 드라이버 내에 컴파일러 들
cc1
C 컴파일러, -E 옵션 을 붙이면 C 전처리기로 동작
Cc1plus
C++ 컴파일러, -E 옵션 을 붙이면 C++ 전처리기로 동작
Collect2
링커(내부에서 링커인 id를 호출해 링크함)


2.2.              gcc compile 과정


1. gcc
cc1 –E를 호출해 전처리 과정을 거쳐 like.c 파일을 like.i 파일로 만든다. 
2. like.i 파일은 C 컴파일러인 cc1에 의해 어셈블리 코드인 like.s로 컴파일된다.
3. like.s as 어셈블러에 의해 어셈블 과정을 거쳐 like.o 오브젝트 파일로 만들어진다.
4. like.o 파일은 다시 collec2가 링커인 id를 호출한 후 표준 C라이브러리와 링크함.
5. 최종적으로 실행파일 like 가 만들어진다.

2.2.1.             gcc compile test - like.c 파일 컴파일 수행

like.c 소스 파일 내용
#include <stdio.h>
int main()
{
        printf("I like you!\n");
        return 0;
}

[euntark@devweb ~]$ gcc -v -save-temps -o like like.c
-v : 컴파일 과정을 화면에 출력
 -save-temps : 컴파일 과정에서 발생되는 중간 파일을 지우지 않고 저장
 -o : 컴파일된 파일명을 like로 하라는 의미
Using built-in specs.
Target: i386-redhat-linux
Configured with: ../configure --prefix=/usr --mandir=/usr/share/man --infodir=/usr/share/info --enable-shared --enable-threads=posix --enable-checking=release --with-system-zlib --enable-__cxa_atexit --disable-libunwind-exceptions --enable-libgcj-multifile --enable-languages=c,c++,objc,obj-c++,java,fortran,ada --enable-java-awt=gtk --disable-dssi --disable-plugin --with-java-home=/usr/lib/jvm/java-1.4.2-gcj-1.4.2.0/jre --with-cpu=generic --host=i386-redhat-linux
Thread model: posix
gcc version 4.1.2 20080704 (Red Hat 4.1.2-50)
 /usr/libexec/gcc/i386-redhat-linux/4.1.2/cc1 -E -quiet -v like.c -mtune=generic -fpch-preprocess -o like.i
ignoring nonexistent directory "/usr/lib/gcc/i386-redhat-linux/4.1.2/../../../../i386-redhat-linux/include"
#include "..." search starts here:
#include <...> search starts here:
 /usr/local/include
 /usr/lib/gcc/i386-redhat-linux/4.1.2/include
 /usr/include
End of search list.
 /usr/libexec/gcc/i386-redhat-linux/4.1.2/cc1 -fpreprocessed like.i -quiet -dumpbase like.c -mtune=generic -auxbase like -version -o like.s
GNU C version 4.1.2 20080704 (Red Hat 4.1.2-50) (i386-redhat-linux)
        compiled by GNU C version 4.1.2 20080704 (Red Hat 4.1.2-50).
GGC heuristics: --param ggc-min-expand=100 --param ggc-min-heapsize=131072
Compiler executable checksum: d8d95095eb3c93dae4bed2137d559f95
 as -V -Qy -o like.o like.s
GNU assembler version 2.17.50.0.6-14.el5 (i386-redhat-linux) using BFD version 2.17.50.0.6-14.el5 20061020
 /usr/libexec/gcc/i386-redhat-linux/4.1.2/collect2 --eh-frame-hdr -m elf_i386 --hash-style=gnu -dynamic-linker /lib/ld-linux.so.2 -o like /usr/lib/gcc/i386-redhat-linux/4.1.2/../../../crt1.o /usr/lib/gcc/i386-redhat-linux/4.1.2/../../../crti.o /usr/lib/gcc/i386-redhat-linux/4.1.2/crtbegin.o -L/usr/lib/gcc/i386-redhat-linux/4.1.2 -L/usr/lib/gcc/i386-redhat-linux/4.1.2 -L/usr/lib/gcc/i386-redhat-linux/4.1.2/../../.. like.o -lgcc --as-needed -lgcc_s --no-as-needed -lc -lgcc --as-needed -lgcc_s --no-as-needed /usr/lib/gcc/i386-redhat-linux/4.1.2/crtend.o /usr/lib/gcc/i386-redhat-linux/4.1.2/../../../crtn.o

생성 확인
ASP50  asp40         hello_dir     like    like.i  like.s    ppurio50  vhosts.conf
asp20  hello_cp.txt  hello_mv.txt  like.c  like.o  ppurio30  test1


3.     Make

3.1.              Make의 이해

make는 파일 관리 유틸리티다. make는 각 파일 간의 종속 관계를 파악해 기술 파일(make file)에 기술된 대로 컴파일 명령이나 shell명령을 순차적으로 내린다. make는 각 파일에 대한 반복적 명령을 자동화시켜 개발자의 수고를 덜고, 시간을 절약 할 수 있다.
make의 동작 방식은 매우 단순하다. makefile 기술 파일을 작성하면 make가 기술 파일에 적힌 대로 명령을 수행한다. 결국 기술 파일을 작성하는 법과 make에 대한 몇 가지 특징만 이해하면 make를 프로젝트에 도입할 수 있다.

3.2.              예제-Make 기본 동작 이해

3.2.1.            예제 소스

예제 소스 파일 내용
diary.h
#include<stdio.h>
int main();
int calendar();
memo.c
#include "diary.h"
int memo()
{
        printf("function memo.\n");
        return 0;
}
calendar.c
#include "diary.h"
int calendar()
{
        printf("function calendar.\n");
        return 0;
}
main.c
#include "diary.h"
int main()
{
        memo();
        calendar();
        return 0;
}




예제 소스 파일 구조도

3.2.2.            예제-make 파일 생성

Makefile의 내용
all : diary


TAB
diary : memo.o calendar.o main.o
        gcc -W -Wall -o diary memo.o calendar.o main.o
memo.o : memo.c
        gcc -W -Wall -c -o memo.o memo.c
calendar.o : calendar.c
        gcc -W -Wall -c -o calendar.o calendar.c
main.o : main.c
        gcc -W -Wall -c -o main.o main.c

clean :
        rm -rf *.o diary
-o : 출력 파일명을 지정할 때 사용합니다.
-c : 링킹 과정을 진행 하지 않고 .o 파일인 오브젝트 파일까지만 생성 하게 됩니다.
-Wall : 모든 모호한 코딩에 대해서 경고를 보내는 옵션
-W : 합법적이지만 모호한 코딩에 대해서 경고를 보내는 옵션
-W -Wall : 아주 사소한 모호성에 대해서도 경고

3.2.3.            make명령으로 컴파일 수행

Make 명령을 내리면 각 오브젝트에 대한 컴파일 명령을 수행한 후 최종적으로 diary 실행 파일을 생성한다.
[euntark@devweb maketest]$ make
gcc -W -Wall -c -o memo.o memo.c
gcc -W -Wall -c -o calendar.o calendar.c
gcc -W -Wall -c -o main.o main.c
gcc -W -Wall -o diary memo.o calendar.o main.o


3.2.4.            생성된 파일 목록

생성한  파일 목록
calendar.c  diary.h  main.c  makefile  memo.c

3.2.5.            컴파일 후 최종 생성된 파일 목록

컴파일 후 생성된 파일 목록
calendar.c  calendar.o  diary  diary.h  main.c  main.o  makefile  memo.c  memo.o

3.2.1.              예제-make기본동작 수행 순서

make의 기본동작순서는
1)make 명령을 내리면 make는 먼저 현재 디렉토리 내에서 기술 파일을 찾는다. 기술 파일은 makefile이다.
2)makefile 내에서 제일 처음 오는 타겟을 찾는다.(위의 예제 all 타겟)
3)해당 타겟을 만들기 위한 종속 항목을 보고(예제 diary)파일이 현재 디렉토리내에 없다는 것을 확인하다.
4)diary를 생성하기 위한 룰을 찾기 위해 diary타겟의 종속 항목을 접하고 첫 종속항목(memo.o)이 아직 만들어져 있지 안았음을 확인하다.
5)memo.o를 생성하기 위한 룰을 찾기 위해 memo.o 항목을 읽고 종속 항목 memo.c 가 현재 디렉토리 내에 있는 것을 확인하면 make memo.o를 만들기 위해 아래 명령으로 memo.o를 컴파일 해 만들어낸다. 만약 memo.o가 미리 만들어져 있다면 make는 다시 만들 필요가 있는지 검토한다. 만들어져 있는 memo.o보다 memo.c의 수정시간이 최근이라면 memo.o가 만들어진 후 memo가 수정되었기 때문에 다시 만들 필요가 없다. 다시 만들어야 할 필요가 있으면 make는 아래 명령을 수행하고 그렇지 않으면 명령을 건너 뛰고 다음 과정을 수행한다.
6)다시 diary 타겟의 종속항목으로가 memo.o는 만들어 졌지만, calendar.o는 아직 생성 되지 않음을 확인하다.
7)calendar.o main.o 5) ~6) 반복
8)이제는 diary를 생성하기 위한 종속 항목임 3개의 파일이 다 만들어진 것을 확인하고 diary를 생성하기 위한 명령을 수행해 dirary를 생성한다.
9)all 타겟으로 가서 생성하기 위한 diary가 만들어진 것을 확인한 후 현재 all 타켓을 생성하기 위한 특별한 명령이 없으므로 make all타겟이 생성 되었다고 간주하고 종료.

3.3.              기술 파일(make file) 작성

3.3.1.            기술 파일의 기본 구조

매크로 정의
CC=gcc
1
Target1 :dependency1 dependeny2 …
명령1
[ TAB ] command1
[ TAB ] command2
…..
N
TargetN :dependencyN dependenyN+1 …
명령2
[ TAB ] commandN
[ TAB ] commandN+1
….

3.3.2.            기술 파일의 구문 작성 기본 규칙

1. 명령의 시작은 반드시 TAB으로 시작되어야 한다.
2. 비어 있는 행은 무시된다.
3. ‘#’을 만나면 개행 문자를 만날 때까지 무시한다.
4. 기술 행이 길어지면 백슬레쉬를 사용해서 이을 수 있다.
5. ‘;’는 명령 라인을 나눌 때 사용 한다.
6. 종속 항목이 없는 타겟도 사용 가능하다.
7. 명령 부분에는 어떤 명령이 와도 상관없다.

3.3.3.            매크로 사용

기술 파일 내에 매크로는 C와 마찬가지로 사용자 정의 변수에 특정한 문자열을 정의하고 표현하는 것을 의미한다.
CC=gcc
           CC매크로를 정의했다면 CC는 기술 파일 내부에서 $(CC)로 표기함으로 써 gcc로 치환될 수 있다.

3.3.3.1.         매크로 기본 규칙

1.     매크로의 정의는 ‘=’를 포함하는 하나의 문장이다.
‘=’의 좌측에는 매크로 이름이 오고 우측에는 정의 문자열이 온다.
2.     ‘#’은 주석문의 시작이다.
3.     여러 행을 사용할 때는 백슬레쉬를 사용한다.
4.     매크로를 참조할 때는 괄호나 중괄호를 둘러싸고 앞에 ’$’를 붙인다.
5.     정의 되지 않는 매크로를 참조할 때는 null 문자열로 치환된다.
6.     중복된 정의는 최후에 정의된 값을 사용한다.
7.     매크로 정의 시 이전에 정의된 매크로를 참조해 정의할 수 있다.
8.     여러 대입 기법을 사용할 수 있다.
NAME1 =string #재귀적 확장 매크로
NAME2 :=string #단순 확장 매크로
NAME2 +=string #기존의 매크로에 공백을 두고 현재의 문자열을 덧붙인다.
NAME3 ?=string #현재 정의하는 매크로가 정의되어 있지 않았다면 치환 하고 이전에 매크로가 정의 되어 있으면 이 치환은 무시한다.

3.3.3.2.         매크로 사용시 주의 사항.

1. 구분을 위해 문자열에 따옴표를 넣으면 따옴표 또한 문자열의 일부로 인식한다.
2. 매크로의 이름에는 ‘:’ , ’=’ , ‘#’ 이 들어 가서는 안되고 TAB으로 시작해서도 안 된다.  (TAB으로 시작하는 라인은 명령라인으로 인식하기 때문에)
              3. 매크로는 반드시 치환될 위치보다 먼저 정의 되어야 한다

3.3.3.3.         매크로 규칙 적용 makefile

매크로 규칙에 유통적으로 직관적이게 고친 예제 makefile
CC = gcc
CFLAGS = -W –Wall
TARGET = diary
all : $(TARGET)

TAB
 
$(TARGET) : memo.o calendar.o main.o
        $(CC) $(CFLAGS) -o $(TARGET) memo.o calendar.o main.o
memo.o : memo.c
        $(CC) $(CFLAGS) -c -o memo.o memo.c
calendar.o : calendar.c
        $(CC) $(CFLAGS) -c -o calendar.o calendar.c
main.o : main.c
        $(CC) $(CFLAGS) -c -o main.o main.c

clean :
        rm -rf *.o diary


3.3.3.4.         내부적으로 정의 되어 있는 매크로

make –p 명령을 쉘에서 내리면 make 내부에 정의된 매크로 리스트들이 나열된다.
매크로 이름
설명
기본값
AR
아카이브 관리 프로그램
ar
AS
어셈블러
as
CC
C 컴파일러
cc
CXX
C++컴파일러
g++
CO
RCS checkout 프로그램
co
CPP
C 전처리기
cc E
FC
포트란 컴파일러
f77
GET
SCCS 관련 프로그램
get
LD
링크
ld
LEX
스캐너 코드 생성기
lex
PC
파스칼 컴파일러
pc
YACC
파서 코드 생성기
yacc
MAKEINFO
Texinfo 파일을 Info 파일로 변환
makeinfo
TEX
TeX 문서로부터 TeX DVI 생성
tex
TEXI2DVI
Texinfo 파일을 dvi 파일로 변환 프로그램
texi2dvi
WEAVE
Web TeX로 변환
weave
CWEAVE
C Web TeX로 변환
cweave
TANGLE
Web을 파스칼로 변환
tangle
CTANGLE
C Web C로 변환
ctangle
RM
파일을 지우는 명령
rm f
ARFLAGS
ar 플래그
rv
ASFLAGS
어셈블러 플래그

CFLAGS
C 컴파일러 플래그

CXXFLAGS
C++ 컴파일러 플래그

COFLAGS
RCS co 플래그

CPPFLAGS
C 전처리기 플래그

FFLAGS
포트란 컴파일러 플래그

GFLAGS
SCCS get 플래그

LDFLAGS
링크 플래그

LFLAGS
Lex 플래그

PFLAGS
파스칼 컴파일러 플래그

YFLAGS
Yacc플래그

3.3.3.5.         자동 매크로

$?
-현재의 타겟보다 최근에 변경된 종속 항목 리스트
 (확장자 규칙에서는 사용 불가)
$^
- 현재 타겟의 종속 항목 리스트
 (확장자 규칙에서는 사용 불가)
$@
-현재 타겟의 이름
$<
-현재 타겟보다 최근에 변경된 종속 항목리스트
 (확장자 규칙에서만 사용 가능)
$*
-현재 타겟보다 최근에 변경된 현재 종속 항목의 이름
 (확장자제외)
 (확장자 규칙에서만 사용 가능)
$%
-현재의 타깃이 라이브러리 모듈일 때 .o 파일에 대응되는 이름

3.3.3.6.         자동매크로를 적용한 makefile.


자동 매크로를 이용한 makefile

CC = gcc
CFLAGS = -W -Wall
TARGET = diary

all : $(TARGET)

$(TARGET) : memo.o calendar.o main.o
        $(CC) $(CFLAGS) -o $@ $^
memo.o : memo.c
        $(CC) $(CFLAGS) -c -o $@ $^
calendar.o : calendar.c
        $(CC) $(CFLAGS) -c -o $@ $^
main.o : main.c
        $(CC) $(CFLAGS) -c -o $@ $^

clean :
        rm -rf *.o diary

3.3.4.            확장자 규칙

컴파일러는 확장자를 보고 어떤 프로그래밍 소스파일인지 인식한다.

3.3.4.1.         내부 정의 확장자 규칙

%.o: %.c
 #  실행할 명령어 (내장) :
                 $(COMPILE.c) $(OUTPUT_OPTION) $<

 %.o: %.f
 #  실행할 명령어 (내장) :
                 $(COMPILE.f) $(OUTPUT_OPTION) $<

 %.o: %.S
 #  실행할 명령어 (내장) :
                 $(COMPILE.S) -o $@ $<

- %는 일치하는 확장자를 제외한 파일명을 의미한다.
- gcc
컴파일러는 *.c 파일이 있을 때 확장자 .c를 보고 그 파일이 C 프로그래밍 소스 파일인 것을 인식한다.

- COMPILE.xx : 컴파일러 및 컴파일 옵션을 지정
- OUTPUT_OPTION : -o $< 로 지정
*.c 파일은 C컴파일러를 이용해 *.o 파일로 만들 수 있고, *.f 파일은 포트란 컴파일러를 이용해 *.o 파일을 만들 수 있다.
이런 확장자가 가지는 규칙에 기초해 make는 사용자가 내리는 명령을 알아서 해석해 컴파일 과정을 자동화할 수 있다.



3.3.4.2.         내부 정의 확장자 규칙 적용 makefile & 설명

내부 정의 확장자 규칙 이용한 makefile
OBJECTS = memo.o calendar.o main.o

all : diary

diary : $(OBJECTS)
        $(CC)  -o $@ $^
clean :
                rm -rf *.o diary

내부 정의 확장자 규칙 이용한 makefile 컴파일 화면
[euntark@devweb maketest]$ make
cc    -c -o memo.o memo.c
cc    -c -o calendar.o calendar.c
cc    -c -o main.o main.c
        cc  -o diary memo.o calendar.o main.o

위와 같은 기술 파일을 make는 다음 과같이 해석해 명령을 수행한다.
1.     기술 파일에서 diary를 생성하기 위해 make는 종속 항목을 살펴보고 종속 항목을 각각 타겟으로 설정한다.
2.     diary memo.o에 의존하고 memo.o는 만들어지지 않았으며 memo.o를 생성하기 위한 룰도 기술 파일에는 정의되어 있지 않다.
3.     make는 확장자가 .o인 내부 확장자 규칙을 이용해 다음과 같은 기준으로 현재 디렉토리에서 memo.o를 생성할 파일을 찾는다.
-확장자를 제외하고 memo.o와 같은 이름이어야 한다.
4.     내부 정의 확장자 규칙의 기술된 명령을 수행하여 컴파일을 수행한다.

3.3.4.2.1.    make 유틸리티의 디폴트 처리 방식
- 타겟과 종속성은 있지만 함께 기술했던 명령어가 없이도 make 유틸리티가 스스로 알고 있다.
- make 유틸리티의 디폴트 처리 방식 : ${CC} ${CFLAGS} -c -o $@ $*.c
- make 유틸리티는 종속성에 의해 .o를 확장자로 하는 타겟을 만날 때마다 이 명령어에 대입한다.

3.3.5.            와일드 카드 매칭 기법과 대입 참조 기법

와일드 카드 매칭 기법과 대입 참조 기법을 적용한 makefile
SRCS =$(wildcard *.c)  # memo.c calendar.c main.c
OBJECTS=$(SRCS: .c=.o)  # memo.c calendar.c main.c


all : diary

diary : $(OBJECTS)
        $(CC)  -o $@ $^
clean :
                rm -rf *.o diary

SRCS 매크로에서 $(wildcard *.c)는 현재 디렉토리에서 *.c 와 파일명이 일치하는 파일을 찾아 공백을 구분 문자로 SRCS 매크로에 정의한다.
결국 SRCS에는 현재 디렉토리에 있는 memo.c  calendar.c  main.c로 정의된다.
정의된 SRCS는 다시 OBJECTS 매크로에 정의 되는데, $(SRCS: .c=.o)와 같은 대입 참조 기법을 통해 확장자가 .c .o로 바뀐다. 그래서 memo.c  calendar.c  main.c로 정의된다.
위 기술 파일에서 SRCS=*.c 라고 하지 않은 이유는 매크로를 정의할 때는 와일드 카드 확장이 되지 않기 때문이다.
*.c 식의 와일드카드 확장은 타겟 정의절과 명령절에서만 일어난다.
그래서 SRCS 매크로는 memo.c  calendar.c  main.c가 정의되는 게 아니라 *.c가 정의 되기 때문에 OBJECTS 역시 *.o로 정의된다.
$(wildcard *.c)와 같이 사용하는 것을 make로 함수의 사용이라고 한다.
또 다른 make함수 patsubst를 사용하여 한 라인 으로 정리 할 수도 있다.
OBJECTS=$(patsubst %.c %.o $(wildcard *.c))
세 번째 인자로 오는 $(wildcard)의 결과를 공백으로 구분된 문자열들 각각에 대해 첫 번째 인자인 %.c와 매칭되는 것을 %.o로 바꾼다.

3.3.5.1.         참고 echo $?

셸에서 바로 직전 명령 수행 후 리턴 값을 보려면 echo $? 명령으로 확인 할 수 있다. 0이면 정상적으로 수행 O,  0이 아니면 정상적으로 수행 X


[linux] Crontab

Crontab
Crontab ?
Ubuntu, linux System에서 특정 명령을 시간마다 실행시키는 기능의 프로그램입니다.

권한
root 또는 다른 사용자에 속하는 crontab 파일을 만들거나 편집하는 경우 수퍼유저 또는 동등한 역할의 사용자여야 합니다. 자신의 crontab 파일을 편집하기 위해 수퍼유저일 필요는 없습니다.

명령어

파일 생성 기존 파일을 편집

$ crontab -e [username]

파일 변경 사항을 확인
# crontab -l [username]

범위
Crontab의 스케쥴은 분 단위 까지 예약이 가능합니다.
MIN HOUR DOM MON DOW   CMD
                  실행명령


    MIN         0-59
    HOUR
       0-23
    DOM 
       0-31
    MON 
       1-12
    DOW 
       0-7 (0 또는 7=일요일, 1=, 2=,...)


- 한 줄당 하나의 명령 (두 줄로 나눠서 표시할 수 없음)
- #
으로 시작하는 줄은 실행하지 않는다 (주석)

    
)
매일 12시에 backup 이라는 명령(cmd)을 실행
00 12 * * * backup

매월  1일과 15 04시에 backup 이라는 명령을 실행
00 04 1,15 * * backup
=> ‘ ,으로 1개 이상의 시간을 예약 할 수 있다.
매일 01시에서부터 16시 까지 매 시간 마다 backup 이라는 명령을 실행
00 01-16 * * * backup
=> ‘ -으로 기간을 설정 할 수 있다.
매일 01시에서부터 16시 까지 3 시간 간격으로  backup 이라는 명령을 실행
00 01-16/3 * * * backup
=> ‘ /으로 시간 간격을 설정 할 수 있다.
예약어
자주 사용사는 것들은 아래와 같이 미리 정의된 닉네임을 사용할 수 있다.
@reboot  : Run once, at startup.
@yearly  : Run once a year, ie. "0 0 1 1 *".
@annually  : Run once a year, ie. "0 0 1 1 *".
@monthly : Run once a month, ie. "0 0 1 * *".
@weekly  : Run once a week, ie. "0 0 * * 0".
@daily   : Run once a day, ie. "0 0 * * *".
@hourly  : Run once an hour, ie. "0 * * * *".

실행 내용 메일 받기
Crontab 수정시 위에 MAILTO를 선언하면 실행 내용을 메일로 받을 수 있다.
# dsmoon@daum.net 으로 메일 받기
MAILTO="dsmoon@daum.net"

참고 http://inforgather.tistory.com/242)

참고)http://docs.oracle.com/cd/E24846_01/html/E23088/sysrescron-24589.html

[형상관리] SVN이란

* SVN이란?

 서브버전(Subversion)은 자유 소프트웨어 버전 관리 시스템이다. 명령행 인터페이스에서 사용하는 명령어를 따서 “SVN”이라고 줄여서 부릅니다.

SVN을 사용하여, 소스 파일과 문서의 이력을 기록할 수 있습니다.

이것은 시간에 걸쳐 파일과 디렉토리를 관리 합니다.

이와 같은 파일의 트리는 저장소(repository)에 놓여 집니다. 저장소는 보통의 파일 서버와 비슷하지만, 이제껏 만들어진 파일과 디렉토리의 모든 변경을 기억하고 있습니다.





- 기능

·  더 이상 나누어 질 수 없는 개별적으로 쓰기를 지원하므로, 쓰기 도중 중단으로 인한 저장소 내의 불일치나 손상을 피할 수 있다.

· 이름을 바꾸거나, 복사하거나, 파일을 지워도 계정 기록을 유지한다.

· 시스템이 디렉토리, 파일 이름 바꾸기, 파일 메타데이터에 대해서도 판본 호수를 지정 관리한다. 사용자는 디렉터리 전체를 빠르게 옮기거나 복사하면서도 전체의 개정 이력을 보유할 수 있다.

· 심볼릭 링크도 판본 호수를 지정.(*심볼릭 링크: #>in –s ..test/test testtest =>현재 위치에 testtest라는 폴더를 생성하고 이폴에 test/test라는 폴더를 링크 걸어줌)

·  이진 파일의 경우 한번 저장한 후 변경될 경우 차이점만 저장하기 때문에 저장소를 효율적으로 사용할 수 있다.

· 소스 저장소의 크기에 관계 없이 일정한 시간 안에 가지 치기(branching)나 태그 넣기(tagging)를 할 수 있다.

·  태생적으로 클라이언트-서버, 계층 라이브러리 설계를 채택.

·  클라이언트/서버 통신규약이 버전간 차이를 양뱡향으로 보냄.

·   소스 저장소로의 접근이 최적화되어 있으므로, 소스 저장고에서 필요 없는 네트워크 트래픽을 줄일 수 있다.


- 기본 용어
  • Repository : 프로젝트 파일 및 변경 정보가 저장되는 장소
  • Import : 빈 Repository에 맨 처음 파일들을 채우는 것
  • Checkout(co) : Repository에서 프로젝트 관련 파일들을 받아 오는 것
  • Commit(ci) : Checkout한 파일의 수정사항을 갱신,Revision 1이 증가
  • Revision : commit 할 때 마다 카운트 되는 번호
  • Update (up) : checkout 한 파일들을 최신의 것으로 갱신, 소스 수정이나 commit 하기 전에 한번씩 해주는 것이 좋다.
  • Export : 버전 관리 파일들을 뺀 순수 파일만 빼내는 것.
  • Tag : 개념적으로 특정 시점에서 프로젝트의 스냅샷을 찍어두는 것이다. 즉 Revision번호 그 자체에 해당한다.
  • Brach : 브런치 생성은 복사와 같은 개념이다.
  • Truck : 프로젝트에서 가장 중심이 되는 디렉토리로 소스와 파일들이 포함된다.
  • Diff : 수정된 파일과 수정 이전 파일을 차이정보를 비교하여 것.

- 목적

  •  파일과 디렉토리 집합에 대한 변경을 추적하고 기록하기 위함.
  • 이력 관리 (누가/ 무엇을/ 무엇을 위해/ 언제/ )


- 버전 관리 시스템의 기본 과제

  복사->편집->병합



시나리오)
1. 두 명의 사용자가 동일한 파일을 읽습니다.
2. 두 사람 모두 각자의 사본을 편집을 시작합니다.
3. Harry가 지신의 버전을 먼저 게시합니다.
4. Sally가 실수로 Harry의 버전을 덮어씁니다.
SO, Harry가 수정한 내용은 없어 집니다.(기본 과제)


Trunk., branch, tags 관계


Trunk
  - 단어 자체의 뜻은 본체, 본문 등입니다.
  - 프로젝트에서 가장 중심이 되는 디렉토리입니다.
  - 모든 프로그램의 개발 작업은 trunk 디렉토리에서 이루어  집니다.
  - trunk 디렉토리 바로 아래에는 소스들의 파일과 디렉토리가 들어가게 됩니다.

Branch
  - trunk에서 뻗어져 나온 나무가지를 뜻합니다.
  - 프로그램을 개발하다 보면 trunk 디렉토리에서 또 다른 작은 분류로 빼서 따로 개발해야 할 경우가 있습니다. 프로젝트안의 작은 프로젝트라고 생각하면 됩니다.
- branches 디렉토리 안에 또 다른 디렉토리를 두어 그 안에서 개발하게 됩니다.

Merge
  - Trunk에서 분기된 Branch를 다시 Trunk로 합쳐는 작업

Tag
  - tag는 꼬리표입니다.
  - 이 디렉토리는 프로그램을 개발하면서 정기적으로 릴리즈 할 때, 0.1 / 0.2 / 1.0 등 이런식의 버전 별로 소스 코드를 따로 저장하는 공간입니다.
- 버전별로 태그를 붙여서 tag 디렉토리 안에 보관한다고 생각하면 됩니다.

 - SVN 명령어) - svn help [명령어]

add : 파일과 디렉토리를 버전관리 대상에 넣습니다. 저장소에 추가하도록 스케줄링 되며, 다음 commit할 때, 추가됩니다.

사용법 : add [PATH]

blame (praise, annotate, ann) : 지정한 파일이나 URL의 내용의 수정내역을 각 라인별로 리비전과 작성자를 보여줍니다.

사용법: blame TARGET[@REV]...

cat : 지정한 파일이나 URL의 내용을 출력합니다.
사용법: cat TARGET[@REV]... 

REV가 지정되면, 지정된 REV에서부터 찾아 출력합니다.
  
checkout (co) : 작업사본을 저장소로부터 꺼냅니다.

사용법: checkout URL[@REV]... [PATH]

REV가 지정되면, 지정된 REV에서부터 찾아 체크아웃합니다.
PATH가 생략되면, URL의 맨 마지막 디렉토리명이 꺼내어 저장될 디렉토리 이름으로 사용됩니다. 
   
cleanup : 제귀적으로 작업 사본을 순회하면서 복사, 제거시 실패한 잠금파일을 삭제하며,
중단된 명령을 재개합니다.

사용법: cleanup [PATH...] 

commit (ci) : 변경된 내용을 작업 사본에서 저장소로 전송합니다.

사용법: commit [PATH...]

로그 메시지는 반드시 넘겨져야 하며, 빈 메시지를 넘길 수도 있습니다.
만약 --message 나 --file 옵션을 사용하지 않았다면, 편집기가 수행됩니다.
잠긴 파일이 있거나, 잠긴 파일이 들어 있는 디렉토리는 성공적으로 커밋이 되면 잠금이 해제가 됩니다.

copy (cp) : 작업 사본 혹은 저장소의 내용을 이전 로그메시지와 함께 복사합니다. 

사용법: copy SRC[@REV]... DST

여러개를 복사할 때, 이들은 모두 DST의 하위에 추가되며, 이때, DST는 반드시 디렉토리어야 합니다.

SRC와 DST는 작업 사본(WC) 혹은 저장소 URL이 될 수 있습니다:
 WC  -> WC:   바로 복사하고 저장소에 이전 로그와 함께 추가하도록 스케쥴
 WC  -> URL:  작업사본을 URL에 복사하고 바로 커밋함
 URL -> WC:   URL로부터 체크아웃해서 현 작업 사본에 추가하도록 스케쥴
 URL -> URL:  서버상에서 바로 복사함; 브랜치,태그를 만들 때 사용됨
 모든 SRC들은 같은 종류의 것이어야 합니다.

경고: Subversion 이전 버전과의 호환성을 위해서, 작업 사본간의 복사
(WC -> WC)는 저장소를 경유하지 않고 수행됩니다. 이런 이유로 원본에서
사본으로 복사할 때, 병합되는 정보는 기본 동작으로는 전달되지 않습니다

사용법: copy SRC[@REV]... DST

delete (del, remove, rm) : 파일과 디렉토리를 버전 관리 대상에서 제거합니다.

사용법: 1. delete PATH...
        2. delete URL...

★diff (di) : 두 리비전 혹은 두 경로상의 차이점을 출력합니다.

Export : 로컬 시스템에서 정리된 디렉토리 트리 내보내기

로컬 시스템상의 버전 없는 복사본, 즉 정리된 트리 디렉토리를 프로젝트 저장소나 로컬 작업 복사본 내부로부터 추출할 수 있습니다. 이전 개정판의 정리된 디렉토리를 저장소로부터 가져오려면 다음과 같이 입력합니다.

help(?, h) : 본 프로그램과 그 하위 명령들에 대한 사용법을 보여줍니다.

Import : 버전관리 대상이 아닌 파일과 디렉토리를 추가합니다.

import를 사용하여 버전 없는 파일이나 트리를 프로젝트 저장소로 반복 커밋할 수 있습니다. 필요에 따라 저장소에 상위 디렉토리가 만들어집니다. 다음 명령은 PATH에서 URL로 복사본을 반복 커밋합니다. PATH가 생략되면 "."로 가정합니다.

사용법 import [PATH] URL

★Info : 사본이나 저장소의 파일, 디렉토리의 정보를 출력합니다.

사용법: info [TARGET[@REV]...]

list (ls) : 저장소에 있는 항목들을 나열해줍니다.
사용법: list [TARGET[@REV]...]

Lock : 작업 사본이나 저장소의 URL을 잠굽니다. 다른 사용자가 변경하여 커밋할 수 없습니다.

사용법: lock TARGET..

log : 커밋 로그 메시지

'작업 복사본' 또는 저장소에 있는 파일/디렉토리의 개별 파일/디렉토리 이력을 조회하면서 개정 정보를 추적할 있습니다


merge : 변경사항 병합하기
svn merge 명령을 실행하면 서브버전 기능을 통해 저장소에서 가장 최신 버전의 파일을 작업 복사본으로 병합할 있습니다.

mergeinfo : Display merge-related information.

SOURCE[@REV] [TARGET[@REV]]

★mkdir : 디렉토리 만들기

디렉토리를 만들어 버전관리 대상으로 둡니다.

사용법: 1. mkdir PATH...
        2. mkdir URL...

디렉토리를 만들어 버전관리 대상으로 만듭니다.

move (mv, rename, ren) : 작업 사본내 혹은 저장소 안의 파일이나 디렉토리를 이동하거나, 이름을 바꿉니다.
1. PATH로 지정된 디렉토리들을 작업 디렉토리안에 만들고,다음 커밋할 때 추가되도록 스케쥴링 합니다.
2. 각 디렉토리들을 지정한 URL에 직접 커밋되는 형식으로 생성합니다.
  

  두 경우 생성될 디렉토리 상위의 디렉토리들은 존재해야만 합니다.
  --parents 옵션을 주면, 중간 디렉토리를 생성합니다

사용법: move SRC DST

propdel (pdel, pd) : 속성을 파일, 디렉토리, 리비전으로부터 제거합니다.
propedit (pedit, pe) : 속성을 외부 편집기를 통해 수정합니다.
propget (pget, pg) : 파일, 디렉토리 또는 리비전의 속성값을 출력합니다.
proplist (plist, pl) : 파일, 디렉토리, 리비전의 모든 속성을 출력합니다.
propset (pset, ps) : 파일, 디렉토리, 리비전의 모든 속성을 설정합니다.

resolve : 작업사본의 파일이나 디렉토리에 발생한 충돌을 해결합니다
사용법: resolve --accept=ARG [PATH...]

Resolved : 작업사본내의 파일이나 디렉토리의 충돌 상황을 제거합니다.
로컬 작업 복사본을 갱신하는 충돌이 발생할 있습니다. 경우 충돌을 해결해야 합니다. 충돌 해결  svn resolved PATH...라고 입력하여 충돌이 '해결'되었음을 작업 복사본에 알립니다.

사용법: resolved PATH...

revert : 작업 사본을 받아 왔던 최초 상태로 되돌립니다. (작업한 내용을 모두 되돌립니다.)
사용법: revert PATH...

status (stat, st) : 파일/디렉토리의 상태 가져오기 
    
switch (sw) : 작업 복사본 전환하기
svn switch URL [PATH]를 사용하면 새 URL을 미러링하도록 작업 복사본을 갱신할 수 있습니다. 작업 복사본 또는 그 일부를 새 브랜치로 이동할 수 있습니다. 이 하위 명령을 브랜치 바로가기로 사용할 수 있습니다.


unlock : 작업사본이나 저장소 URL의 잠금을 해제합니다.
사용법: unlock TARGET...

update (up) : 작업 복사본 갱신하기
버전 관리에서는 다음 명령을 사용하여 로컬 작업 복사본을 프로젝트 저장소로 매일 갱신하는 것이 좋습니다.

2017년 1월 5일 목요일

[알고리즘] 순환 ( Recursion ) 예제

package com.algo.recursion;

public class MainClass {


/**
* Recursion 으로 문자열 길이 구하기
* @param String
* @return int
*/
public static int  length(String str) {
if(str.equals(""))
return 0;
else
return 1 + length(str.substring(1));

}


/**
* Recursion 으로 문자열 출력하기
* @param String
* @return void
*/
public static void printChars(String str ){

if(str.length() == 0 )
return;

else{
System.out.print(str.charAt(0));
printChars(str.substring(1));

}

}

/**
* Recursion 으로 문자열 거꾸로 출력하기
* @param String
* @return void
*/
public static void printCharsReverse(String str) {

if(str.length() == 0 )
return ;
else {
printCharsReverse(str.substring(1));
System.out.print(str.charAt(0));

}
}

/**
* Recursion 으로  입력된 정수의 이진수 출력하기
* @param int
* @return void
*/
public static void printInBinary( int n ){

if(n<2)
System.out.println(n);
else {
printInBinary(n/2);
System.out.println(n%2);

}

}

public static int sum( int n , int[] data ) {

if (n <= 0 )
return 0;
else
return sum( n-1 ,data) + data[n-1];

}



public static void main(String[] args) {
// TODO Auto-generated method stub

String testStr = "ABCDE";
String testStr1 = "E";
System.out.println( MainClass.length(testStr) );
MainClass.printChars(testStr);
System.out.println();
MainClass.printCharsReverse(testStr);

System.out.println(testStr1.substring(1));


int[] intArray = {1,2,3,4};
System.out.println( MainClass.sum( 4, intArray) );


}




}

2016년 11월 6일 일요일

[AWS] AWS에서 리눅스 서버 만들기

http://sarc.io/index.php/aws/517-aws-ec2-10-linux


*Secure CRT에서 발급 받은 인증서(*.pem)로 ssh 접속 하기
http://ryusstory.tistory.com/entry/SecureCRT%EB%A5%BC-%EC%9D%B4%EC%9A%A9%ED%95%B4%EC%84%9C-AWS-%EB%B3%B4%EC%95%88%ED%82%A4%EB%A1%9C-EC2-%EC%A0%91%EC%86%8D%ED%95%98%EA%B8%B0

HOME