Open
Description
I'm trying to catch CVE-2019-19775 with CodeQL. The flow is from the REQ
function called to create the default argument value, to the redirect function call:
@has_request_variables
def backend_serve_thumbnail(request: HttpRequest, user_profile: UserProfile,
url: str=REQ(), size_requested: str=REQ("size")) -> HttpResponse:
...
thumbnail_url = generate_thumbnail_url(url, size)
return redirect(thumbnail_url)
This is the code I've been using (yes I know I'm reinventing the wheel, but I wanted to make the example self contained and do some sanity checking):
import python
import semmle.python.security.TaintTracking
import semmle.python.web.HttpRequest
class ZulipReqSource extends TaintTracking::Source {
ZulipReqSource() {
exists( FunctionValue f | f.getName() = "REQ" and f.getACall() = this)
}
override predicate isSourceOf(TaintKind kind) { kind instanceof DjangoRequest }
override string toString() { result = "Zulip's custom 'Req' source" }
}
class RedirectSink extends TaintTracking::Sink {
RedirectSink() {
Module::named("django").attr("redirect").getACall().getArg(0) = this
}
override predicate sinks(TaintKind kind) {
kind instanceof DjangoRequest
}
override string toString() { result = "Django's redirect sink" }
}
class UrlRedirectConfiguration extends TaintTracking::Configuration {
UrlRedirectConfiguration() { this = "URL redirect configuration" }
override predicate isSource(TaintTracking::Source source) {
source instanceof ZulipReqSource
}
override predicate isSink(TaintTracking::Sink sink) {
sink instanceof RedirectSink
}
}
from UrlRedirectConfiguration config, TaintedPathSource src, TaintedPathSink sink
where config.hasFlowPath(src, sink)
select sink.getSink() , src, sink, "This argument to 'unsafe' depends on $@.", src.getSource(), "a user-provided value"
I can't seem to catch the flow when running on the Zulip database from lgtm.com. As best I can tell, I think taint flow through the defaulted parameter might not be being tracked properly. If I run the above code, but swap generate_thumbnail_url
for REQ
, it works and I am able to catch the flow from generate_thumbnail_url
-> redirect