




















Updated Dec 20th. This article describes how Magento is affected by the critical log4j vulnerability, and what you can (and should) do to prevent a hack.
A critical vulnerability in the popular Log4j Java library has been massively exploited since December 1st. It exposes full control to a remote attacker, is easy to exploit, and almost every company that uses Java is affected. Attackers have launched mass scanners in the first 48 hours, while most organizations are struggling to find affected components in their IT landscape.
The good news: popular ecommerce platforms such as Magento are not written in Java and in itself are not vulnerable. However, your store may use Java-based components, so you should ensure to upgrade those as soon as possible, in particular:
Sansec has ran a global scan of all Magento stores and found a handful of stores that appeared susceptible to the basic attack method. However, this is not a safety guarantee for other stores, because:
To maximize visibility of any log4j fallout, we recommend to eComscan on your store. It will detect any vulnerable log4j versions in Java archives, and it should detect whether any malicious assets have been deployed already. Get a fully functioning trial with coupon SECURE2021 and run a scan within 5 minutes.
Believe you are under attack right now? Contact us!
Development agencies: do reach out if you want to do a mass rollout of security measures for all your customers.
Find and upgrade vulnerable log4j components to version 2.17 as quickly as possible. If that is somehow not possible, please see the other sections below for quick fixes.
To identify any Java based applications on your servers and see if they use the Log4j library, you can use the latest eComscan release. Run it like this:
ecomscan --key=LICENSE_KEY -m0 --maxsize=0 /path/to/java/application
If you find any vulnerable versions, chances are that attackers have already injected malware on your system. You should consider your system as compromised. Launch an incident response investigation, and use a server side malware scanner to find malicious files and processes.
Sansec has identified numerous attacks methods already. The primary vector is to install zombie agents on vulnerable systems. These agents (RATs) can be used at a later stage to install cryptominers, skimmers or ransomware. We will likely see a flood of hacked organizations in the coming weeks. Update Dec 14th: first cases of ransomware have been reported
If you cannot upgrade right away, early guides recommended to set the JVM flag log4j2.formatMsgNoLookups=true, but this does not protect against all attacks. You should implement it just in case, but do not rely on this.
Fastly has published a Varnish log4j ruleset that will block all requests that have ${ in incoming HTTP headers or POST data. This is very effective but also a very crude measure, as it may block regular (API) calls. We recommend to use these rules, if:
# Apache Log4j2 <=2.14.1 JNDI RCE - CVE-2021-44228
# This is a more strict sibling of https://fiddle.fastlydemo.net/fiddle/049ae446 , it will generate false positives.
if (
std.strstr(urldecode(req.body), "${")
|| std.strstr(urldecode(req.http.accept), "${")
|| std.strstr(urldecode(req.http.accept-additions), "${")
|| std.strstr(urldecode(req.http.accept-ch), "${")
|| std.strstr(urldecode(req.http.accept-charset), "${")
|| std.strstr(urldecode(req.http.accept-ch-lifetime), "${")
|| std.strstr(urldecode(req.http.accept-datetime), "${")
|| std.strstr(urldecode(req.http.accept-encoding), "${")
|| std.strstr(urldecode(req.http.accept-features), "${")
|| std.strstr(urldecode(req.http.accept-language), "${")
|| std.strstr(urldecode(req.http.accept-patch), "${")
|| std.strstr(urldecode(req.http.accept-post), "${")
|| std.strstr(urldecode(req.http.accept-ranges), "${")
|| std.strstr(urldecode(req.http.cache-control), "${")
|| std.strstr(urldecode(req.http.connection), "${")
|| std.strstr(urldecode(req.http.content-length), "${")
|| std.strstr(urldecode(req.http.content-range), "${")
|| std.strstr(urldecode(req.http.content-type), "${")
|| std.strstr(urldecode(req.http.cookie), "${")
|| std.strstr(urldecode(req.http.cookie2), "${")
|| std.strstr(urldecode(req.http.dnt), "${")
|| std.strstr(urldecode(req.http.if-modified-since), "${")
|| std.strstr(urldecode(req.http.if-none-match), "${")
|| std.strstr(urldecode(req.http.if-range), "${")
|| std.strstr(urldecode(req.http.range), "${")
|| std.strstr(urldecode(req.http.referer), "${")
|| std.strstr(urldecode(req.http.referer-root), "${")
|| std.strstr(urldecode(req.http.sec-fetch-dest), "${")
|| std.strstr(urldecode(req.http.sec-fetch-mode), "${")
|| std.strstr(urldecode(req.http.sec-fetch-site), "${")
|| std.strstr(urldecode(req.http.sec-websocket-accept), "${")
|| std.strstr(urldecode(req.http.set-cookie), "${")
|| std.strstr(urldecode(req.http.set-cookie2), "${")
|| std.strstr(urldecode(req.http.user-agent), "${")
|| std.strstr(urldecode(req.http.via), "${")
|| std.strstr(urldecode(req.http.x-content-type-options), "${")
|| std.strstr(urldecode(req.http.x-device-accept), "${")
|| std.strstr(urldecode(req.http.x-device-accept-charset), "${")
|| std.strstr(urldecode(req.http.x-device-accept-encoding), "${")
|| std.strstr(urldecode(req.http.x-device-accept-language), "${")
|| std.strstr(urldecode(req.http.x-device-user-agent), "${")
|| std.strstr(urldecode(req.http.x-forwarded-for), "${")
|| std.strstr(urldecode(req.http.x-forwarded-host), "${")
|| std.strstr(urldecode(req.http.x-forwarded-proto), "${")
|| std.strstr(urldecode(req.url), "${")
) {
error 403;
}
If you don't have Varnish but use the Nginx webserver, you can filter attack requests as well. However, you need to have the LUA scripting engine installed. Infiniroot shared a good example:
-- 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
此内容由惯性聚合(RSS阅读器)自动聚合整理,仅供阅读参考。 原文来自 — 版权归原作者所有。