Skip to content

Instantly share code, notes, and snippets.

@AysadKozanoglu
Created November 1, 2022 23:11
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save AysadKozanoglu/0148201e46afa41fea399334ee673b00 to your computer and use it in GitHub Desktop.
Save AysadKozanoglu/0148201e46afa41fea399334ee673b00 to your computer and use it in GitHub Desktop.
nginx lua scripting against log4j protection
# LUA block to detect, block and log Log4Shell attacks (C) Infiniroot 2021 (@infiniroot)
# with lua fixes and other enhancements from Andreas Nanko (@andreasnanko)
rewrite_by_lua_block {
function decipher(v)
local s = tostring(v)
s=ngx.unescape_uri(s)
if string.find(s, "${base64:") then
t=(string.gsub(s, "${${base64:([%d%a%=]+)}}", "%1"))
s=string.gsub(s, "${base64:([%d%a%=]+)}", tostring(ngx.decode_base64(t)))
end
s=string.gsub(s, "${lower:(%a+)}", "%1")
s=string.gsub(s, "${upper:(%a+)}", "%1")
s=string.gsub(s, "${env:[%a_-]+:%-([%a:])}", "%1")
s=string.gsub(s, "${::%-(%a+)}", "%1")
if string.lower(s) == string.lower(tostring(v)) then
return string.lower(s)
else
return decipher(s)
end
end
local req_headers = "Headers: ";
local h, err = ngx.req.get_headers()
for k, v in pairs(h) do
req_headers = req_headers .. k .. ": " .. tostring(v) .. "\n";
if v then
if string.match(decipher(v), "{jndi:") then
ngx.log(ngx.ERR, 'Found potential log4j attack in header ' .. k .. ':' .. tostring(v))
ngx.exit(ngx.HTTP_FORBIDDEN)
end
else
if err then
ngx.log(ngx.ERR, "error: ", err)
return
end
end
end
local uri = tostring(ngx.var.request_uri)
if string.match(decipher(uri), "{jndi:") then
ngx.log(ngx.ERR, 'Found potential log4j attack in request: ' .. uri )
ngx.exit(ngx.HTTP_FORBIDDEN)
end
}
@AysadKozanoglu
Copy link
Author

This not only blocks the attacks (with a HTTP 403) but also logs the attack vector in the relevant error log. Are there better mitigations? Most likely, as always (e.g. WAF, IPS, NIDS, etc). But this solution is a quick and effective way to tackle the attacks whilst keeping the logs for analysis in the coming days.
After a couple of hours in production, we found quite a few attacks - mainly on "well known" customer domains. The Lua script nicely logged which domain was targeted and how (in which header) the exploit was added in the payload:

@AysadKozanoglu
Copy link
Author

thanks a lot to infinitboot GmbH / Germany

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment