AtraFelis's Develop Diary

[Linux] make 명령어란? 본문

ETC/Linux

[Linux] make 명령어란?

AtraFelis 2024. 5. 20. 21:22

최근에는 컴파일러의 발전과 AI의 발전으로 잘 사용하지 않는 추세라고 하지만, 알아두면 알게 모르게 편하게 사용할 구석이 많은 것 같은 make 명령어에 대해 알아보려고 한다. 개인 프로젝트 보다는 규모가 큰 팀프로젝트 등에서 자주 활용하게 되지 않을까 하는 생각이 든다.

간략하게 설명하자면, make는 매크로다. 명령어를 입력하면 사전에 정의해둔 순서대로 명령어가 실행된다. 그렇다면 이 정보를 어디에 저장하느냐? 그것이 이 다음에 설명할 Makefile이다.


Makefile

당연히 이 파일은 make를 실행하는 디렉토리에 존재해야 한다. 간단한 예시를 몇 가지 보자.

1. 소스파일 → 실행파일

all: test1 test2 # 만들어지는 실행파일 이름이 들어간다. 여러 개일 경우 반드시 이곳에 기술해야 한다.

test1 : test1.c
    gcc -o test1 test1.c

test2 : test2.c
    gcc -o test2 test2.c

여기서 # 으로 표시된 부분은 주석을 의미한다.

디렉토리에 test1.c, test2.c라는 소스 코드가 존재한다고 했을 때, 이 소스코드를 자동으로 컴파일 시켜주는 매크로다. 여기서 $ make를 입력하면, Makefile에 정의된 대로 test1.c가 컴파일 되어 test1, test2.c가 컴파일 되어 test2라는 실행 파일이 만들어진다.

$ make
gcc -o test1 test1.c
gcc -o test2 test2.c

제대로 컴파일이 되었다면 이런 메시지가 나타날 것이다.

make: 'all'을(를) 위해 할 일이 없습니다.
위와 문구가 나타난다면, 이것은 오류 메시지가 아니라 이미 최신 버전의 실행파일을 가지고 있기 때문이다. touch test1.c test2.c를 한 후 다시 make를 하면 위처럼 나타날 것이다.

 

2. 소스파일 → 목적어파일 → 실행파일

all: test1

# 링크 룰
test1 : test1.o
    gcc -o test1 test1.o

#컴파일 룰
test1.o : test1.c
    gcc -c test1.c

링크 룰과 컴파일 룰의 순서는 엄격하게 정해져 있지 않으나, 일반적으로 링크 룰을 먼저 작성한 후 컴파일 룰을 작성하는 것이 읽기 쉽다. 링크 룰이 최종 목표를 정의하고, 그 목표를 달성하기 위해 필요한 중간 파일을 나열하기 때문이다. (GPT 선생님께서 그렇다고 한다.)

# make
gcc -c test1.c
gcc -o test1 test1.o

test1.c에 대한 목적어 파일인 test1.o가 먼저 생성된 후, test1이 링크 룰에 의해 만들어진다.

 

3. 소스 파일이 여러 개인 경우

# test1.c 파일이 add.c, sub.c, mul.c, dvd.c 소스를 include하고 있다고 가정한다.

SOURCE = test1.c add.c sub.c mul.c dvd.c
OBJECTS = test1.o add.o sub.o mul.o dvd.o

all: test1

test1: $(SOURCE)
    gcc -o test2 $(SOURCE)

test2: $(OBJECTS)
    gcc -o test1 $(OBJECTS)

test1.o: test1.c
    gcc -c test1.c

add.o: add.c
    gcc -c add.c

sub.o: sub.c
    gcc -c sub.c

mul.o: mul.c
    gcc -c mul.c

dvd.o: dvd.c
    gcc -c dvd.c

이렇게 파일이 여러 개일 경우, 위에 상수를 정의할 수 있다. 위 예제에서는 소스 파일과 목적어 파일을 각각 SOURCE, OBJECTS에 미리 정의해두었다. $(상수 이름)으로 사용할 수 있다.

$ make
gcc -o test1 test1.c add.c sub.c mul.c dvd.c
gcc -c test1.c
gcc -c add.c
gcc -c sub.c
gcc -c mul.c
gcc -c dvd.c
gcc -o test2 test1.o add.o sub.o mul.o dvd.o

clean rule

# 3번 예제와 동일하다고 가정.

clean:
    rm -f test1 test2 $(OBJECTS)

위와 같이 작성해두면, $ make clean 명령어를 이용해 rm -f test1 test2 $(OBJECTS)를 실행할 수 있다. 즉, make로 만든 실행파일과 목적어 파일을 한 번에 삭제할 수 있다.