본문 바로가기
IT생활

소스 코드의 주석은 컴파일될까? 그리고 디컴파일하면 복구될까?

by 우물 밖 개구리. 2025. 3. 15.
반응형

소스 코드의 주석은 컴파일될까? 그리고 디컴파일하면 복구될까?

코드를 작성할 때 주석(Comment)을 활용하여 설명을 추가하는 것은 일반적인 습관이다. 하지만 이 주석이 컴파일 과정에서 유지되는지, 그리고 디컴파일을 하면 다시 복구할 수 있는지에 대한 궁금증이 있을 수 있다.

이 질문에 대한 답을 단순화하면:

  • 일반적으로 주석은 컴파일 시 제거되며, 실행 파일에는 포함되지 않는다.
  • 디컴파일을 해도 주석을 복구하는 것은 불가능하다.

그러나 이는 사용된 프로그래밍 언어, 컴파일러의 종류, 그리고 디컴파일 방법에 따라 달라질 수 있다. 이를 좀 더 깊이 분석해 보자.


1. 주석이 컴파일에 포함되는가?

대부분의 프로그래밍 언어에서 주석은 컴파일러 또는 인터프리터가 무시하는 요소이다. 이를 통해 코드의 가독성을 높이고 개발자가 참고할 수 있도록 돕지만, 실행 바이너리에는 포함되지 않는다.

주석의 종류에 따라 처리 방식이 다를 수 있다.

1.1. 주석의 종류와 컴파일 처리 방식

프로그래밍 언어에서 주석은 주로 다음과 같이 구분된다.

① 소스 코드 주석 (Source Code Comment) - 무시됨

일반적인 주석으로, 컴파일러가 무시하는 코드의 일부이다.

  • C, C++, Java 등에서 사용되는 주석
  • // 한 줄 주석 - 컴파일러가 무시함 /* 여러 줄 주석 - 컴파일러가 무시함 */
  • Python 주석
  • # 한 줄 주석 - 실행되지 않음 """ 여러 줄 주석 (문자열 리터럴로 인식될 수도 있음) """

이러한 주석들은 컴파일 과정에서 제거되므로 실행 파일에 포함되지 않는다.

② 문서화 주석 (Documentation Comment) - 일부 유지될 수 있음

일부 언어에서는 문서화를 위한 주석이 제공되며, 이는 코드에서 제거될 수도 있지만, 특정 설정에서는 유지될 수도 있다.

  • JavaDoc 스타일 주석 (Java, Kotlin)
    • JavaDoc 도구를 통해 API 문서를 생성할 때 사용됨.
    • 컴파일 후 .class 파일에는 남지 않지만, Java 리플렉션(Reflection)과 같은 기법을 사용하면 일부 주석 기반 메타데이터를 접근할 수도 있음.
  • /** * 이 메서드는 사용자의 정보를 출력합니다. */ public void printUserInfo() { ... }
  • C# XML 주석
    • XML 기반 문서화 주석은 컴파일된 DLL이나 XML 파일로 별도 저장될 수 있음.
  • /// <summary>사용자 정보를 출력합니다.</summary> public void PrintUserInfo() { ... }

③ 애노테이션 및 프리프로세서 지시문 - 일부 포함 가능

어떤 주석은 실제로 코드에 영향을 미치기도 한다.

  • C 계열 언어에서의 프리프로세서 지시문
    • #ifdef, #define 등의 전처리기 지시문은 컴파일 타임에 해석되며, 특정 조건에서만 코드가 포함될 수도 있다.
    • 따라서 이러한 주석과 함께 조건부 컴파일 코드가 실행 파일에 영향을 줄 수 있음.
  • #ifdef DEBUG // 이 코드는 디버그 모드에서만 포함됨 #endif
  • Java의 애노테이션 (@Annotation)
    • 애노테이션 자체는 주석처럼 보이지만, 런타임에 유지되는 경우(예: @Retention(RetentionPolicy.RUNTIME)) 리플렉션을 통해 접근할 수 있음.
    • 일반 주석과 다르게 실행 바이너리에 포함될 수도 있음.
  • @Override public void someMethod() { ... }

2. 디컴파일하면 주석을 복구할 수 있을까?

일반적으로 디컴파일을 통해 실행 파일에서 주석을 복구하는 것은 불가능하다. 그 이유는 다음과 같다.

2.1. 주석은 컴파일 과정에서 사라짐

  • 주석은 실행과 무관한 부분이므로, 컴파일러는 이를 완전히 제거한 후 바이너리를 생성한다.
  • 따라서 실행 파일(예: .exe, .class, .jar, .so, .dll)에는 주석이 포함되지 않는다.

2.2. 디컴파일의 원리

디컴파일(decompilation)은 바이너리를 다시 소스 코드 형태로 변환하는 과정이다. 그러나 주석은 소스 코드에만 존재하므로, 디컴파일 과정에서 복구할 수 없다.

예제:

  1. C 코드 (소스 코드)
  2. // 이 함수는 두 수를 더합니다. int add(int a, int b) { return a + b; }
  3. 컴파일된 어셈블리 코드 (gcc -O2 적용 후)
    • 여기에는 원래 주석(“이 함수는 두 수를 더합니다.”)이 포함되지 않는다.
  4. _add: lea eax, [rdi + rsi] ; a + b 연산 수행 ret
  5. 디컴파일 후 C 코드 복구 (Ghidra, IDA 사용)
    • 디컴파일러는 코드를 분석하여 원래 C 코드와 유사한 형태로 변환하지만, 주석은 복구되지 않는다.
  6. int add(int a, int b) { return a + b; }

2.3. 예외적인 경우: 디버그 심볼이 포함된 경우

  • 일부 디버그 빌드(Debug Build) 의 경우, 심볼(Symbol) 정보가 포함될 수 있다.
  • 예를 들어, PDB (Program Database) 파일을 포함하면 변수명, 함수명, 디버깅 메시지는 일부 복원될 수 있으나, 여전히 주석은 복구되지 않는다.

결론: 주석은 컴파일되지 않으며, 디컴파일로 복구할 수 없다.

  1. 일반적인 주석은 컴파일러가 무시하고 실행 파일에 포함되지 않는다.
  2. 디컴파일을 하더라도 주석을 복구하는 것은 불가능하다.
  3. 다만, 문서화 주석(예: JavaDoc, XML 주석)이나 애노테이션 같은 일부 주석 기반 정보는 별도 파일로 유지될 가능성이 있다.
  4. 디버그 심볼이 포함된 빌드의 경우, 코드 설명을 포함한 일부 주석 정보가 유지될 가능성이 있으나, 일반적인 배포용 실행 파일(Release Build)에서는 사라진다.

즉, 컴파일된 실행 파일에서 원래 소스 코드의 주석을 찾을 수 있는 방법은 없으며, 코드 분석을 통해 유추하는 것만 가능하다.

반응형