태그 보관물: compiler

compiler

임의의 낯선 사람으로부터 소스 코드를 컴파일하는 것이 얼마나 안전합니까? [닫은] 보내는 실행 파일을 실행하고

직업 지원자가 자신의 기술을 증명하기 위해 보내는 코드를 검토한다고 가정합니다. 분명히 그들이 보내는 실행 파일을 실행하고 싶지 않습니다. 명확하지는 않지만 코드 컴파일 결과를 실행하지는 않습니다 (예를 들어 Java는 주석에서 실행 가능한 코드를 숨길 수 있습니다 ).

코드를 컴파일하는 것은 어떻습니까? 컴파일러 경고가 필요하지만 코드에 컴파일러를 악용하는 영리한 문자 시퀀스가 ​​포함되어 있고 컴파일러가 내 컴퓨터를 손상시키는 경우 어떻게해야합니까?

내가 “컴파일러 취약점”에 대해 Google을 방문했을 때 내가 얻은 히트는 컴파일러 최적화 및 코드 방출에 관한 것입니다.

컴파일러는 일반적으로 영리한 코드를 컴파일 할 때 사용자 시스템을 손상시키지 않도록 유효성을 검사합니까? 낯선 사람의 코드를 컴파일하는 것이 얼마나 안전합니까?



답변

따라 다릅니다.

이 makefile 조각은 홈 디렉토리를 삭제할 수 있습니다.

all:
    rm -rf ~

따라서 도구 (예 : cmake 또는 makefile 시스템)를 사용해야하는 경우 안전하지 않습니다. 그것은 코더가 얼마나 악의적인지에 달려 있습니다.

반면에 컴파일러는 사람들이 프로그래밍하므로 버그가 있습니다. 따라서 누군가 컴파일 과정에서 악성 코드를 실행하는 방법을 찾았을 수도 있습니다.

주석에서 제안한대로 컴퓨터에서 재미있는 작업을 수행하지 않으려면 가상 컴퓨터를 사용하십시오.


답변

나는 비즈니스의 어딘가에 이미 특정 언어와 컴파일러 버전에 대한 해킹을 만든 영리한 사람들이 있다고 확신합니다. 이와 같은 것을 찾는 가장 좋아하는 장소는 아마도 International Obfuscated C 콘테스트 일 것입니다 (Java와 비슷한 것이 있는지 모릅니다). 그러나 실제로는 위험을 얼마나 높게 생각합니까?

  • 신청자가 당신에게 그럴듯한 인상을 남긴다

  • 그 사람은 당신의 리뷰가 얼마나 많은지 알지 못합니다.

  • 그는 / 사용중인 정확한 컴파일러 버전을 모른다

  • 그 / 그녀는 당신이 가상 환경이나 온라인 컴파일러를 사용하는지 알지 못합니다.

  • 효과적으로 검토하기에는 너무 큰 프로그램을 수락하지 않습니다

  • 당신은 당신에게 의심스러운 것을 컴파일하지 않습니다

  • 실제로 이러한 작업을 기술적으로 수행하는 방법을 실제로 아는 사람은 많지 않습니다.

따라서 컴파일은 이론적으로 “완전히 안전하지”않지만 IMHO는 실제로 “컴파일러가 pwn 될”위험이 매우 낮습니다.


답변

