개요

이 글에서는 유니코드 쉘코드와 베니스 쉘코드에 대하여 간단하게 알아본다.

 

유니코드를 기본 값으로 사용하는 시스템에서 Payload를 주입했을 때, 중간에 Null byte가 삽입되는 경우가 있을 수 있다. 이는 입력값을 Unicode로 처리하기 때문에 일어날 수 있는데, 이러한 경우 홀수번째 값이 Null byte인 값으로 쉘코드를 만들수 있을 것인지에 대한 내용을 다루어보도록 하자.

 

베니스 쉘코드(venetian shellcode)

일단 PC는 원하는 주소로 잘 변경했다고 가정을 한 뒤 생각해보자.

 

그냥은 쉘코드를 만들기에는 중간에 null byte가 들어있는 기계어 코드는 많지 않으므로 제약사항이 많을 수 있다.

 

하지만 몇가지 코드들을 이용해서 메모리에 값을 쓰도록 한다던지, 레지스터 값을 +1를 한다던지 등의 작업은 할 수 있다.

 

위와 같이 코드를 구성한다면 중간중간에 Null byte가 들어가지만, 원하는 동작들은 할 수 있다.

 

그리고 또한 inc instruction도 쓸만하다.

위와 같이 구성을 하면 조건에 맞게 shellcode를 만들 수 있다.

 

이를 이용해서 eax를 하나씩 늘려가면서 eax를 가리키는 메모리 주소에 원하는 1byte를 쓸 수 있다.

그리고 null byte align을 맞추기 위해서 [ebp]가 가리키는 곳에 ch 레지스터의 값을 더할 수 있는데 보통 이 값은 0이므로 아무일도 일어나지 않는다.

 

이러한 걸 이용해서 베니스 쉘코드란걸 작성을 할 것인데, 아이디어는 간단하다.

 

베니스 코드라는 녀석을 이용해서 메모리 적당한 곳에 Null byte가 없는 우리가 원래 쓰던 진짜 쉘코드를 쓰게 만든다.

베니스 코드는 유니코드로 인코딩되어서 중간중간에 null byte가 있지만, 위에서 하는방식으로 원하는 값을 1byte씩 한땀 한땀 작성할 수 있다.

그리고 우리가 베니스 코드로 작성한 진짜 쉘코드(null byte가 없는)녀석으로 점프를 뛰면 끝이다.

블랙햇 발표자료 슬라이드에 해당 내용을 나타낸 곳이다. UNICODE인 베니스 코드가 리얼 쉘코드를 한땀 한땀 쓰는 모습이다.

 

그외에도 NOP이나 byte값 변경이라던지 등에 유용한 어샘 코드들이 좀 있다.

저런 녀석들을 이용해서 리얼 쉘코드를 만든 뒤 점프뛰면 되겠다

add al, 0는 NOP에 해당하고

inc byte ptr[eax]는 1바이트 값 변경, mov byte ptr[eax]도 mov를 이용한 바이트 값 변경에 해당된다.

 

대신 이 쉘코드는 꽤 길어지는 경향이 있긴 한데 그래도 꽤 쓸만하다.

 

 

--------------------------------------------------------------------

https://www.corelan.be/index.php/2009/11/06/exploit-writing-tutorial-part-7-unicode-from-0x00410041-to-calc/

https://www.blackhat.com/presentations/win-usa-04/bh-win-04-fx.pdf

https://www.kisec.com/_core/_download.php?file_url=lab&file_name=album_5b69337831c13.pdf&real_name=%5Bexploit+writing%5D+7_%EC%9C%A0%EB%8B%88%EC%BD%94%EB%93%9C.pdf

+ Recent posts