728x90
반응형
맨 위로 올라가기
GCC(GCN Compiler Collection)

 

다양한 프로그래밍 언어를 위한 컴파일러 모음이다. 현재는 C, C++, Objective C, Go 및 기타 여러 언어를 지원한다.
GCC는 오픈 소스 소프트웨어 개발에서 중요한 역할을 한다.

 

  1. -o: (output)
    출력 파일 이름을 지정한다.
    예를 들어 'gcc -o <OUTFILE_NAME> <FILENAME.c>
    FILENAME.c를 컴파일 하여 실행파일을 생성한다.

  2. -I: (Include)
    컴파일러가 헤더파일을 찾을 추가 디렉토리를 지정한다.
    예를 들어, 'gcc -I <HEADER_PATH> FILENAME.c' 은 실행파일 FILENAME을 컴파일 할 때 지정된 헤더 경로도
    포함하는 것이다.

  3. -L: (Library)
    컴파일러가 라이브러리 파일을 찾을 추가 디렉토리를 지정한다. 'gcc -L <LIB_PATH> FILENAME.c'

  4. -E: (preprocess)
    이 옵션은 컴파일러가 소스파일을 전처리만(prerpocess)만 하고 컴파일하지 않는다.

  5. -S: (assembly)
    이 옵션은 소스 코드를 aseembly 언어로만 컴파일하고 오브젝트 파일을 생성하지 않을 때 사용한다.

  6. -c: (compile)
    오브젝트 파일(.o 파일)은 생성하나, 링크과정은 수행하지 않는다.

// module1.c
#include <stdio.h>

void module1(void)
{
        printf("Module1\n");
}

$ gcc -E module1.c  -o module1.i

* gcc 명령어에 -E 옵션을 통해 전처리만하고 'module1.i'라는 파일로 출력한다.
어떤 빌드 툴과 라이브러리가 사용되는지 세부적으로 기술되어 있다.

// module1.i
# 1 "module1.c"
# 1 "<built-in>"
# 1 "<command-line>"
# 31 "<command-line>"
# 1 "/usr/include/stdc-predef.h" 1 3 4
# 32 "<command-line>" 2
# 1 "module1.c"
# 1 "/usr/include/stdio.h" 1 3 4
# 27 "/usr/include/stdio.h" 3 4
# 1 "/usr/include/aarch64-linux-gnu/bits/libc-header-start.h" 1 3 4
# 33 "/usr/include/aarch64-linux-gnu/bits/libc-header-start.h" 3 4
# 1 "/usr/include/features.h" 1 3 4
# 461 "/usr/include/features.h" 3 4
# 1 "/usr/include/aarch64-linux-gnu/sys/cdefs.h" 1 3 4
# 452 "/usr/include/aarch64-linux-gnu/sys/cdefs.h" 3 4
# 1 "/usr/include/aarch64-linux-gnu/bits/wordsize.h" 1 3 4
# 453 "/usr/include/aarch64-linux-gnu/sys/cdefs.h" 2 3 4
# 1 "/usr/include/aarch64-linux-gnu/bits/long-double.h" 1 3 4
# 454 "/usr/include/aarch64-linux-gnu/sys/cdefs.h" 2 3 4
# 462 "/usr/include/features.h" 2 3 4
# 485 "/usr/include/features.h" 3 4
# 1 "/usr/include/aarch64-linux-gnu/gnu/stubs.h" 1 3 4

...

$ gcc -S module1.c

 

* 위 명령어를 통해 module1.c 코드 파일을 어셈블리 코드변환하여 파일로 출력된 것을 확인할 수 있다.

 

// module1.s        
        .arch armv8-a
        .file   "module1.c"
        .text
        .section        .rodata
        .align  3
.LC0:
        .string "Module1"
        .text
        .align  2
        .global module1
        .type   module1, %function
module1:
.LFB0:
        .cfi_startproc
        stp     x29, x30, [sp, -16]!
        .cfi_def_cfa_offset 16
        .cfi_offset 29, -16
        .cfi_offset 30, -8
        mov     x29, sp
        adrp    x0, .LC0
        add     x0, x0, :lo12:.LC0
        bl      puts
        nop
        ldp     x29, x30, [sp], 16
        .cfi_restore 30
        .cfi_restore 29
        .cfi_def_cfa_offset 0
        ret
        .cfi_endproc
.LFE0:
        .size   module1, .-module1
        .ident  "GCC: (Ubuntu 9.4.0-1ubuntu1~20.04.2) 9.4.0"
        .section        .note.GNU-stack,"",@progbits

* module1.c로 정적 라이브러리를 만들고 난 후 링크하여 실행 파일을 생성하는 과정이다.

$ gcc -c module1.c

 

* module.o 라는 오브젝트 파일을 생성한다.

$ ar rcs libmodule1.a module1.o

* 'ar' 아카이브 프로그램을 사용하여 'module1.o' 오브젝트 파일로부터 정적 라이브러리인 'libmodule1.a' 를 생성한다.
ar은 Unix 시스템에서 사용되는 archiver 툴이다. 정적 라이브러리를 생성하고 관리하는 데 주로 사용된다.

'r'(replace) 는 기존 존재하는 파일을 새버전으로 교체, 'c'는 아카이브 생성시 사용, s는 심볼테이블 생성 및 업데이트할 때 사용된다. 이런 정적 라이브러리는 프로그램을 컴파일 할 때 링커에 의해 사용된다.

 

이제 main 파일에서 생성된 라이브러리를 링크하여 사용해보겠다.
-L 라이브러리 경로에 libmodule1.a의 경로인 현재위치(.), -l을 라이브러리 이름에 module1을 입력한다.

$ gcc -o exec main.c -L. -lmodule1 -I ../include

 

 

 

728x90
반응형

'Language > C & C++' 카테고리의 다른 글

Variable arguments.  (0) 2024.03.09
A simple question about the preprocessor directive 'include'  (0) 2024.03.05
구조체(Structure)  (0) 2023.04.16
증감 연산자의 응용  (0) 2023.04.15
특수연산자 (괄호, 쉼표)  (0) 2023.04.15

+ Recent posts