몇 가지 경우를 구별해야합니다.

  1. 컴파일러의 버그. 모든 복잡한 프로그램과 마찬가지로 컴파일러에도 버그가있을 수 있으며 이러한 버그 중 하나를 악용 할 수 있습니다.
  2. 트로이 목마. 공격자는 컴파일 프로세스의 일부로 임의의 코드를 실행하도록 할 수 있습니다. A Makefile, a build.xml, configure셸 스크립트 등 기술적으로 이것은 공격자의 코드를 컴파일하는 것이 아니라 컴파일 환경을 설정하기 때문입니다.
  3. 컴파일 타임에 임의의 코드를 실행할 수있는 언어 스칼라의 매크로 언어는 스칼라이고, 커먼 리스프의 매크로 언어는 커먼 리스프, 템플릿 하스켈의 매크로 언어는 하스켈입니다. 스칼라는 또한 컴파일러 플러그인을 가지고 있는데, 이는 컴파일 타임에 실행되는 임의의 스칼라 코드입니다. F #에는 형식 공급자가 있습니다.
  4. 컴파일 타임에 튜링 계산을 허용하는 언어. 스칼라와 하스켈 타입 시스템은 C ++의 템플릿과 마찬가지로 Turing-complete입니다. 무한 루프를 포함하여 (이에 국한되지는 않음) 컴파일 타임에 컴파일러가 임의의 Turing 계산을 수행하도록 할 수 있습니다. Turing-complete는 모든 Turing-computable 함수를 계산할 수 있다는 것을 의미하며, 파일 시스템이나 이와 유사한 것에 액세스 할 수있는 것은 아닙니다. 그러나 컴파일하는 데 시간이 오래 걸리는 프로그램을 만들 수 있습니다.
  5. 컴파일 시간이 매우 길다. 예를 들어, 과부하 해결에 대한 C #의 규칙은 너무 복잡하여 3-SAT 문제를 C # 과부하 해결로 인코딩 할 수 있습니다. 3-SAT는 물론 NP- 완료로 유명합니다. 다시 말해, 현재의 지식에 따르면 C #에서 과부하 해결을위한 효율적인 알고리즘을 찾는 것은 불가능합니다. 컴파일에 시간이 오래 걸리지 않지만, 우주의 수명보다 컴파일 시간이 오래 걸리는 큰 프로그램은 아닙니다.

# 4. 그리고 # 5. 서비스 거부가 발생합니다. 실제로 C ++ 및 Scala 컴파일러는 재귀의 양을 제한하므로 실제로 무한 루프를 작성할 수 는 없습니다 . 스칼라에서는 구현 제약 일 뿐이지 만 C ++에서는 스펙에서 명시 적으로 허용한다고 생각합니다.

# 2. 코드를 실행하지 않는 코드를 컴파일하는 것에 관한 질문이기 때문에 기술적으로 문제의 범위를 벗어났습니다.

#1. 없을 것입니다. 한편으로 프로덕션 컴파일러는 매우 복잡하므로 버그 가능성이 높습니다. 다른 한편으로, 그들은 형식이 잘못된 입력을 정상적으로 처리하는 것은 컴파일러의 작업 설명의 일부입니다. 테스트를 거치지 않더라도 어쨌든 잘못된 코드로 공격받을 것입니다. 정크 사람들이 컴파일러에서 던지는 것에 대한 예제는 StackOverflow 질문을 살펴보십시오!

일부 컴파일러는 컴파일 타임 코드가 시스템에 갖는 액세스 종류를 제한 할 수 있지만 일부 사용 사례의 경우 전체 액세스를 피할 수 없습니다. 예를 들어, F #의 형식 공급자의 목적은 형식 시스템이 F #과 일치하지 않는 데이터에 대해 합성 형식을 “가짜”로 만들어 강력한 형식의 WSDL 스키마가있는 웹 서비스와 상호 작용할 수 있도록하는 것입니다. 패션. 그러나이를 수행하려면 유형 제공자가 파일 시스템 또는 웹에서 WSDL 스키마 자원에 액세스 할 수 있어야하므로 파일 시스템 및 네트워크 액세스 권한이 있어야합니다.

안전합니까? 엄밀히 말하면 위험합니까? 실제로는 아닙니다.


답변

코드를 컴파일 할 때 위험이 없어야 합니다. 에 이론 영리한 해커를 활용하지만, 매우 가능성이 소리입니다 수있는 컴파일러의 버그가있을 수 있습니다.

주의하십시오 건물은 안전하지 않을 수 있습니다. 예를 들어 C # ‘build event’를 사용하면 빌드 전후에 실행할 임의의 명령 줄을 지정할 수 있습니다. 이는 분명히 위험하며 컴파일러 코드의 버퍼 오버플로보다 훨씬 쉽게 이용할 수 있습니다.


답변

추측하는 대신, 나는 실제로 대답하기 전에이 주제에 대해 약간의 연구를하면서, 내가 생각할 수있는 가장 권위있는 자료 ( CVE Details )로 이동했다. 공개적으로 공개 된 보안 익스플로잇의이 포괄적 인 목록은 다양한 유형의 소프트웨어의 위협 수준을 평가하기 위해 할 수있는 최선의 방법 일 것입니다.

물론 사용 가능한 모든 자료 를 읽는 데 시간이 걸리지는 않았지만 샘플 위협 평가를 위해 몇 가지 “기본”컴파일러, IDE 및 텍스트 편집기를 선택했습니다. 소프트웨어 실행에 대해 진지한 경우 최소한 어떤 위협이 있는지 확인해야합니다. 또한 오래된 소프트웨어는 일반적으로 최신 소프트웨어보다 버그가 많으므로 실행중인 최신 버전을 실행하는 것이 이상적입니다.

먼저 다양한 텍스트 편집기를 살펴볼 수 있습니다. 최고의 편집자가 가장 간단한 것 같습니다. Linux 쉘을 사용중인 경우 Vi, Windows를 사용중인 경우 메모장 단일 문자가 현재 인코딩 체계를 벗어나는 경우 형식 지정 기능, 구문 분석, 데이터에 대한 간단한보기 및 구문 분석의 자동 종료가없는 것입니다. 메모장 ++조차도 소수의 취약점이 있습니다. 신뢰할 수없는 파일을 볼 때 복잡한 것을 피하십시오.

둘째, IDE를 살펴볼 수 있습니다. IDE에서 파일을 열도록 선택하면 일부 IDE에서 버그가보고 된 것입니다. Visual Studio에는 확장 메커니즘을 통해 이용 가능한 익스플로잇이 있었으므로 솔루션을 여는 데 문제가있을 수 있습니다. IDE를 피하면 사용자와 신뢰할 수없는 코드 사이의 전체 문제가 발생하지 않습니다. VI를 사용하는 것이 훨씬 안전 해 보입니다.

셋째, 실제 컴파일러를 살펴볼 수 있습니다. 나는 Adobe, Microsoft, Java 및 GNU의 C / C ++를 포함한 몇 가지를 탐색했으며 일반적으로 말해서 컴파일하는 코드 (및 사용자 정의 make-file이 없다고 가정하여 빌드 조차도 )가 상대적으로 안전하다는 것을 알았습니다. 실제로 컴파일 된 바이너리를 실행하여 발생할 수있는 보안 취약점이 있습니다. 다시 말해, 컴파일만으로 시스템을 인수 할 수는 없지만 코드를 실행하여 시스템을 인수 할 수 있습니다.

결론적으로, 전달 방법이 시스템을 이미 가로 채지 않았다고 가정하면 (예 : 이메일 클라이언트가 해킹되었거나 USB 드라이브가 감염된 경우 …) 소스 코드를 읽고 소스 코드를 컴파일하는 것이 안전 할 것입니다 . 특정 소프트웨어를 조사하면 파일을 올바른 코드 페이지 등으로 검증하는 등의 방법으로 더 안전하게 만들 수 있습니다. 코드 실행은 신경 쓰지 않는 하드웨어에서만 수행해야합니다. VM은 아니지만 네트워크 액세스가없고 민감한 파일이나 외부 장치가없는 물리적으로 다른 컴퓨터입니다. 코드를 이해 한다고 생각 하더라도 간단한 연구 결과에 따르면 컴파일러에도 숨겨진 버퍼 오버플로 악용이 뒤에서 몰래 들어가 임의의 코드를 실행할 수있는 버그가 있지만 원하는 경우에만프로그램을 실행 하거나 디버그 하십시오. 실제 컴파일은 안전해야합니다.


답변

글쎄, 나는 “코드 검토”로 시작할 것이다. 실제로 코드를 실행해야하는 이유는 무엇입니까?

그 외에도 코드를 넣고 컴파일 및 / 또는 실행할 수있는 온라인 컴파일러가 많이 있습니다. 이를 요구 사항으로 만들 수 있습니다. 온라인 컴파일러에서 컴파일합니다.

온라인 컴파일러가있는 페이지의 예는 다음과 같습니다. 온라인 컴파일러

면접 검토를위한 코드는 어떤 일이 일어나고 있는지 이해하지 못할 정도로 크지 않아야합니다.


답변

컴파일러는 일반적으로 영리한 코드 조각을 컴파일 할 때 사용자 시스템을 손상시키지 않도록 확인됩니까?

일반적으로 그것들은 너무 복잡해서 종종이 속성을 증명하는 것이 실용적이지 않은 언어를 사용하여 작성되었습니다.

아마도 이러한 특정 의도는 아니지만 퍼즈 테스트 컴파일러의 개념은 적어도 알려져 있습니다 ( LLVM은 이제 스스로 퍼지를 테스트 할 수 있습니다 ). 컴파일러 버그로 인해 컴파일러와 충돌하는 입력을 포착하기위한 테스트는 악용 가능한 결함을 유발 하는 경향 이 있습니다.

당연히 관심있는 특정 컴파일러가 잠재적 충돌을 찾기 위해 테스트 또는 퍼지 테스트되었는지 여부와 발견 된 버그가 실제로 수정되었는지 여부를 조사해야합니다. 경험상 메모리 예외에서 잡히지 않는 것보다 더 심각한 충돌이 발생하면 세부 사항을 더 조사하지 않고 악용 될 수있는 심각한 가능성을 고려해야합니다.

낯선 사람의 코드를 컴파일하는 것이 얼마나 안전합니까?

불행히도, 한 줄의 길이는 얼마입니까? 원칙적 으로 전자 메일은 메일 클라이언트를 이용하거나 소스 코드는 텍스트 편집기 나 cppcheck를 이용하여 컴파일러에 도달하기도합니다. 온라인 컴파일러 사용에 대한 의견에 대한 Sebastian의 제안은 꽤 좋은 것이지만, 물론 코드는 컴파일러가 수용 할 수있는 형식이어야합니다.

일반 코드의 컴파일 타임 실행을위한 기능이있는 언어 또는 컴파일러는 물론 의심의 여지가 있습니다. C ++ 템플릿은 기능적으로 완전하지만 시스템에 대한 (의도적 인) 액세스 권한이 없으므로 상대적으로 위험이 적습니다. BЈовић는 make위험성이 매우 높은 것으로 언급 합니다. 낯선 사람의 코드를 실행하기 때문에 코드가 makeC ++이 아닌 언어 로 작성된 것입니다 . 컴파일러가 실행 system되면 동일한 보트에 있습니다. 필자가 올바르게 기억한다면 임의의 컴파일 타임 코드 실행을 수행 할 수있는 어셈블러를 사용했습니다. 조회 테이블을 계산하기위한 것이지만 시스템 호출을 방해하는 것은 없다고 생각합니다.

실제로 코드가 괜찮아 보이고 이해한다고 생각되면 컴파일 할 위험이 매우 낮으며 “잠긴 브라우저로 인터넷을 탐색”하는 것보다 훨씬 낮은 위험을 고려할 것입니다. 나는 범용 컴퓨터에서 일상적으로 위험한 일을하지만 바이러스 랩이나 중요한 서버에서는 수행하지 않는 것들이 많습니다. 코드가 웃기거나 난독 화되면 읽을 수없는 쓰레기에 숨겨진 악용을 포함 할 수있는 위험 외에도 쓰레기 코드이기 때문에 컴파일 할 위험이 없습니다. 언더 핸드 코드는 어렵지만 가능합니다. 컴파일러 익스플로잇을 통해 머신을 소유하는 언더 핸드 코드는 사소한 실행 페이로드를 포함해야하므로 매우 어렵습니다.

더 자세히 살펴보고 싶다면 온라인 컴파일러를 호스팅하는 사람들에게 물어보십시오. 그것이 그들에게 수행되지 않은 경우 (NSA 또는 이와 동등한 것의주의를 기울이지 않음) 당신은 그것이 당신에게 이루어지지 않을 것이라고 합리적으로 생각할 수 있습니다. 그들은 적절한 샌드 박스에서 컴파일러를 실행하는 데 약간의 노력을 기울 였는데, 이는 당신이 가고 싶어하는 것보다 더 많은 노력일지도 모르지만, 적어도 그 샌드 박스가 얼마나 자주 문제를 해결하는지 알려줄 수있을 것입니다.