diff --git a/go/ql/lib/ext/fmt.model.yml b/go/ql/lib/ext/fmt.model.yml index 5234b509933b..ff975cf423cd 100644 --- a/go/ql/lib/ext/fmt.model.yml +++ b/go/ql/lib/ext/fmt.model.yml @@ -1,4 +1,11 @@ extensions: + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["fmt", "", False, "Print", "", "", "Argument[0]", "log-injection", "manual"] + - ["fmt", "", False, "Printf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["fmt", "", False, "Println", "", "", "Argument[0]", "log-injection", "manual"] - addsTo: pack: codeql/go-all extensible: summaryModel diff --git a/go/ql/lib/ext/github.com.beego.beego.core.logs.model.yml b/go/ql/lib/ext/github.com.beego.beego.core.logs.model.yml new file mode 100644 index 000000000000..3dfbbe89719e --- /dev/null +++ b/go/ql/lib/ext/github.com.beego.beego.core.logs.model.yml @@ -0,0 +1,34 @@ +extensions: + - addsTo: + pack: codeql/go-all + extensible: packageGrouping + data: + - ["beego-logs", "github.com/astaxie/beego/logs"] + - ["beego-logs", "github.com/beego/beego/logs"] + - ["beego-logs", "github.com/beego/beego/core/logs"] + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["group:beego-logs", "", False, "Alert", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "", False, "Critical", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "", False, "Debug", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "", False, "Emergency", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "", False, "Error", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "", False, "Info", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "", False, "Informational", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "", False, "Notice", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "", False, "Trace", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "", False, "Warn", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "", False, "Warning", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "BeeLogger", False, "Alert", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "BeeLogger", False, "Critical", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "BeeLogger", False, "Debug", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "BeeLogger", False, "Emergency", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "BeeLogger", False, "Error", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "BeeLogger", False, "Info", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "BeeLogger", False, "Informational", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "BeeLogger", False, "Notice", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "BeeLogger", False, "Trace", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "BeeLogger", False, "Warn", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego-logs", "BeeLogger", False, "Warning", "", "", "Argument[0..1]", "log-injection", "manual"] diff --git a/go/ql/lib/ext/github.com.beego.beego.core.utils.model.yml b/go/ql/lib/ext/github.com.beego.beego.core.utils.model.yml index 4eb0688e37e7..63c05b920401 100644 --- a/go/ql/lib/ext/github.com.beego.beego.core.utils.model.yml +++ b/go/ql/lib/ext/github.com.beego.beego.core.utils.model.yml @@ -6,6 +6,11 @@ extensions: - ["beego-utils", "github.com/astaxie/beego/utils"] - ["beego-utils", "github.com/beego/beego/utils"] - ["beego-utils", "github.com/beego/beego/core/utils"] + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["group:beego-utils", "", False, "Display", "", "", "Argument[0]", "log-injection", "manual"] - addsTo: pack: codeql/go-all extensible: summaryModel diff --git a/go/ql/lib/ext/github.com.beego.beego.server.web.context.model.yml b/go/ql/lib/ext/github.com.beego.beego.server.web.context.model.yml index 89f8eeebfba4..6da9308208ca 100644 --- a/go/ql/lib/ext/github.com.beego.beego.server.web.context.model.yml +++ b/go/ql/lib/ext/github.com.beego.beego.server.web.context.model.yml @@ -6,6 +6,11 @@ extensions: - ["beego-context", "github.com/astaxie/beego/context"] - ["beego-context", "github.com/beego/beego/context"] - ["beego-context", "github.com/beego/beego/server/web/context"] + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["group:beego-context", "BeegoOutput", False, "Download", "", "", "Argument[0]", "path-injection", "manual"] - addsTo: pack: codeql/go-all extensible: summaryModel diff --git a/go/ql/lib/ext/github.com.beego.beego.server.web.model.yml b/go/ql/lib/ext/github.com.beego.beego.server.web.model.yml index ee14aa224d4f..d02fb628127f 100644 --- a/go/ql/lib/ext/github.com.beego.beego.server.web.model.yml +++ b/go/ql/lib/ext/github.com.beego.beego.server.web.model.yml @@ -6,6 +6,27 @@ extensions: - ["beego", "github.com/astaxie/beego"] - ["beego", "github.com/beego/beego"] - ["beego", "github.com/beego/beego/server/web"] + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + # log-injection + - ["group:beego", "", False, "Alert", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego", "", False, "Critical", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego", "", False, "Debug", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego", "", False, "Emergency", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego", "", False, "Error", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego", "", False, "Info", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego", "", False, "Informational", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego", "", False, "Notice", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego", "", False, "Trace", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego", "", False, "Warn", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:beego", "", False, "Warning", "", "", "Argument[0..1]", "log-injection", "manual"] + # path-injection + - ["group:beego", "", False, "Walk", "", "", "Argument[1]", "path-injection", "manual"] + - ["group:beego", "Controller", False, "SaveToFile", "", "", "Argument[1]", "path-injection", "manual"] + - ["group:beego", "Controller", False, "SaveToFileWithBuffer", "", "", "Argument[1]", "path-injection", "manual"] # only exists in v2 + - ["group:beego", "FileSystem", False, "Open", "", "", "Argument[0]", "path-injection", "manual"] - addsTo: pack: codeql/go-all extensible: summaryModel diff --git a/go/ql/lib/ext/github.com.codeskyblue.go-sh.model.yml b/go/ql/lib/ext/github.com.codeskyblue.go-sh.model.yml new file mode 100644 index 000000000000..d1e5c590af6c --- /dev/null +++ b/go/ql/lib/ext/github.com.codeskyblue.go-sh.model.yml @@ -0,0 +1,9 @@ +extensions: + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["github.com/codeskyblue/go-sh", "", False, "Command", "", "", "Argument[0]", "command-injection", "manual"] + - ["github.com/codeskyblue/go-sh", "Session", False, "Call", "", "", "Argument[0]", "command-injection", "manual"] + - ["github.com/codeskyblue/go-sh", "Session", False, "Command", "", "", "Argument[0]", "command-injection", "manual"] + - ["github.com/codeskyblue/go-sh", "Session", False, "Exec", "", "", "Argument[0]", "command-injection", "manual"] diff --git a/go/ql/lib/ext/github.com.davecgh.go-spew.spew.model.yml b/go/ql/lib/ext/github.com.davecgh.go-spew.spew.model.yml new file mode 100644 index 000000000000..4b4996926e31 --- /dev/null +++ b/go/ql/lib/ext/github.com.davecgh.go-spew.spew.model.yml @@ -0,0 +1,14 @@ +extensions: + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["github.com/davecgh/go-spew/spew", "", False, "Dump", "", "", "Argument[0]", "log-injection", "manual"] + - ["github.com/davecgh/go-spew/spew", "", False, "Errorf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["github.com/davecgh/go-spew/spew", "", False, "Fdump", "", "", "Argument[1]", "log-injection", "manual"] + - ["github.com/davecgh/go-spew/spew", "", False, "Fprint", "", "", "Argument[1]", "log-injection", "manual"] + - ["github.com/davecgh/go-spew/spew", "", False, "Fprintf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["github.com/davecgh/go-spew/spew", "", False, "Fprintln", "", "", "Argument[1]", "log-injection", "manual"] + - ["github.com/davecgh/go-spew/spew", "", False, "Print", "", "", "Argument[0]", "log-injection", "manual"] + - ["github.com/davecgh/go-spew/spew", "", False, "Printf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["github.com/davecgh/go-spew/spew", "", False, "Println", "", "", "Argument[0]", "log-injection", "manual"] diff --git a/go/ql/lib/ext/github.com.elazarl.goproxy.model.yml b/go/ql/lib/ext/github.com.elazarl.goproxy.model.yml index 20e4a26f1cdb..01a61d2c3acd 100644 --- a/go/ql/lib/ext/github.com.elazarl.goproxy.model.yml +++ b/go/ql/lib/ext/github.com.elazarl.goproxy.model.yml @@ -1,4 +1,10 @@ extensions: + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["github.com/elazarl/goproxy", "ProxyCtx", False, "Logf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["github.com/elazarl/goproxy", "ProxyCtx", False, "Warnf", "", "", "Argument[0..1]", "log-injection", "manual"] - addsTo: pack: codeql/go-all extensible: summaryModel diff --git a/go/ql/lib/ext/github.com.gin-gonic.gin.model.yml b/go/ql/lib/ext/github.com.gin-gonic.gin.model.yml index 22d81ce946b0..bd228fc0ec35 100644 --- a/go/ql/lib/ext/github.com.gin-gonic.gin.model.yml +++ b/go/ql/lib/ext/github.com.gin-gonic.gin.model.yml @@ -1,4 +1,11 @@ extensions: + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["github.com/gin-gonic/gin", "Context", False, "File", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/gin-gonic/gin", "Context", False, "FileAttachment", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/gin-gonic/gin", "Context", False, "SaveUploadedFile", "", "", "Argument[1]", "path-injection", "manual"] - addsTo: pack: codeql/go-all extensible: summaryModel diff --git a/go/ql/lib/ext/github.com.gofiber.fiber.model.yml b/go/ql/lib/ext/github.com.gofiber.fiber.model.yml new file mode 100644 index 000000000000..3a5c0ef56ae7 --- /dev/null +++ b/go/ql/lib/ext/github.com.gofiber.fiber.model.yml @@ -0,0 +1,9 @@ +extensions: + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["github.com/gofiber/fiber", "Ctx", False, "SendFile", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/gofiber/fiber", "Ctx", False, "Download", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/gofiber/fiber", "Ctx", False, "SaveFile", "", "", "Argument[1]", "path-injection", "manual"] + - ["github.com/gofiber/fiber", "Ctx", False, "SaveFileToStorage", "", "", "Argument[1]", "path-injection", "manual"] # does not exist in v1 diff --git a/go/ql/lib/ext/github.com.golang.glog.model.yml b/go/ql/lib/ext/github.com.golang.glog.model.yml new file mode 100644 index 000000000000..dd36e6a7d8fa --- /dev/null +++ b/go/ql/lib/ext/github.com.golang.glog.model.yml @@ -0,0 +1,102 @@ +extensions: + - addsTo: + pack: codeql/go-all + extensible: packageGrouping + data: + - ["glog", "github.com/golang/glog"] + - ["glog", "gopkg.in/glog"] + - ["glog", "k8s.io/klog"] + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["group:glog", "", False, "Error", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "", False, "ErrorContext", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "", False, "ErrorContextDepth", "", "", "Argument[2]", "log-injection", "manual"] + - ["group:glog", "", False, "ErrorContextDepthf", "", "", "Argument[2..3]", "log-injection", "manual"] + - ["group:glog", "", False, "ErrorContextf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "", False, "ErrorDepth", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "", False, "ErrorDepthf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "", False, "Errorf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:glog", "", False, "Errorln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "", False, "Exit", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "", False, "ExitContext", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "", False, "ExitContextDepth", "", "", "Argument[2]", "log-injection", "manual"] + - ["group:glog", "", False, "ExitContextDepthf", "", "", "Argument[2..3]", "log-injection", "manual"] + - ["group:glog", "", False, "ExitContextf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "", False, "ExitDepth", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "", False, "ExitDepthf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "", False, "Exitf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:glog", "", False, "Exitln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "", False, "Fatal", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "", False, "FatalContext", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "", False, "FatalContextDepth", "", "", "Argument[2]", "log-injection", "manual"] + - ["group:glog", "", False, "FatalContextDepthf", "", "", "Argument[2..3]", "log-injection", "manual"] + - ["group:glog", "", False, "FatalContextf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "", False, "FatalDepth", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "", False, "FatalDepthf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "", False, "Fatalf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:glog", "", False, "Fatalln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "", False, "Info", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "", False, "InfoContext", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "", False, "InfoContextDepth", "", "", "Argument[2]", "log-injection", "manual"] + - ["group:glog", "", False, "InfoContextDepthf", "", "", "Argument[2..3]", "log-injection", "manual"] + - ["group:glog", "", False, "InfoContextf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "", False, "InfoDepth", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "", False, "InfoDepthf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "", False, "Infof", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:glog", "", False, "Infoln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "", False, "Warning", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "", False, "WarningContext", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "", False, "WarningContextDepth", "", "", "Argument[2]", "log-injection", "manual"] + - ["group:glog", "", False, "WarningContextDepthf", "", "", "Argument[2..3]", "log-injection", "manual"] + - ["group:glog", "", False, "WarningContextf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "", False, "WarningDepth", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "", False, "WarningDepthf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "", False, "Warningf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:glog", "", False, "Warningln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "Error", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "ErrorContext", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "ErrorContextDepth", "", "", "Argument[2]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "ErrorContextDepthf", "", "", "Argument[2..3]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "ErrorContextf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "ErrorDepth", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "ErrorDepthf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "Errorf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "Errorln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "Exit", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "ExitContext", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "ExitContextDepth", "", "", "Argument[2]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "ExitContextDepthf", "", "", "Argument[2..3]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "ExitContextf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "ExitDepth", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "ExitDepthf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "Exitf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "Exitln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "Fatal", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "FatalContext", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "FatalContextDepth", "", "", "Argument[2]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "FatalContextDepthf", "", "", "Argument[2..3]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "FatalContextf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "FatalDepth", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "FatalDepthf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "Fatalf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "Fatalln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "Info", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "InfoContext", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "InfoContextDepth", "", "", "Argument[2]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "InfoContextDepthf", "", "", "Argument[2..3]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "InfoContextf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "InfoDepth", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "InfoDepthf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "Infof", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "Infoln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "Warning", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "WarningContext", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "WarningContextDepth", "", "", "Argument[2]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "WarningContextDepthf", "", "", "Argument[2..3]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "WarningContextf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "WarningDepth", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "WarningDepthf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "Warningf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:glog", "Verbose", False, "Warningln", "", "", "Argument[0]", "log-injection", "manual"] diff --git a/go/ql/lib/ext/github.com.kataras.iris.context.model.yml b/go/ql/lib/ext/github.com.kataras.iris.context.model.yml new file mode 100644 index 000000000000..5b5b7e793e2e --- /dev/null +++ b/go/ql/lib/ext/github.com.kataras.iris.context.model.yml @@ -0,0 +1,17 @@ +extensions: + - addsTo: + pack: codeql/go-all + extensible: packageGrouping + data: + - ["iris-context", "github.com/kataras/iris/context"] + - ["iris-context", "github.com/kataras/iris/server/web/context"] + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["group:iris-context", "Context", True, "SendFile", "", "", "Argument[0]", "path-injection", "manual"] + - ["group:iris-context", "Context", True, "ServeFile", "", "", "Argument[0]", "path-injection", "manual"] + - ["group:iris-context", "Context", True, "SendFileWithRate", "", "", "Argument[0]", "path-injection", "manual"] + - ["group:iris-context", "Context", True, "ServeFileWithRate", "", "", "Argument[0]", "path-injection", "manual"] + - ["group:iris-context", "Context", True, "UploadFormFiles", "", "", "Argument[0]", "path-injection", "manual"] + - ["group:iris-context", "Context", True, "SaveFormFile", "", "", "Argument[1]", "path-injection", "manual"] diff --git a/go/ql/lib/ext/github.com.labstack.echo.model.yml b/go/ql/lib/ext/github.com.labstack.echo.model.yml index 21e637a3b65b..48e5ccd33b58 100644 --- a/go/ql/lib/ext/github.com.labstack.echo.model.yml +++ b/go/ql/lib/ext/github.com.labstack.echo.model.yml @@ -1,4 +1,10 @@ extensions: + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["github.com/labstack/echo", "Context", False, "Attachment", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/labstack/echo", "Context", False, "File", "", "", "Argument[0]", "path-injection", "manual"] - addsTo: pack: codeql/go-all extensible: summaryModel diff --git a/go/ql/lib/ext/github.com.revel.revel.model.yml b/go/ql/lib/ext/github.com.revel.revel.model.yml index e5907088dff1..41b5397466cf 100644 --- a/go/ql/lib/ext/github.com.revel.revel.model.yml +++ b/go/ql/lib/ext/github.com.revel.revel.model.yml @@ -32,6 +32,11 @@ extensions: - ["group:revel", "Request", True, "UserAgent", "", "", "ReturnValue", "remote", "manual"] - ["group:revel", "ServerWebSocket", True, "MessageReceive", "", "", "Argument[0]", "remote", "manual"] - ["group:revel", "ServerWebSocket", True, "MessageReceiveJSON", "", "", "Argument[0]", "remote", "manual"] + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["group:revel", "Controller", True, "RenderFileName", "", "", "Argument[0]", "path-injection", "manual"] # we model this as a path-injection sink rather than extending HTTP::ResponseBody as this will usually mean exposing a user-controlled file rather than the actual contents being user-controlled. - addsTo: pack: codeql/go-all extensible: summaryModel diff --git a/go/ql/lib/ext/github.com.sirupsen.logrus.model.yml b/go/ql/lib/ext/github.com.sirupsen.logrus.model.yml new file mode 100644 index 000000000000..54f802e02413 --- /dev/null +++ b/go/ql/lib/ext/github.com.sirupsen.logrus.model.yml @@ -0,0 +1,131 @@ +extensions: + - addsTo: + pack: codeql/go-all + extensible: packageGrouping + data: + - ["logrus", "github.com/sirupsen/logrus"] + - ["logrus", "github.com/Sirupsen/logrus"] + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["group:logrus", "", False, "Debug", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "DebugFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Debugf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "", False, "Debugln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Error", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "ErrorFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Errorf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "", False, "Errorln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Fatal", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "FatalFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Fatalf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "", False, "Fatalln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Info", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "InfoFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Infof", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "", False, "Infoln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Panic", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "PanicFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Panicf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "", False, "Panicln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Print", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "PrintFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Printf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "", False, "Println", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Trace", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "TraceFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Tracef", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "", False, "Traceln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Warn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "WarnFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Warnf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "", False, "Warnln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Warning", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "WarningFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "Warningf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "", False, "Warningln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "WithError", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "WithField", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "", False, "WithFields", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "", False, "WithTime", "", "", "Argument[0]", "log-injection", "manual"] + + - ["group:logrus", "Entry", False, "Debug", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Debugf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Debugln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Error", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Errorf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Errorln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Fatal", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Fatalf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Fatalln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Info", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Infof", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Infoln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Log", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Logf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Logln", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Panic", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Panicf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Panicln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Print", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Printf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Println", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Trace", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Tracef", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Traceln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Warn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Warnf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Warnln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Warning", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Warningf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "Warningln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "WithError", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "WithField", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "WithFields", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Entry", False, "WithTime", "", "", "Argument[0]", "log-injection", "manual"] + + - ["group:logrus", "Logger", False, "Debug", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "DebugFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Debugf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Debugln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Error", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "ErrorFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Errorf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Errorln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Fatal", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "FatalFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Fatalf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Fatalln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Info", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "InfoFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Infof", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Infoln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Log", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "LogFn", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Logf", "", "", "Argument[1..2]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Logln", "", "", "Argument[1]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Panic", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "PanicFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Panicf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Panicln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Print", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "PrintFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Printf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Println", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Trace", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "TraceFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Tracef", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Traceln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Warn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "WarnFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Warnf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Warnln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Warning", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "WarningFn", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Warningf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "Warningln", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "WithError", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "WithField", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "WithFields", "", "", "Argument[0]", "log-injection", "manual"] + - ["group:logrus", "Logger", False, "WithTime", "", "", "Argument[0]", "log-injection", "manual"] diff --git a/go/ql/lib/ext/github.com.spf13.afero.model.yml b/go/ql/lib/ext/github.com.spf13.afero.model.yml new file mode 100644 index 000000000000..94879539233d --- /dev/null +++ b/go/ql/lib/ext/github.com.spf13.afero.model.yml @@ -0,0 +1,39 @@ +extensions: + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["github.com/spf13/afero", "HttpFs", False, "Create", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "HttpFs", False, "Open", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "HttpFs", False, "OpenFile", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "HttpFs", False, "Remove", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "HttpFs", False, "RemoveAll", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "MemMapFs", False, "Create", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "MemMapFs", False, "Open", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "MemMapFs", False, "OpenFile", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "MemMapFs", False, "Remove", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "MemMapFs", False, "RemoveAll", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "MemMapFs", False, "Mkdir", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "MemMapFs", False, "MkdirAll", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "OsFs", False, "Create", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "OsFs", False, "Open", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "OsFs", False, "OpenFile", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "OsFs", False, "ReadlinkIfPossible", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "OsFs", False, "Remove", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "OsFs", False, "RemoveAll", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "OsFs", False, "Mkdir", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "OsFs", False, "MkdirAll", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "ReadOnlyFs", False, "Create", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "ReadOnlyFs", False, "Open", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "ReadOnlyFs", False, "OpenFile", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "ReadOnlyFs", False, "ReadDir", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "ReadOnlyFs", False, "ReadlinkIfPossible", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "ReadOnlyFs", False, "Mkdir", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "ReadOnlyFs", False, "MkdirAll", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "RegexpFs", False, "Create", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "RegexpFs", False, "Open", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "RegexpFs", False, "OpenFile", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "RegexpFs", False, "Remove", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "RegexpFs", False, "RemoveAll", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "RegexpFs", False, "Mkdir", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/spf13/afero", "RegexpFs", False, "MkdirAll", "", "", "Argument[0]", "path-injection", "manual"] diff --git a/go/ql/lib/ext/github.com.valyala.fasthttp.model.yml b/go/ql/lib/ext/github.com.valyala.fasthttp.model.yml index 7faa69493d4d..ea6c117f8539 100644 --- a/go/ql/lib/ext/github.com.valyala.fasthttp.model.yml +++ b/go/ql/lib/ext/github.com.valyala.fasthttp.model.yml @@ -3,6 +3,7 @@ extensions: pack: codeql/go-all extensible: sinkModel data: + # request-forgery - ["github.com/valyala/fasthttp", "", True, "Get", "", "", "Argument[1]", "request-forgery", "manual"] - ["github.com/valyala/fasthttp", "", True, "GetDeadline", "", "", "Argument[1]", "request-forgery", "manual"] - ["github.com/valyala/fasthttp", "", True, "GetTimeout", "", "", "Argument[1]", "request-forgery", "manual"] @@ -28,6 +29,15 @@ extensions: - ["github.com/valyala/fasthttp", "TCPDialer", True, "DialDualStack", "", "", "Argument[0]", "request-forgery[TCP Addr + Port]", "manual"] - ["github.com/valyala/fasthttp", "TCPDialer", True, "DialDualStackTimeout", "", "", "Argument[0]", "request-forgery[TCP Addr + Port]", "manual"] - ["github.com/valyala/fasthttp", "TCPDialer", True, "DialTimeout", "", "", "Argument[0]", "request-forgery[TCP Addr + Port]", "manual"] + # path-injection + - ["github.com/valyala/fasthttp", "", False, "SaveMultipartFile", "", "", "Argument[1]", "path-injection", "manual"] + - ["github.com/valyala/fasthttp", "", False, "ServeFile", "", "", "Argument[1]", "path-injection", "manual"] + - ["github.com/valyala/fasthttp", "", False, "ServeFileBytes", "", "", "Argument[1]", "path-injection", "manual"] + - ["github.com/valyala/fasthttp", "", False, "ServeFileBytesUncompressed", "", "", "Argument[1]", "path-injection", "manual"] + - ["github.com/valyala/fasthttp", "", False, "ServeFileUncompressed", "", "", "Argument[1]", "path-injection", "manual"] + - ["github.com/valyala/fasthttp", "RequestCtx", False, "SendFile", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/valyala/fasthttp", "RequestCtx", False, "SendFileBytes", "", "", "Argument[0]", "path-injection", "manual"] + - ["github.com/valyala/fasthttp", "Response", False, "SendFile", "", "", "Argument[0]", "path-injection", "manual"] - addsTo: pack: codeql/go-all extensible: summaryModel diff --git a/go/ql/lib/ext/go.uber.org.zap.model.yml b/go/ql/lib/ext/go.uber.org.zap.model.yml index 2ca7f7e8a804..c4e43356f269 100644 --- a/go/ql/lib/ext/go.uber.org.zap.model.yml +++ b/go/ql/lib/ext/go.uber.org.zap.model.yml @@ -1,4 +1,41 @@ extensions: + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["go.uber.org/zap", "Logger", False, "DPanic", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "Logger", False, "Debug", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "Logger", False, "Error", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "Logger", False, "Fatal", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "Logger", False, "Info", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "Logger", False, "Named", "", "", "Argument[0]", "log-injection", "manual"] + - ["go.uber.org/zap", "Logger", False, "Panic", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "Logger", False, "Warn", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "Logger", False, "With", "", "", "Argument[0]", "log-injection", "manual"] + - ["go.uber.org/zap", "Logger", False, "WithOptions", "", "", "Argument[0]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "DPanic", "", "", "Argument[0]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "DPanicf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "DPanicw", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Debug", "", "", "Argument[0]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Debugf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Debugw", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Error", "", "", "Argument[0]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Errorf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Errorw", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Fatal", "", "", "Argument[0]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Fatalf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Fatalw", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Info", "", "", "Argument[0]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Infof", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Infow", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Named", "", "", "Argument[0]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Panic", "", "", "Argument[0]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Panicf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Panicw", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Warn", "", "", "Argument[0]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Warnf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "Warnw", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["go.uber.org/zap", "SugaredLogger", False, "With", "", "", "Argument[0]", "log-injection", "manual"] - addsTo: pack: codeql/go-all extensible: summaryModel diff --git a/go/ql/lib/ext/golang.org.x.crypto.ssh.model.yml b/go/ql/lib/ext/golang.org.x.crypto.ssh.model.yml new file mode 100644 index 000000000000..8419737a2f2d --- /dev/null +++ b/go/ql/lib/ext/golang.org.x.crypto.ssh.model.yml @@ -0,0 +1,9 @@ +extensions: + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["golang.org/x/crypto/ssh", "Session", False, "CombinedOutput", "", "", "Argument[0]", "command-injection", "manual"] + - ["golang.org/x/crypto/ssh", "Session", False, "Output", "", "", "Argument[0]", "command-injection", "manual"] + - ["golang.org/x/crypto/ssh", "Session", False, "Run", "", "", "Argument[0]", "command-injection", "manual"] + - ["golang.org/x/crypto/ssh", "Session", False, "Start", "", "", "Argument[0]", "command-injection", "manual"] diff --git a/go/ql/lib/ext/io.ioutil.model.yml b/go/ql/lib/ext/io.ioutil.model.yml index c3182daf36d0..f5fd2ea0fb4a 100644 --- a/go/ql/lib/ext/io.ioutil.model.yml +++ b/go/ql/lib/ext/io.ioutil.model.yml @@ -1,4 +1,13 @@ extensions: + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["io/ioutil", "", False, "ReadDir", "", "", "Argument[0]", "path-injection", "manual"] + - ["io/ioutil", "", False, "ReadFile", "", "", "Argument[0]", "path-injection", "manual"] + - ["io/ioutil", "", False, "TempDir", "", "", "Argument[0..1]", "path-injection", "manual"] + - ["io/ioutil", "", False, "TempFile", "", "", "Argument[0..1]", "path-injection", "manual"] + - ["io/ioutil", "", False, "WriteFile", "", "", "Argument[0]", "path-injection", "manual"] - addsTo: pack: codeql/go-all extensible: summaryModel diff --git a/go/ql/lib/ext/log.model.yml b/go/ql/lib/ext/log.model.yml index 7f52a1733073..1ebce079a52f 100644 --- a/go/ql/lib/ext/log.model.yml +++ b/go/ql/lib/ext/log.model.yml @@ -1,4 +1,28 @@ extensions: + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["log", "", False, "Fatal", "", "", "Argument[0]", "log-injection", "manual"] + - ["log", "", False, "Fatalf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["log", "", False, "Fatalln", "", "", "Argument[0]", "log-injection", "manual"] + - ["log", "", False, "Output", "", "", "Argument[1]", "log-injection", "manual"] + - ["log", "", False, "Panic", "", "", "Argument[0]", "log-injection", "manual"] + - ["log", "", False, "Panicf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["log", "", False, "Panicln", "", "", "Argument[0]", "log-injection", "manual"] + - ["log", "", False, "Print", "", "", "Argument[0]", "log-injection", "manual"] + - ["log", "", False, "Printf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["log", "", False, "Println", "", "", "Argument[0]", "log-injection", "manual"] + - ["log", "Logger", False, "Fatal", "", "", "Argument[0]", "log-injection", "manual"] + - ["log", "Logger", False, "Fatalf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["log", "Logger", False, "Fatalln", "", "", "Argument[0]", "log-injection", "manual"] + - ["log", "Logger", False, "Output", "", "", "Argument[1]", "log-injection", "manual"] + - ["log", "Logger", False, "Panic", "", "", "Argument[0]", "log-injection", "manual"] + - ["log", "Logger", False, "Panicf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["log", "Logger", False, "Panicln", "", "", "Argument[0]", "log-injection", "manual"] + - ["log", "Logger", False, "Print", "", "", "Argument[0]", "log-injection", "manual"] + - ["log", "Logger", False, "Printf", "", "", "Argument[0..1]", "log-injection", "manual"] + - ["log", "Logger", False, "Println", "", "", "Argument[0]", "log-injection", "manual"] - addsTo: pack: codeql/go-all extensible: summaryModel diff --git a/go/ql/lib/ext/net.http.model.yml b/go/ql/lib/ext/net.http.model.yml index ce543583700c..931c56db8048 100644 --- a/go/ql/lib/ext/net.http.model.yml +++ b/go/ql/lib/ext/net.http.model.yml @@ -1,4 +1,9 @@ extensions: + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["net/http", "", False, "ServeFile", "", "", "Argument[2]", "path-injection", "manual"] - addsTo: pack: codeql/go-all extensible: summaryModel diff --git a/go/ql/lib/ext/os.exec.model.yml b/go/ql/lib/ext/os.exec.model.yml new file mode 100644 index 000000000000..6b3a80c372c3 --- /dev/null +++ b/go/ql/lib/ext/os.exec.model.yml @@ -0,0 +1,7 @@ +extensions: + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["os/exec", "", False, "Command", "", "", "Argument[0]", "command-injection", "manual"] + - ["os/exec", "", False, "CommandContext", "", "", "Argument[1]", "command-injection", "manual"] diff --git a/go/ql/lib/ext/os.model.yml b/go/ql/lib/ext/os.model.yml index b0314dc71ed4..11a28a0d1fc4 100644 --- a/go/ql/lib/ext/os.model.yml +++ b/go/ql/lib/ext/os.model.yml @@ -1,4 +1,37 @@ extensions: + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + # path-injection + - ["os", "", False, "Chdir", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "Chmod", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "Chown", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "Chtimes", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "Create", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "Lchown", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "Link", "", "", "Argument[0..1]", "path-injection", "manual"] + - ["os", "", False, "Lstat", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "Mkdir", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "MkdirAll", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "NewFile", "", "", "Argument[1]", "path-injection", "manual"] + - ["os", "", False, "Open", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "OpenFile", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "Readlink", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "Remove", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "RemoveAll", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "Rename", "", "", "Argument[0..1]", "path-injection", "manual"] + - ["os", "", False, "Stat", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "Symlink", "", "", "Argument[0..1]", "path-injection", "manual"] + - ["os", "", False, "Truncate", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "DirFS", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "ReadDir", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "ReadFile", "", "", "Argument[0]", "path-injection", "manual"] + - ["os", "", False, "MkdirTemp", "", "", "Argument[0..1]", "path-injection", "manual"] + - ["os", "", False, "CreateTemp", "", "", "Argument[0..1]", "path-injection", "manual"] + - ["os", "", False, "WriteFile", "", "", "Argument[0]", "path-injection", "manual"] + # command-injection + - ["os", "", False, "StartProcess", "", "", "Argument[0]", "command-injection", "manual"] - addsTo: pack: codeql/go-all extensible: summaryModel diff --git a/go/ql/lib/ext/syscall.model.yml b/go/ql/lib/ext/syscall.model.yml index f22167d41d87..14ddd68b4021 100644 --- a/go/ql/lib/ext/syscall.model.yml +++ b/go/ql/lib/ext/syscall.model.yml @@ -1,4 +1,13 @@ extensions: + - addsTo: + pack: codeql/go-all + extensible: sinkModel + data: + - ["syscall", "", False, "Exec", "", "", "Argument[0]", "command-injection", "manual"] + - ["syscall", "", False, "ForkExec", "", "", "Argument[0]", "command-injection", "manual"] + - ["syscall", "", False, "StartProcess", "", "", "Argument[0]", "command-injection", "manual"] + - ["syscall", "", False, "CreateProcess", "", "", "Argument[0]", "command-injection", "manual"] + - ["syscall", "", False, "CreateProcessAsUser", "", "", "Argument[1]", "command-injection", "manual"] - addsTo: pack: codeql/go-all extensible: summaryModel diff --git a/go/ql/lib/go.qll b/go/ql/lib/go.qll index 42da6af149ae..fb59790dcc53 100644 --- a/go/ql/lib/go.qll +++ b/go/ql/lib/go.qll @@ -40,15 +40,12 @@ import semmle.go.frameworks.ElazarlGoproxy import semmle.go.frameworks.Email import semmle.go.frameworks.Encoding import semmle.go.frameworks.Fasthttp -import semmle.go.frameworks.Fiber -import semmle.go.frameworks.Gin import semmle.go.frameworks.GinCors import semmle.go.frameworks.Glog import semmle.go.frameworks.GoJose import semmle.go.frameworks.GoKit import semmle.go.frameworks.GoMicro import semmle.go.frameworks.Gqlgen -import semmle.go.frameworks.Iris import semmle.go.frameworks.Jwt import semmle.go.frameworks.K8sIoApimachineryPkgRuntime import semmle.go.frameworks.K8sIoApiCoreV1 diff --git a/go/ql/lib/semmle/go/Concepts.qll b/go/ql/lib/semmle/go/Concepts.qll index 2fb4e35d94b2..bb9ca12d0f71 100644 --- a/go/ql/lib/semmle/go/Concepts.qll +++ b/go/ql/lib/semmle/go/Concepts.qll @@ -112,6 +112,23 @@ module FileSystemAccess { } } +private class DefaultFileSystemAccess extends FileSystemAccess::Range, DataFlow::CallNode { + DataFlow::ArgumentNode pathArgument; + + DefaultFileSystemAccess() { + sinkNode(pathArgument, "path-injection") and + this = pathArgument.getCall() + } + + override DataFlow::Node getAPathArgument() { + not pathArgument instanceof DataFlow::ImplicitVarargsSlice and + result = pathArgument + or + pathArgument instanceof DataFlow::ImplicitVarargsSlice and + result = this.getAnImplicitVarargsArgument() + } +} + /** A function that escapes meta-characters to prevent injection attacks. */ class EscapeFunction extends Function instanceof EscapeFunction::Range { /** @@ -360,6 +377,23 @@ module LoggerCall { } } +private class DefaultLoggerCall extends LoggerCall::Range, DataFlow::CallNode { + DataFlow::ArgumentNode messageComponent; + + DefaultLoggerCall() { + sinkNode(messageComponent, "log-injection") and + this = messageComponent.getCall() + } + + override DataFlow::Node getAMessageComponent() { + not messageComponent instanceof DataFlow::ImplicitVarargsSlice and + result = messageComponent + or + messageComponent instanceof DataFlow::ImplicitVarargsSlice and + result = this.getAnImplicitVarargsArgument() + } +} + /** * A function that encodes data into a binary or textual format. * diff --git a/go/ql/lib/semmle/go/frameworks/Afero.qll b/go/ql/lib/semmle/go/frameworks/Afero.qll index 52d488bff093..598036de22bc 100644 --- a/go/ql/lib/semmle/go/frameworks/Afero.qll +++ b/go/ql/lib/semmle/go/frameworks/Afero.qll @@ -15,9 +15,11 @@ module Afero { string aferoPackage() { result = package("github.com/spf13/afero", "") } /** + * DEPRECATED: Use `FileSystemAccess::Range` instead. + * * The File system access sinks of [afero](https://github.com/spf13/afero) framework methods */ - class AferoSystemAccess extends FileSystemAccess::Range, DataFlow::CallNode { + deprecated class AferoSystemAccess extends FileSystemAccess::Range, DataFlow::CallNode { AferoSystemAccess() { exists(Method m | m.hasQualifiedName(aferoPackage(), "HttpFs", diff --git a/go/ql/lib/semmle/go/frameworks/Beego.qll b/go/ql/lib/semmle/go/frameworks/Beego.qll index 20e26eb01889..7a16e0911516 100644 --- a/go/ql/lib/semmle/go/frameworks/Beego.qll +++ b/go/ql/lib/semmle/go/frameworks/Beego.qll @@ -33,13 +33,6 @@ module Beego { result = package(v2modulePath(), "server/web/context") } - /** Gets the path for the logs package of beego. */ - string logsPackagePath() { - result = package(v1modulePath(), "logs") - or - result = package(v2modulePath(), "core/logs") - } - /** Gets the path for the utils package of beego. */ string utilsPackagePath() { result = package(v1modulePath(), "utils") @@ -172,36 +165,6 @@ module Beego { override string getAContentType() { none() } } - private string getALogFunctionName() { - result = - [ - "Alert", "Critical", "Debug", "Emergency", "Error", "Info", "Informational", "Notice", - "Trace", "Warn", "Warning" - ] - } - - private class ToplevelBeegoLoggers extends LoggerCall::Range, DataFlow::CallNode { - ToplevelBeegoLoggers() { - this.getTarget().hasQualifiedName([packagePath(), logsPackagePath()], getALogFunctionName()) - } - - override DataFlow::Node getAMessageComponent() { result = this.getASyntacticArgument() } - } - - private class BeegoLoggerMethods extends LoggerCall::Range, DataFlow::MethodCallNode { - BeegoLoggerMethods() { - this.getTarget().hasQualifiedName(logsPackagePath(), "BeeLogger", getALogFunctionName()) - } - - override DataFlow::Node getAMessageComponent() { result = this.getASyntacticArgument() } - } - - private class UtilLoggers extends LoggerCall::Range, DataFlow::CallNode { - UtilLoggers() { this.getTarget().hasQualifiedName(utilsPackagePath(), "Display") } - - override DataFlow::Node getAMessageComponent() { result = this.getASyntacticArgument() } - } - private class HtmlQuoteSanitizer extends SharedXss::Sanitizer { HtmlQuoteSanitizer() { exists(DataFlow::CallNode c | c.getTarget().hasQualifiedName(packagePath(), "Htmlquote") | @@ -210,33 +173,6 @@ module Beego { } } - /** - * The File system access sinks - */ - private class FsOperations extends FileSystemAccess::Range, DataFlow::CallNode { - int pathArg; - - FsOperations() { - this.getTarget().hasQualifiedName(packagePath(), "Walk") and pathArg = 1 - or - exists(Method m | this = m.getACall() | - m.hasQualifiedName(packagePath(), "FileSystem", "Open") and pathArg = 0 - or - m.hasQualifiedName(packagePath(), "Controller", "SaveToFile") and pathArg = 1 - or - m.hasQualifiedName(contextPackagePath(), "BeegoOutput", "Download") and - pathArg = 0 - or - // SaveToFileWithBuffer only available in v2 - m.hasQualifiedName("github.com/beego/beego/v2/server/web", "Controller", - "SaveToFileWithBuffer") and - pathArg = 1 - ) - } - - override DataFlow::Node getAPathArgument() { result = this.getArgument(pathArg) } - } - private class RedirectMethods extends Http::Redirect::Range, DataFlow::CallNode { string className; diff --git a/go/ql/lib/semmle/go/frameworks/Echo.qll b/go/ql/lib/semmle/go/frameworks/Echo.qll index 440d2effd5c5..4c05f0fd6927 100644 --- a/go/ql/lib/semmle/go/frameworks/Echo.qll +++ b/go/ql/lib/semmle/go/frameworks/Echo.qll @@ -70,9 +70,11 @@ private module Echo { } /** + * DEPRECATED: Use `FileSystemAccess::Range` instead. + * * The File system access sinks */ - class FsOperations extends FileSystemAccess::Range, DataFlow::CallNode { + deprecated class FsOperations extends FileSystemAccess::Range, DataFlow::CallNode { FsOperations() { exists(Method m | m.hasQualifiedName(packagePath(), "Context", ["Attachment", "File"]) and diff --git a/go/ql/lib/semmle/go/frameworks/ElazarlGoproxy.qll b/go/ql/lib/semmle/go/frameworks/ElazarlGoproxy.qll index 4d10c8af312d..b1bf4571216a 100644 --- a/go/ql/lib/semmle/go/frameworks/ElazarlGoproxy.qll +++ b/go/ql/lib/semmle/go/frameworks/ElazarlGoproxy.qll @@ -100,10 +100,4 @@ module ElazarlGoproxy { override int getFormatStringIndex() { result = 0 } } - - private class ProxyLog extends LoggerCall::Range, DataFlow::MethodCallNode { - ProxyLog() { this.getTarget() instanceof ProxyLogFunction } - - override DataFlow::Node getAMessageComponent() { result = this.getASyntacticArgument() } - } } diff --git a/go/ql/lib/semmle/go/frameworks/Fasthttp.qll b/go/ql/lib/semmle/go/frameworks/Fasthttp.qll index e0ec0293ef2a..8ac4f709fa2d 100644 --- a/go/ql/lib/semmle/go/frameworks/Fasthttp.qll +++ b/go/ql/lib/semmle/go/frameworks/Fasthttp.qll @@ -175,9 +175,11 @@ module Fasthttp { */ module Functions { /** + * DEPRECATED: Use `FileSystemAccess::Range` instead. + * * A function that doesn't sanitize user-provided file paths. */ - class FileSystemAccess extends FileSystemAccess::Range, DataFlow::CallNode { + deprecated class FileSystemAccess extends FileSystemAccess::Range, DataFlow::CallNode { FileSystemAccess() { exists(Function f | f.hasQualifiedName(packagePath(), @@ -399,12 +401,14 @@ module Fasthttp { /** * Provide modeling for fasthttp.Response Type. */ - module Response { + deprecated module Response { /** + * DEPRECATED: Use `FileSystemAccess::Range` instead. + * * A Method that sends files from its input. * It does not check the input path against path traversal attacks, So it is a dangerous method. */ - class FileSystemAccess extends FileSystemAccess::Range, DataFlow::CallNode { + deprecated class FileSystemAccess extends FileSystemAccess::Range, DataFlow::CallNode { FileSystemAccess() { exists(Method mcn | mcn.hasQualifiedName(packagePath(), "Response", "SendFile") and @@ -477,9 +481,11 @@ module Fasthttp { */ module RequestCtx { /** + * DEPRECATED: Use `FileSystemAccess::Range` instead. + * * The Methods that don't sanitize user provided file paths. */ - class FileSystemAccess extends FileSystemAccess::Range, DataFlow::CallNode { + deprecated class FileSystemAccess extends FileSystemAccess::Range, DataFlow::CallNode { FileSystemAccess() { exists(Method mcn | mcn.hasQualifiedName(packagePath(), "RequestCtx", ["SendFile", "SendFileBytes"]) and diff --git a/go/ql/lib/semmle/go/frameworks/Fiber.qll b/go/ql/lib/semmle/go/frameworks/Fiber.qll deleted file mode 100644 index 38dd2ca7df12..000000000000 --- a/go/ql/lib/semmle/go/frameworks/Fiber.qll +++ /dev/null @@ -1,38 +0,0 @@ -/** - * Provides classes for working the `github.com/gofiber/fiber` package. - */ - -import go - -private module Fiber { - /** Gets the package name `github.com/gofiber/fiber`. */ - string packagePath() { result = package("github.com/gofiber/fiber", "") } - - /** Gets the v2 module path `github.com/gofiber/fiber/v2` */ - string v2modulePath() { result = "github.com/gofiber/fiber/v2" } - - /** - * The File system access sinks - */ - class FsOperations extends FileSystemAccess::Range, DataFlow::CallNode { - int pathArg; - - FsOperations() { - exists(Method m | - ( - m.hasQualifiedName(packagePath(), "Ctx", ["SendFile", "Download"]) and - pathArg = 0 - or - m.hasQualifiedName(packagePath(), "Ctx", "SaveFile") and - pathArg = 1 - or - m.hasQualifiedName(v2modulePath(), "Ctx", "SaveFileToStorage") and - pathArg = 1 - ) and - this = m.getACall() - ) - } - - override DataFlow::Node getAPathArgument() { result = this.getArgument(pathArg) } - } -} diff --git a/go/ql/lib/semmle/go/frameworks/Gin.qll b/go/ql/lib/semmle/go/frameworks/Gin.qll deleted file mode 100644 index e91ef2565d05..000000000000 --- a/go/ql/lib/semmle/go/frameworks/Gin.qll +++ /dev/null @@ -1,32 +0,0 @@ -/** - * Provides classes for working with the `github.com/gin-gonic/gin` package. - */ - -import go - -private module Gin { - /** Gets the package name `github.com/gin-gonic/gin`. */ - string packagePath() { result = package("github.com/gin-gonic/gin", "") } - - /** - * The File system access sinks - */ - class FsOperations extends FileSystemAccess::Range, DataFlow::CallNode { - int pathArg; - - FsOperations() { - exists(Method m | - ( - m.hasQualifiedName(packagePath(), "Context", ["File", "FileAttachment"]) and - pathArg = 0 - or - m.hasQualifiedName(packagePath(), "Context", "SaveUploadedFile") and - pathArg = 1 - ) and - this = m.getACall() - ) - } - - override DataFlow::Node getAPathArgument() { result = this.getArgument(pathArg) } - } -} diff --git a/go/ql/lib/semmle/go/frameworks/Glog.qll b/go/ql/lib/semmle/go/frameworks/Glog.qll index f9f5c9e3f11f..146b8a4f814b 100644 --- a/go/ql/lib/semmle/go/frameworks/Glog.qll +++ b/go/ql/lib/semmle/go/frameworks/Glog.qll @@ -40,14 +40,4 @@ module Glog { override int getFormatStringIndex() { result = super.getFirstPrintedArg() } } - - private class GlogCall extends LoggerCall::Range, DataFlow::CallNode { - GlogFunction callee; - - GlogCall() { this = callee.getACall() } - - override DataFlow::Node getAMessageComponent() { - result = this.getSyntacticArgument(any(int i | i >= callee.getFirstPrintedArg())) - } - } } diff --git a/go/ql/lib/semmle/go/frameworks/Iris.qll b/go/ql/lib/semmle/go/frameworks/Iris.qll deleted file mode 100644 index bb965769d5c4..000000000000 --- a/go/ql/lib/semmle/go/frameworks/Iris.qll +++ /dev/null @@ -1,49 +0,0 @@ -/** - * Provides classes for working the `github.com/kataras/iris` package. - */ - -import go - -private module Iris { - /** Gets the v1 module path `github.com/kataras/iris`. */ - string v1modulePath() { result = "github.com/kataras/iris" } - - /** Gets the v12 module path `github.com/kataras/iris/v12` */ - string v12modulePath() { result = "github.com/kataras/iris/v12" } - - /** Gets the path for the context package of all versions of beego. */ - string contextPackagePath() { - result = v12contextPackagePath() - or - result = v1contextPackagePath() - } - - /** Gets the path for the context package of beego v12. */ - string v12contextPackagePath() { result = v12modulePath() + "/context" } - - /** Gets the path for the context package of beego v1. */ - string v1contextPackagePath() { result = v1modulePath() + "/server/web/context" } - - /** - * The File system access sinks - */ - class FsOperations extends FileSystemAccess::Range, DataFlow::CallNode { - int pathArg; - - FsOperations() { - exists(Method m | - ( - m.hasQualifiedName(contextPackagePath(), "Context", - ["SendFile", "ServeFile", "SendFileWithRate", "ServeFileWithRate", "UploadFormFiles"]) and - pathArg = 0 - or - m.hasQualifiedName(v12contextPackagePath(), "Context", "SaveFormFile") and - pathArg = 1 - ) and - this = m.getACall() - ) - } - - override DataFlow::Node getAPathArgument() { result = this.getArgument(pathArg) } - } -} diff --git a/go/ql/lib/semmle/go/frameworks/Logrus.qll b/go/ql/lib/semmle/go/frameworks/Logrus.qll index f7de9a75dae8..83278a4cd9e2 100644 --- a/go/ql/lib/semmle/go/frameworks/Logrus.qll +++ b/go/ql/lib/semmle/go/frameworks/Logrus.qll @@ -28,12 +28,6 @@ module Logrus { } } - private class LogCall extends LoggerCall::Range, DataFlow::CallNode { - LogCall() { this = any(LogFunction f).getACall() } - - override DataFlow::Node getAMessageComponent() { result = this.getASyntacticArgument() } - } - private class StringFormatters extends StringOps::Formatting::Range instanceof LogFunction { int argOffset; diff --git a/go/ql/lib/semmle/go/frameworks/Revel.qll b/go/ql/lib/semmle/go/frameworks/Revel.qll index 43ac4d92a265..874d46bc8380 100644 --- a/go/ql/lib/semmle/go/frameworks/Revel.qll +++ b/go/ql/lib/semmle/go/frameworks/Revel.qll @@ -87,20 +87,6 @@ module Revel { override string getAContentType() { result = contentType } } - /** - * The `revel.Controller.RenderFileName` method, which instructs Revel to open a file and return its contents. - * We extend FileSystemAccess rather than HTTP::ResponseBody as this will usually mean exposing a user-controlled - * file rather than the actual contents being user-controlled. - */ - private class RenderFileNameCall extends FileSystemAccess::Range, DataFlow::CallNode { - RenderFileNameCall() { - this = - any(Method m | m.hasQualifiedName(packagePath(), "Controller", "RenderFileName")).getACall() - } - - override DataFlow::Node getAPathArgument() { result = this.getArgument(0) } - } - /** * The `revel.Controller.Redirect` method. * diff --git a/go/ql/lib/semmle/go/frameworks/Spew.qll b/go/ql/lib/semmle/go/frameworks/Spew.qll index b12bd0fed815..f49a4aa4d89d 100644 --- a/go/ql/lib/semmle/go/frameworks/Spew.qll +++ b/go/ql/lib/semmle/go/frameworks/Spew.qll @@ -33,16 +33,6 @@ module Spew { override int getFormatStringIndex() { result = super.getFirstPrintedArg() } } - private class SpewCall extends LoggerCall::Range, DataFlow::CallNode { - SpewFunction target; - - SpewCall() { this = target.getACall() } - - override DataFlow::Node getAMessageComponent() { - result = this.getSyntacticArgument(any(int i | i >= target.getFirstPrintedArg())) - } - } - // These are expressed using TaintTracking::FunctionModel because varargs functions don't work with Models-as-Data sumamries yet. /** The `Sprint` function or one of its variants. */ class Sprinter extends TaintTracking::FunctionModel { diff --git a/go/ql/lib/semmle/go/frameworks/Stdlib.qll b/go/ql/lib/semmle/go/frameworks/Stdlib.qll index 44f3d16c11ce..3b05627168d4 100644 --- a/go/ql/lib/semmle/go/frameworks/Stdlib.qll +++ b/go/ql/lib/semmle/go/frameworks/Stdlib.qll @@ -24,7 +24,6 @@ import semmle.go.frameworks.stdlib.Html import semmle.go.frameworks.stdlib.HtmlTemplate import semmle.go.frameworks.stdlib.Io import semmle.go.frameworks.stdlib.IoFs -import semmle.go.frameworks.stdlib.IoIoutil import semmle.go.frameworks.stdlib.Log import semmle.go.frameworks.stdlib.MimeMultipart import semmle.go.frameworks.stdlib.MimeQuotedprintable diff --git a/go/ql/lib/semmle/go/frameworks/SystemCommandExecutors.qll b/go/ql/lib/semmle/go/frameworks/SystemCommandExecutors.qll index 3728a6bee3c1..7c7ab8c18351 100644 --- a/go/ql/lib/semmle/go/frameworks/SystemCommandExecutors.qll +++ b/go/ql/lib/semmle/go/frameworks/SystemCommandExecutors.qll @@ -5,6 +5,25 @@ import go +private class DefaultSystemCommandExecution extends SystemCommandExecution::Range, + DataFlow::CallNode +{ + DataFlow::ArgumentNode commandName; + + DefaultSystemCommandExecution() { + sinkNode(commandName, "command-injection") and + this = commandName.getCall() + } + + override DataFlow::Node getCommandName() { + not commandName instanceof DataFlow::ImplicitVarargsSlice and + result = commandName + or + commandName instanceof DataFlow::ImplicitVarargsSlice and + result = this.getAnImplicitVarargsArgument() + } +} + /** * An indirect system-command execution via an argument argument passed to a command interpreter * such as a shell, `sudo`, or a programming-language interpreter. @@ -26,85 +45,19 @@ private class ShellOrSudoExecution extends SystemCommandExecution::Range, DataFl } } -private class SystemCommandExecutors extends SystemCommandExecution::Range, DataFlow::CallNode { - int cmdArg; - - SystemCommandExecutors() { - exists(string pkg, string name | this.getTarget().hasQualifiedName(pkg, name) | - pkg = "os" and name = "StartProcess" and cmdArg = 0 - or - // assume that if a `Cmd` is instantiated it will be run - pkg = "os/exec" and name = "Command" and cmdArg = 0 - or - pkg = "os/exec" and name = "CommandContext" and cmdArg = 1 - or - // NOTE: syscall.ForkExec exists only on unix. - // NOTE: syscall.CreateProcess and syscall.CreateProcessAsUser exist only on windows. - pkg = "syscall" and - name = ["Exec", "ForkExec", "StartProcess", "CreateProcess"] and - cmdArg = 0 - or - pkg = "syscall" and - name = "CreateProcessAsUser" and - cmdArg = 1 - ) - } - - override DataFlow::Node getCommandName() { result = this.getSyntacticArgument(cmdArg) } -} - -/** - * A call to the `Command` function, or `Call` or `Command` methods on a `Session` object - * from the [go-sh](https://github.com/codeskyblue/go-sh) package, viewed as a - * system-command execution. - */ -private class GoShCommandExecution extends SystemCommandExecution::Range, DataFlow::CallNode { - GoShCommandExecution() { - exists(string packagePath | packagePath = package("github.com/codeskyblue/go-sh", "") | - // Catch method calls on the `Session` object: - exists(Method method | - method.hasQualifiedName(packagePath, "Session", "Call") - or - method.hasQualifiedName(packagePath, "Session", "Command") - or - method.hasQualifiedName(packagePath, "Session", "Exec") - | - this = method.getACall() - ) - or - // Catch calls to the `Command` function: - this.getTarget().hasQualifiedName(packagePath, "Command") - ) - } - - override DataFlow::Node getCommandName() { result = this.getSyntacticArgument(0) } -} - /** + * DEPRECATED + * * Provides classes for working with the * [golang.org/x/crypto/ssh](https://pkg.go.dev/golang.org/x/crypto/ssh) package. */ -module CryptoSsh { - /** Gets the package path `golang.org/x/crypto/ssh`. */ - string packagePath() { result = package("golang.org/x/crypto", "ssh") } - +deprecated module CryptoSsh { /** - * A call to a method on a `Session` object from the [ssh](golang.org/x/crypto/ssh) - * package, viewed as a system-command execution. + * DEPRECATED: Use `package("golang.org/x/crypto", "ssh")` instead. + * + * Gets the package path `golang.org/x/crypto/ssh`. */ - private class SshCommandExecution extends SystemCommandExecution::Range, DataFlow::CallNode { - SshCommandExecution() { - // Catch method calls on the `Session` object: - exists(Method method, string methodName | - methodName = ["CombinedOutput", "Output", "Run", "Start"] - | - method.hasQualifiedName(packagePath(), "Session", methodName) and - this = method.getACall() - ) - } - - override DataFlow::Node getCommandName() { result = this.getSyntacticArgument(0) } - } + deprecated string packagePath() { result = package("golang.org/x/crypto", "ssh") } } /** diff --git a/go/ql/lib/semmle/go/frameworks/Zap.qll b/go/ql/lib/semmle/go/frameworks/Zap.qll index 359f9aba4107..0928d2b0595c 100644 --- a/go/ql/lib/semmle/go/frameworks/Zap.qll +++ b/go/ql/lib/semmle/go/frameworks/Zap.qll @@ -34,18 +34,6 @@ module Zap { override int getFormatStringIndex() { result = 0 } } - /** - * A call to a logger function in Zap. - * - * Functions which add data to be included the next time a direct logging - * function is called are included. - */ - private class ZapCall extends LoggerCall::Range, DataFlow::MethodCallNode { - ZapCall() { this = any(ZapFunction f).getACall() } - - override DataFlow::Node getAMessageComponent() { result = this.getASyntacticArgument() } - } - // These are expressed using TaintTracking::FunctionModel because varargs functions don't work with Models-as-Data sumamries yet. /** The function `Fields` that creates an `Option` that can be added to the logger out of `Field`s. */ class FieldsFunction extends TaintTracking::FunctionModel { diff --git a/go/ql/lib/semmle/go/frameworks/stdlib/Fmt.qll b/go/ql/lib/semmle/go/frameworks/stdlib/Fmt.qll index 950b67483f00..8c4a5f27b3cd 100644 --- a/go/ql/lib/semmle/go/frameworks/stdlib/Fmt.qll +++ b/go/ql/lib/semmle/go/frameworks/stdlib/Fmt.qll @@ -41,13 +41,6 @@ module Fmt { Printer() { this.hasQualifiedName("fmt", ["Print", "Printf", "Println"]) } } - /** A call to `Print` or similar. */ - private class PrintCall extends LoggerCall::Range, DataFlow::CallNode { - PrintCall() { this.getTarget() instanceof Printer } - - override DataFlow::Node getAMessageComponent() { result = this.getASyntacticArgument() } - } - /** The `Fprint` function or one of its variants. */ private class Fprinter extends TaintTracking::FunctionModel { Fprinter() { diff --git a/go/ql/lib/semmle/go/frameworks/stdlib/IoIoutil.qll b/go/ql/lib/semmle/go/frameworks/stdlib/IoIoutil.qll deleted file mode 100644 index d8e69af13072..000000000000 --- a/go/ql/lib/semmle/go/frameworks/stdlib/IoIoutil.qll +++ /dev/null @@ -1,18 +0,0 @@ -/** - * Provides classes modeling security-relevant aspects of the `io/ioutil` package. - */ - -import go - -/** Provides models of commonly used functions in the `io/ioutil` package. */ -module IoIoutil { - private class IoUtilFileSystemAccess extends FileSystemAccess::Range, DataFlow::CallNode { - IoUtilFileSystemAccess() { - exists(string fn | this.getTarget().hasQualifiedName("io/ioutil", fn) | - fn = ["ReadDir", "ReadFile", "TempDir", "TempFile", "WriteFile"] - ) - } - - override DataFlow::Node getAPathArgument() { result = this.getAnArgument() } - } -} diff --git a/go/ql/lib/semmle/go/frameworks/stdlib/Log.qll b/go/ql/lib/semmle/go/frameworks/stdlib/Log.qll index 5b402fca1b7e..ca74160bf0df 100644 --- a/go/ql/lib/semmle/go/frameworks/stdlib/Log.qll +++ b/go/ql/lib/semmle/go/frameworks/stdlib/Log.qll @@ -32,16 +32,6 @@ module Log { override int getFormatStringIndex() { result = 0 } } - private class LogCall extends LoggerCall::Range, DataFlow::CallNode { - LogFunction target; - - LogCall() { this = target.getACall() } - - override DataFlow::Node getAMessageComponent() { - result = this.getSyntacticArgument(any(int i | i >= target.getFirstPrintedArg())) - } - } - /** A fatal log function, which calls `os.Exit`. */ private class FatalLogFunction extends Function { FatalLogFunction() { this.hasQualifiedName("log", ["Fatal", "Fatalf", "Fatalln"]) } diff --git a/go/ql/lib/semmle/go/frameworks/stdlib/NetHttp.qll b/go/ql/lib/semmle/go/frameworks/stdlib/NetHttp.qll index 8d307fc67ff4..73991e334f32 100644 --- a/go/ql/lib/semmle/go/frameworks/stdlib/NetHttp.qll +++ b/go/ql/lib/semmle/go/frameworks/stdlib/NetHttp.qll @@ -288,9 +288,11 @@ module NetHttp { } /** + * DEPRECATED: Use `FileSystemAccess::Range` instead. + * * The File system access sinks */ - class HttpServeFile extends FileSystemAccess::Range, DataFlow::CallNode { + deprecated class HttpServeFile extends FileSystemAccess::Range, DataFlow::CallNode { HttpServeFile() { exists(Function f | f.hasQualifiedName("net/http", "ServeFile") and diff --git a/go/ql/lib/semmle/go/frameworks/stdlib/Os.qll b/go/ql/lib/semmle/go/frameworks/stdlib/Os.qll index 24b30c15e96f..72ea4cc6c573 100644 --- a/go/ql/lib/semmle/go/frameworks/stdlib/Os.qll +++ b/go/ql/lib/semmle/go/frameworks/stdlib/Os.qll @@ -6,71 +6,6 @@ import go /** Provides models of commonly used functions in the `os` package. */ module Os { - /** - * A call to a function in `os` that accesses the file system. - */ - private class OsFileSystemAccess extends FileSystemAccess::Range, DataFlow::CallNode { - int pathidx; - - OsFileSystemAccess() { - exists(string fn | this.getTarget().hasQualifiedName("os", fn) | - fn = "Chdir" and pathidx = 0 - or - fn = "Chmod" and pathidx = 0 - or - fn = "Chown" and pathidx = 0 - or - fn = "Chtimes" and pathidx = 0 - or - fn = "Create" and pathidx = 0 - or - fn = "Lchown" and pathidx = 0 - or - fn = "Link" and pathidx in [0 .. 1] - or - fn = "Lstat" and pathidx = 0 - or - fn = "Mkdir" and pathidx = 0 - or - fn = "MkdirAll" and pathidx = 0 - or - fn = "NewFile" and pathidx = 1 - or - fn = "Open" and pathidx = 0 - or - fn = "OpenFile" and pathidx = 0 - or - fn = "Readlink" and pathidx = 0 - or - fn = "Remove" and pathidx = 0 - or - fn = "RemoveAll" and pathidx = 0 - or - fn = "Rename" and pathidx in [0 .. 1] - or - fn = "Stat" and pathidx = 0 - or - fn = "Symlink" and pathidx in [0 .. 1] - or - fn = "Truncate" and pathidx = 0 - or - fn = "DirFS" and pathidx = 0 - or - fn = "ReadDir" and pathidx = 0 - or - fn = "ReadFile" and pathidx = 0 - or - fn = "MkdirTemp" and pathidx in [0 .. 1] - or - fn = "CreateTemp" and pathidx in [0 .. 1] - or - fn = "WriteFile" and pathidx = 0 - ) - } - - override DataFlow::Node getAPathArgument() { result = this.getArgument(pathidx) } - } - /** The `os.Exit` function, which ends the process. */ private class Exit extends Function { Exit() { this.hasQualifiedName("os", "Exit") } diff --git a/go/ql/src/Security/CWE-322/InsecureHostKeyCallback.ql b/go/ql/src/Security/CWE-322/InsecureHostKeyCallback.ql index bca436dc2998..2c292785f7f1 100644 --- a/go/ql/src/Security/CWE-322/InsecureHostKeyCallback.ql +++ b/go/ql/src/Security/CWE-322/InsecureHostKeyCallback.ql @@ -12,17 +12,17 @@ import go +private string cryptoSshPackage() { result = package("golang.org/x/crypto", "ssh") } + /** The `ssh.InsecureIgnoreHostKey` function, which allows connecting to any host regardless of its host key. */ class InsecureIgnoreHostKey extends Function { - InsecureIgnoreHostKey() { - this.hasQualifiedName(CryptoSsh::packagePath(), "InsecureIgnoreHostKey") - } + InsecureIgnoreHostKey() { this.hasQualifiedName(cryptoSshPackage(), "InsecureIgnoreHostKey") } } /** An SSH host-key checking function. */ class HostKeyCallbackFunc extends DataFlow::Node { HostKeyCallbackFunc() { - exists(NamedType nt | nt.hasQualifiedName(CryptoSsh::packagePath(), "HostKeyCallback") | + exists(NamedType nt | nt.hasQualifiedName(cryptoSshPackage(), "HostKeyCallback") | this.getType().getUnderlyingType() = nt.getUnderlyingType() ) and // Restrict possible sources to either function definitions or @@ -62,7 +62,7 @@ module Config implements DataFlow::ConfigSig { */ additional predicate writeIsSink(DataFlow::Node sink, Write write) { exists(Field f | - f.hasQualifiedName(CryptoSsh::packagePath(), "ClientConfig", "HostKeyCallback") and + f.hasQualifiedName(cryptoSshPackage(), "ClientConfig", "HostKeyCallback") and write.writesField(_, f, sink) ) } diff --git a/go/ql/src/experimental/CWE-918/SSRF.qll b/go/ql/src/experimental/CWE-918/SSRF.qll index 0796d9c3892d..dd5eebc8b10b 100644 --- a/go/ql/src/experimental/CWE-918/SSRF.qll +++ b/go/ql/src/experimental/CWE-918/SSRF.qll @@ -10,7 +10,6 @@ import go * (SSRF) vulnerabilities. */ module ServerSideRequestForgery { - private import semmle.go.frameworks.Gin private import validator private import semmle.go.security.UrlConcatenation private import semmle.go.dataflow.barrierguardutil.RegexpCheck diff --git a/go/ql/test/library-tests/semmle/go/frameworks/Beego/TaintedPath.expected b/go/ql/test/library-tests/semmle/go/frameworks/Beego/TaintedPath.expected index 420f2105dce2..d5717b91edc3 100644 --- a/go/ql/test/library-tests/semmle/go/frameworks/Beego/TaintedPath.expected +++ b/go/ql/test/library-tests/semmle/go/frameworks/Beego/TaintedPath.expected @@ -7,18 +7,23 @@ | test.go:342:53:342:61 | untrusted | test.go:340:15:340:26 | call to Data | test.go:342:53:342:61 | untrusted | This path depends on a $@. | test.go:340:15:340:26 | call to Data | user-provided value | | test.go:344:23:344:31 | untrusted | test.go:340:15:340:26 | call to Data | test.go:344:23:344:31 | untrusted | This path depends on a $@. | test.go:340:15:340:26 | call to Data | user-provided value | edges -| test.go:215:15:215:26 | call to Data | test.go:216:18:216:26 | untrusted | provenance | Src:MaD:2 | -| test.go:215:15:215:26 | call to Data | test.go:217:10:217:18 | untrusted | provenance | Src:MaD:2 | -| test.go:215:15:215:26 | call to Data | test.go:218:35:218:43 | untrusted | provenance | Src:MaD:2 | -| test.go:324:17:324:37 | selection of RequestBody | test.go:324:40:324:43 | &... | provenance | Src:MaD:3 MaD:1 | -| test.go:324:40:324:43 | &... | test.go:326:35:326:43 | untrusted | provenance | | -| test.go:332:15:332:26 | call to Data | test.go:334:23:334:31 | untrusted | provenance | Src:MaD:2 | -| test.go:340:15:340:26 | call to Data | test.go:342:53:342:61 | untrusted | provenance | Src:MaD:2 | -| test.go:340:15:340:26 | call to Data | test.go:344:23:344:31 | untrusted | provenance | Src:MaD:2 | +| test.go:215:15:215:26 | call to Data | test.go:216:18:216:26 | untrusted | provenance | Src:MaD:3 Sink:MaD:5 | +| test.go:215:15:215:26 | call to Data | test.go:217:10:217:18 | untrusted | provenance | Src:MaD:3 Sink:MaD:8 | +| test.go:215:15:215:26 | call to Data | test.go:218:35:218:43 | untrusted | provenance | Src:MaD:3 Sink:MaD:6 | +| test.go:324:17:324:37 | selection of RequestBody | test.go:324:40:324:43 | &... | provenance | Src:MaD:4 MaD:1 | +| test.go:324:40:324:43 | &... | test.go:326:35:326:43 | untrusted | provenance | Sink:MaD:6 | +| test.go:332:15:332:26 | call to Data | test.go:334:23:334:31 | untrusted | provenance | Src:MaD:3 Sink:MaD:2 | +| test.go:340:15:340:26 | call to Data | test.go:342:53:342:61 | untrusted | provenance | Src:MaD:3 Sink:MaD:7 | +| test.go:340:15:340:26 | call to Data | test.go:344:23:344:31 | untrusted | provenance | Src:MaD:3 Sink:MaD:2 | models | 1 | Summary: encoding/json; ; false; Unmarshal; ; ; Argument[0]; Argument[1]; taint; manual | -| 2 | Source: group:beego-context; BeegoInput; true; Data; ; ; ReturnValue[0]; remote; manual | -| 3 | Source: group:beego-context; BeegoInput; true; RequestBody; ; ; ; remote; manual | +| 2 | Sink: group:beego-context; BeegoOutput; false; Download; ; ; Argument[0]; path-injection; manual | +| 3 | Source: group:beego-context; BeegoInput; true; Data; ; ; ReturnValue[0]; remote; manual | +| 4 | Source: group:beego-context; BeegoInput; true; RequestBody; ; ; ; remote; manual | +| 5 | Sink: group:beego; ; false; Walk; ; ; Argument[1]; path-injection; manual | +| 6 | Sink: group:beego; Controller; false; SaveToFile; ; ; Argument[1]; path-injection; manual | +| 7 | Sink: group:beego; Controller; false; SaveToFileWithBuffer; ; ; Argument[1]; path-injection; manual | +| 8 | Sink: group:beego; FileSystem; false; Open; ; ; Argument[0]; path-injection; manual | nodes | test.go:215:15:215:26 | call to Data | semmle.label | call to Data | | test.go:216:18:216:26 | untrusted | semmle.label | untrusted | diff --git a/go/ql/test/library-tests/semmle/go/frameworks/Echo/TaintedPath.expected b/go/ql/test/library-tests/semmle/go/frameworks/Echo/TaintedPath.expected index 9005fa41f54b..d4fe58766098 100644 --- a/go/ql/test/library-tests/semmle/go/frameworks/Echo/TaintedPath.expected +++ b/go/ql/test/library-tests/semmle/go/frameworks/Echo/TaintedPath.expected @@ -2,10 +2,12 @@ | test.go:222:17:222:24 | filepath | test.go:221:15:221:38 | call to QueryParam | test.go:222:17:222:24 | filepath | This path depends on a $@. | test.go:221:15:221:38 | call to QueryParam | user-provided value | | test.go:226:23:226:30 | filepath | test.go:225:15:225:38 | call to QueryParam | test.go:226:23:226:30 | filepath | This path depends on a $@. | test.go:225:15:225:38 | call to QueryParam | user-provided value | edges -| test.go:221:15:221:38 | call to QueryParam | test.go:222:17:222:24 | filepath | provenance | Src:MaD:1 | -| test.go:225:15:225:38 | call to QueryParam | test.go:226:23:226:30 | filepath | provenance | Src:MaD:1 | +| test.go:221:15:221:38 | call to QueryParam | test.go:222:17:222:24 | filepath | provenance | Src:MaD:3 Sink:MaD:2 | +| test.go:225:15:225:38 | call to QueryParam | test.go:226:23:226:30 | filepath | provenance | Src:MaD:3 Sink:MaD:1 | models -| 1 | Source: github.com/labstack/echo; Context; true; QueryParam; ; ; ReturnValue[0]; remote; manual | +| 1 | Sink: github.com/labstack/echo; Context; false; Attachment; ; ; Argument[0]; path-injection; manual | +| 2 | Sink: github.com/labstack/echo; Context; false; File; ; ; Argument[0]; path-injection; manual | +| 3 | Source: github.com/labstack/echo; Context; true; QueryParam; ; ; ReturnValue[0]; remote; manual | nodes | test.go:221:15:221:38 | call to QueryParam | semmle.label | call to QueryParam | | test.go:222:17:222:24 | filepath | semmle.label | filepath | diff --git a/go/ql/test/library-tests/semmle/go/frameworks/Encoding/jsoniter.expected b/go/ql/test/library-tests/semmle/go/frameworks/Encoding/jsoniter.expected index d8ce6dfef69a..222d0ce4a706 100644 --- a/go/ql/test/library-tests/semmle/go/frameworks/Encoding/jsoniter.expected +++ b/go/ql/test/library-tests/semmle/go/frameworks/Encoding/jsoniter.expected @@ -3,19 +3,20 @@ models | 2 | Summary: github.com/json-iterator/go; ; false; UnmarshalFromString; ; ; Argument[0]; Argument[1]; taint; manual | | 3 | Summary: github.com/json-iterator/go; API; true; Unmarshal; ; ; Argument[0]; Argument[1]; taint; manual | | 4 | Summary: github.com/json-iterator/go; API; true; UnmarshalFromString; ; ; Argument[0]; Argument[1]; taint; manual | +| 5 | Sink: os/exec; ; false; Command; ; ; Argument[0]; command-injection; manual | edges | jsoniter.go:23:20:23:38 | call to getUntrustedBytes | jsoniter.go:27:17:27:30 | untrustedInput | provenance | | | jsoniter.go:23:20:23:38 | call to getUntrustedBytes | jsoniter.go:31:21:31:34 | untrustedInput | provenance | | | jsoniter.go:24:21:24:40 | call to getUntrustedString | jsoniter.go:35:27:35:41 | untrustedString | provenance | | | jsoniter.go:24:21:24:40 | call to getUntrustedString | jsoniter.go:39:31:39:45 | untrustedString | provenance | | | jsoniter.go:27:17:27:30 | untrustedInput | jsoniter.go:27:33:27:37 | &... | provenance | MaD:3 | -| jsoniter.go:27:33:27:37 | &... | jsoniter.go:28:15:28:24 | selection of field | provenance | | +| jsoniter.go:27:33:27:37 | &... | jsoniter.go:28:15:28:24 | selection of field | provenance | Sink:MaD:5 | | jsoniter.go:31:21:31:34 | untrustedInput | jsoniter.go:31:37:31:42 | &... | provenance | MaD:1 | -| jsoniter.go:31:37:31:42 | &... | jsoniter.go:32:15:32:25 | selection of field | provenance | | +| jsoniter.go:31:37:31:42 | &... | jsoniter.go:32:15:32:25 | selection of field | provenance | Sink:MaD:5 | | jsoniter.go:35:27:35:41 | untrustedString | jsoniter.go:35:44:35:49 | &... | provenance | MaD:4 | -| jsoniter.go:35:44:35:49 | &... | jsoniter.go:36:15:36:25 | selection of field | provenance | | +| jsoniter.go:35:44:35:49 | &... | jsoniter.go:36:15:36:25 | selection of field | provenance | Sink:MaD:5 | | jsoniter.go:39:31:39:45 | untrustedString | jsoniter.go:39:48:39:53 | &... | provenance | MaD:2 | -| jsoniter.go:39:48:39:53 | &... | jsoniter.go:40:15:40:25 | selection of field | provenance | | +| jsoniter.go:39:48:39:53 | &... | jsoniter.go:40:15:40:25 | selection of field | provenance | Sink:MaD:5 | nodes | jsoniter.go:23:20:23:38 | call to getUntrustedBytes | semmle.label | call to getUntrustedBytes | | jsoniter.go:24:21:24:40 | call to getUntrustedString | semmle.label | call to getUntrustedString | diff --git a/go/ql/test/library-tests/semmle/go/frameworks/Gin/TaintedPath.expected b/go/ql/test/library-tests/semmle/go/frameworks/Gin/TaintedPath.expected index f22e662ac192..b0f1baba28a5 100644 --- a/go/ql/test/library-tests/semmle/go/frameworks/Gin/TaintedPath.expected +++ b/go/ql/test/library-tests/semmle/go/frameworks/Gin/TaintedPath.expected @@ -4,12 +4,16 @@ | Gin.go:27:20:27:27 | filepath | Gin.go:24:15:24:33 | call to Query | Gin.go:27:20:27:27 | filepath | This path depends on a $@. | Gin.go:24:15:24:33 | call to Query | user-provided value | | Gin.go:29:32:29:39 | filepath | Gin.go:24:15:24:33 | call to Query | Gin.go:29:32:29:39 | filepath | This path depends on a $@. | Gin.go:24:15:24:33 | call to Query | user-provided value | edges -| Gin.go:24:15:24:33 | call to Query | Gin.go:25:10:25:17 | filepath | provenance | Src:MaD:1 | -| Gin.go:24:15:24:33 | call to Query | Gin.go:26:39:26:46 | filepath | provenance | Src:MaD:1 | -| Gin.go:24:15:24:33 | call to Query | Gin.go:27:20:27:27 | filepath | provenance | Src:MaD:1 | -| Gin.go:24:15:24:33 | call to Query | Gin.go:29:32:29:39 | filepath | provenance | Src:MaD:1 | +| Gin.go:24:15:24:33 | call to Query | Gin.go:25:10:25:17 | filepath | provenance | Src:MaD:4 Sink:MaD:1 | +| Gin.go:24:15:24:33 | call to Query | Gin.go:26:39:26:46 | filepath | provenance | Src:MaD:4 Sink:MaD:5 | +| Gin.go:24:15:24:33 | call to Query | Gin.go:27:20:27:27 | filepath | provenance | Src:MaD:4 Sink:MaD:2 | +| Gin.go:24:15:24:33 | call to Query | Gin.go:29:32:29:39 | filepath | provenance | Src:MaD:4 Sink:MaD:3 | models -| 1 | Source: github.com/gin-gonic/gin; Context; true; Query; ; ; ReturnValue; remote; manual | +| 1 | Sink: github.com/gin-gonic/gin; Context; false; File; ; ; Argument[0]; path-injection; manual | +| 2 | Sink: github.com/gin-gonic/gin; Context; false; FileAttachment; ; ; Argument[0]; path-injection; manual | +| 3 | Sink: github.com/gin-gonic/gin; Context; false; SaveUploadedFile; ; ; Argument[1]; path-injection; manual | +| 4 | Source: github.com/gin-gonic/gin; Context; true; Query; ; ; ReturnValue; remote; manual | +| 5 | Sink: net/http; ; false; ServeFile; ; ; Argument[2]; path-injection; manual | nodes | Gin.go:24:15:24:33 | call to Query | semmle.label | call to Query | | Gin.go:25:10:25:17 | filepath | semmle.label | filepath | diff --git a/go/ql/test/library-tests/semmle/go/frameworks/Gorestful/gorestful.expected b/go/ql/test/library-tests/semmle/go/frameworks/Gorestful/gorestful.expected index 107678aeb1c6..b20fb2b555c8 100644 --- a/go/ql/test/library-tests/semmle/go/frameworks/Gorestful/gorestful.expected +++ b/go/ql/test/library-tests/semmle/go/frameworks/Gorestful/gorestful.expected @@ -3,15 +3,16 @@ models | 2 | Source: github.com/emicklei/go-restful; Request; true; BodyParameter; ; ; ReturnValue[0]; remote; manual | | 3 | Source: github.com/emicklei/go-restful; Request; true; PathParameters; ; ; ReturnValue; remote; manual | | 4 | Source: github.com/emicklei/go-restful; Request; true; ReadEntity; ; ; Argument[0]; remote; manual | +| 5 | Sink: os/exec; ; false; Command; ; ; Argument[0]; command-injection; manual | edges -| gorestful.go:15:15:15:44 | call to QueryParameters | gorestful.go:15:15:15:47 | index expression | provenance | Src:MaD:1 | -| gorestful.go:17:2:17:39 | ... := ...[0] | gorestful.go:18:15:18:17 | val | provenance | Src:MaD:2 | -| gorestful.go:21:15:21:38 | call to PathParameters | gorestful.go:21:15:21:45 | index expression | provenance | Src:MaD:3 | -| gorestful.go:23:21:23:24 | &... | gorestful.go:24:15:24:21 | selection of cmd | provenance | Src:MaD:4 | -| gorestful_v2.go:15:15:15:44 | call to QueryParameters | gorestful_v2.go:15:15:15:47 | index expression | provenance | Src:MaD:1 | -| gorestful_v2.go:17:2:17:39 | ... := ...[0] | gorestful_v2.go:18:15:18:17 | val | provenance | Src:MaD:2 | -| gorestful_v2.go:21:15:21:38 | call to PathParameters | gorestful_v2.go:21:15:21:45 | index expression | provenance | Src:MaD:3 | -| gorestful_v2.go:23:21:23:24 | &... | gorestful_v2.go:24:15:24:21 | selection of cmd | provenance | Src:MaD:4 | +| gorestful.go:15:15:15:44 | call to QueryParameters | gorestful.go:15:15:15:47 | index expression | provenance | Src:MaD:1 Sink:MaD:5 | +| gorestful.go:17:2:17:39 | ... := ...[0] | gorestful.go:18:15:18:17 | val | provenance | Src:MaD:2 Sink:MaD:5 | +| gorestful.go:21:15:21:38 | call to PathParameters | gorestful.go:21:15:21:45 | index expression | provenance | Src:MaD:3 Sink:MaD:5 | +| gorestful.go:23:21:23:24 | &... | gorestful.go:24:15:24:21 | selection of cmd | provenance | Src:MaD:4 Sink:MaD:5 | +| gorestful_v2.go:15:15:15:44 | call to QueryParameters | gorestful_v2.go:15:15:15:47 | index expression | provenance | Src:MaD:1 Sink:MaD:5 | +| gorestful_v2.go:17:2:17:39 | ... := ...[0] | gorestful_v2.go:18:15:18:17 | val | provenance | Src:MaD:2 Sink:MaD:5 | +| gorestful_v2.go:21:15:21:38 | call to PathParameters | gorestful_v2.go:21:15:21:45 | index expression | provenance | Src:MaD:3 Sink:MaD:5 | +| gorestful_v2.go:23:21:23:24 | &... | gorestful_v2.go:24:15:24:21 | selection of cmd | provenance | Src:MaD:4 Sink:MaD:5 | nodes | gorestful.go:15:15:15:44 | call to QueryParameters | semmle.label | call to QueryParameters | | gorestful.go:15:15:15:47 | index expression | semmle.label | index expression | diff --git a/go/ql/test/library-tests/semmle/go/frameworks/Revel/TaintedPath.expected b/go/ql/test/library-tests/semmle/go/frameworks/Revel/TaintedPath.expected index 1dd758c931ac..33d8bb8ae178 100644 --- a/go/ql/test/library-tests/semmle/go/frameworks/Revel/TaintedPath.expected +++ b/go/ql/test/library-tests/semmle/go/frameworks/Revel/TaintedPath.expected @@ -3,12 +3,14 @@ | EndToEnd.go:64:26:64:55 | call to Get | EndToEnd.go:64:26:64:33 | selection of Params | EndToEnd.go:64:26:64:55 | call to Get | This path depends on a $@. | EndToEnd.go:64:26:64:33 | selection of Params | user-provided value | edges | EndToEnd.go:58:18:58:25 | selection of Params | EndToEnd.go:58:18:58:30 | selection of Form | provenance | Src:MaD:1 | -| EndToEnd.go:58:18:58:30 | selection of Form | EndToEnd.go:58:18:58:47 | call to Get | provenance | MaD:2 | +| EndToEnd.go:58:18:58:30 | selection of Form | EndToEnd.go:58:18:58:47 | call to Get | provenance | MaD:3 Sink:MaD:4 | | EndToEnd.go:64:26:64:33 | selection of Params | EndToEnd.go:64:26:64:38 | selection of Form | provenance | Src:MaD:1 | -| EndToEnd.go:64:26:64:38 | selection of Form | EndToEnd.go:64:26:64:55 | call to Get | provenance | MaD:2 | +| EndToEnd.go:64:26:64:38 | selection of Form | EndToEnd.go:64:26:64:55 | call to Get | provenance | MaD:3 Sink:MaD:2 | models | 1 | Source: group:revel; Controller; true; Params; ; ; ; remote; manual | -| 2 | Summary: net/url; Values; true; Get; ; ; Argument[receiver]; ReturnValue; taint; manual | +| 2 | Sink: group:revel; Controller; true; RenderFileName; ; ; Argument[0]; path-injection; manual | +| 3 | Summary: net/url; Values; true; Get; ; ; Argument[receiver]; ReturnValue; taint; manual | +| 4 | Sink: os; ; false; Open; ; ; Argument[0]; path-injection; manual | nodes | EndToEnd.go:58:18:58:25 | selection of Params | semmle.label | selection of Params | | EndToEnd.go:58:18:58:30 | selection of Form | semmle.label | selection of Form | diff --git a/go/ql/test/query-tests/Security/CWE-022/TaintedPath.expected b/go/ql/test/query-tests/Security/CWE-022/TaintedPath.expected index 72d303a5545f..b64fea5197dc 100644 --- a/go/ql/test/query-tests/Security/CWE-022/TaintedPath.expected +++ b/go/ql/test/query-tests/Security/CWE-022/TaintedPath.expected @@ -1,14 +1,19 @@ -models -| 1 | Source: net/http; Request; true; URL; ; ; ; remote; manual | -| 2 | Summary: net/url; URL; true; Query; ; ; Argument[receiver]; ReturnValue; taint; manual | -| 3 | Summary: path; ; false; Clean; ; ; Argument[0]; ReturnValue; taint; manual | +#select +| TaintedPath.go:17:29:17:40 | tainted_path | TaintedPath.go:14:18:14:22 | selection of URL | TaintedPath.go:17:29:17:40 | tainted_path | This path depends on a $@. | TaintedPath.go:14:18:14:22 | selection of URL | user-provided value | +| TaintedPath.go:21:28:21:69 | call to Join | TaintedPath.go:14:18:14:22 | selection of URL | TaintedPath.go:21:28:21:69 | call to Join | This path depends on a $@. | TaintedPath.go:14:18:14:22 | selection of URL | user-provided value | +| TaintedPath.go:68:28:68:57 | call to Clean | TaintedPath.go:14:18:14:22 | selection of URL | TaintedPath.go:68:28:68:57 | call to Clean | This path depends on a $@. | TaintedPath.go:14:18:14:22 | selection of URL | user-provided value | edges -| TaintedPath.go:14:18:14:22 | selection of URL | TaintedPath.go:14:18:14:30 | call to Query | provenance | Src:MaD:1 MaD:2 | -| TaintedPath.go:14:18:14:30 | call to Query | TaintedPath.go:17:29:17:40 | tainted_path | provenance | | +| TaintedPath.go:14:18:14:22 | selection of URL | TaintedPath.go:14:18:14:30 | call to Query | provenance | Src:MaD:2 MaD:3 | +| TaintedPath.go:14:18:14:30 | call to Query | TaintedPath.go:17:29:17:40 | tainted_path | provenance | Sink:MaD:1 | | TaintedPath.go:14:18:14:30 | call to Query | TaintedPath.go:21:57:21:68 | tainted_path | provenance | | | TaintedPath.go:14:18:14:30 | call to Query | TaintedPath.go:68:39:68:56 | ...+... | provenance | | -| TaintedPath.go:21:57:21:68 | tainted_path | TaintedPath.go:21:28:21:69 | call to Join | provenance | FunctionModel | -| TaintedPath.go:68:39:68:56 | ...+... | TaintedPath.go:68:28:68:57 | call to Clean | provenance | MaD:3 | +| TaintedPath.go:21:57:21:68 | tainted_path | TaintedPath.go:21:28:21:69 | call to Join | provenance | FunctionModel Sink:MaD:1 | +| TaintedPath.go:68:39:68:56 | ...+... | TaintedPath.go:68:28:68:57 | call to Clean | provenance | MaD:4 Sink:MaD:1 | +models +| 1 | Sink: io/ioutil; ; false; ReadFile; ; ; Argument[0]; path-injection; manual | +| 2 | Source: net/http; Request; true; URL; ; ; ; remote; manual | +| 3 | Summary: net/url; URL; true; Query; ; ; Argument[receiver]; ReturnValue; taint; manual | +| 4 | Summary: path; ; false; Clean; ; ; Argument[0]; ReturnValue; taint; manual | nodes | TaintedPath.go:14:18:14:22 | selection of URL | semmle.label | selection of URL | | TaintedPath.go:14:18:14:30 | call to Query | semmle.label | call to Query | @@ -18,7 +23,3 @@ nodes | TaintedPath.go:68:28:68:57 | call to Clean | semmle.label | call to Clean | | TaintedPath.go:68:39:68:56 | ...+... | semmle.label | ...+... | subpaths -#select -| TaintedPath.go:17:29:17:40 | tainted_path | TaintedPath.go:14:18:14:22 | selection of URL | TaintedPath.go:17:29:17:40 | tainted_path | This path depends on a $@. | TaintedPath.go:14:18:14:22 | selection of URL | user-provided value | -| TaintedPath.go:21:28:21:69 | call to Join | TaintedPath.go:14:18:14:22 | selection of URL | TaintedPath.go:21:28:21:69 | call to Join | This path depends on a $@. | TaintedPath.go:14:18:14:22 | selection of URL | user-provided value | -| TaintedPath.go:68:28:68:57 | call to Clean | TaintedPath.go:14:18:14:22 | selection of URL | TaintedPath.go:68:28:68:57 | call to Clean | This path depends on a $@. | TaintedPath.go:14:18:14:22 | selection of URL | user-provided value | diff --git a/go/ql/test/query-tests/Security/CWE-022/UnsafeUnzipSymlink.expected b/go/ql/test/query-tests/Security/CWE-022/UnsafeUnzipSymlink.expected index bddeaf06e627..98bde83cdf8e 100644 --- a/go/ql/test/query-tests/Security/CWE-022/UnsafeUnzipSymlink.expected +++ b/go/ql/test/query-tests/Security/CWE-022/UnsafeUnzipSymlink.expected @@ -1,8 +1,16 @@ +#select +| UnsafeUnzipSymlink.go:31:15:31:29 | selection of Linkname | UnsafeUnzipSymlink.go:31:15:31:29 | selection of Linkname | UnsafeUnzipSymlink.go:31:15:31:29 | selection of Linkname | Unresolved path from an archive header, which may point outside the archive root, is used in $@. | UnsafeUnzipSymlink.go:31:15:31:29 | selection of Linkname | symlink creation | +| UnsafeUnzipSymlink.go:31:32:31:42 | selection of Name | UnsafeUnzipSymlink.go:31:32:31:42 | selection of Name | UnsafeUnzipSymlink.go:31:32:31:42 | selection of Name | Unresolved path from an archive header, which may point outside the archive root, is used in $@. | UnsafeUnzipSymlink.go:31:32:31:42 | selection of Name | symlink creation | +| UnsafeUnzipSymlink.go:43:25:43:35 | selection of Name | UnsafeUnzipSymlink.go:43:25:43:35 | selection of Name | UnsafeUnzipSymlink.go:43:25:43:35 | selection of Name | Unresolved path from an archive header, which may point outside the archive root, is used in $@. | UnsafeUnzipSymlink.go:43:25:43:35 | selection of Name | symlink creation | +| UnsafeUnzipSymlink.go:126:17:126:31 | selection of Linkname | UnsafeUnzipSymlink.go:126:17:126:31 | selection of Linkname | UnsafeUnzipSymlink.go:112:13:112:20 | linkName | Unresolved path from an archive header, which may point outside the archive root, is used in $@. | UnsafeUnzipSymlink.go:112:13:112:20 | linkName | symlink creation | +| UnsafeUnzipSymlink.go:126:34:126:44 | selection of Name | UnsafeUnzipSymlink.go:126:34:126:44 | selection of Name | UnsafeUnzipSymlink.go:112:23:112:30 | fileName | Unresolved path from an archive header, which may point outside the archive root, is used in $@. | UnsafeUnzipSymlink.go:112:23:112:30 | fileName | symlink creation | edges -| UnsafeUnzipSymlink.go:111:19:111:26 | definition of linkName | UnsafeUnzipSymlink.go:112:13:112:20 | linkName | provenance | | -| UnsafeUnzipSymlink.go:111:29:111:36 | definition of fileName | UnsafeUnzipSymlink.go:112:23:112:30 | fileName | provenance | | +| UnsafeUnzipSymlink.go:111:19:111:26 | definition of linkName | UnsafeUnzipSymlink.go:112:13:112:20 | linkName | provenance | Sink:MaD:1 | +| UnsafeUnzipSymlink.go:111:29:111:36 | definition of fileName | UnsafeUnzipSymlink.go:112:23:112:30 | fileName | provenance | Sink:MaD:1 | | UnsafeUnzipSymlink.go:126:17:126:31 | selection of Linkname | UnsafeUnzipSymlink.go:111:19:111:26 | definition of linkName | provenance | | | UnsafeUnzipSymlink.go:126:34:126:44 | selection of Name | UnsafeUnzipSymlink.go:111:29:111:36 | definition of fileName | provenance | | +models +| 1 | Sink: os; ; false; Symlink; ; ; Argument[0..1]; path-injection; manual | nodes | UnsafeUnzipSymlink.go:31:15:31:29 | selection of Linkname | semmle.label | selection of Linkname | | UnsafeUnzipSymlink.go:31:32:31:42 | selection of Name | semmle.label | selection of Name | @@ -14,9 +22,3 @@ nodes | UnsafeUnzipSymlink.go:126:17:126:31 | selection of Linkname | semmle.label | selection of Linkname | | UnsafeUnzipSymlink.go:126:34:126:44 | selection of Name | semmle.label | selection of Name | subpaths -#select -| UnsafeUnzipSymlink.go:31:15:31:29 | selection of Linkname | UnsafeUnzipSymlink.go:31:15:31:29 | selection of Linkname | UnsafeUnzipSymlink.go:31:15:31:29 | selection of Linkname | Unresolved path from an archive header, which may point outside the archive root, is used in $@. | UnsafeUnzipSymlink.go:31:15:31:29 | selection of Linkname | symlink creation | -| UnsafeUnzipSymlink.go:31:32:31:42 | selection of Name | UnsafeUnzipSymlink.go:31:32:31:42 | selection of Name | UnsafeUnzipSymlink.go:31:32:31:42 | selection of Name | Unresolved path from an archive header, which may point outside the archive root, is used in $@. | UnsafeUnzipSymlink.go:31:32:31:42 | selection of Name | symlink creation | -| UnsafeUnzipSymlink.go:43:25:43:35 | selection of Name | UnsafeUnzipSymlink.go:43:25:43:35 | selection of Name | UnsafeUnzipSymlink.go:43:25:43:35 | selection of Name | Unresolved path from an archive header, which may point outside the archive root, is used in $@. | UnsafeUnzipSymlink.go:43:25:43:35 | selection of Name | symlink creation | -| UnsafeUnzipSymlink.go:126:17:126:31 | selection of Linkname | UnsafeUnzipSymlink.go:126:17:126:31 | selection of Linkname | UnsafeUnzipSymlink.go:112:13:112:20 | linkName | Unresolved path from an archive header, which may point outside the archive root, is used in $@. | UnsafeUnzipSymlink.go:112:13:112:20 | linkName | symlink creation | -| UnsafeUnzipSymlink.go:126:34:126:44 | selection of Name | UnsafeUnzipSymlink.go:126:34:126:44 | selection of Name | UnsafeUnzipSymlink.go:112:23:112:30 | fileName | Unresolved path from an archive header, which may point outside the archive root, is used in $@. | UnsafeUnzipSymlink.go:112:23:112:30 | fileName | symlink creation | diff --git a/go/ql/test/query-tests/Security/CWE-022/ZipSlip.expected b/go/ql/test/query-tests/Security/CWE-022/ZipSlip.expected index bfcba5f4535b..7f19c98ab061 100644 --- a/go/ql/test/query-tests/Security/CWE-022/ZipSlip.expected +++ b/go/ql/test/query-tests/Security/CWE-022/ZipSlip.expected @@ -5,20 +5,23 @@ | tst.go:23:2:43:2 | range statement[1] | tst.go:23:2:43:2 | range statement[1] | tst.go:29:20:29:23 | path | Unsanitized archive entry, which may contain '..', is used in a $@. | tst.go:29:20:29:23 | path | file system operation | edges | UnsafeUnzipSymlinkGood.go:52:24:52:32 | definition of candidate | UnsafeUnzipSymlinkGood.go:61:53:61:61 | candidate | provenance | | -| UnsafeUnzipSymlinkGood.go:61:53:61:61 | candidate | UnsafeUnzipSymlinkGood.go:61:31:61:62 | call to Join | provenance | FunctionModel | +| UnsafeUnzipSymlinkGood.go:61:53:61:61 | candidate | UnsafeUnzipSymlinkGood.go:61:31:61:62 | call to Join | provenance | FunctionModel Sink:MaD:3 | | UnsafeUnzipSymlinkGood.go:72:3:72:25 | ... := ...[0] | UnsafeUnzipSymlinkGood.go:76:24:76:38 | selection of Linkname | provenance | | | UnsafeUnzipSymlinkGood.go:72:3:72:25 | ... := ...[0] | UnsafeUnzipSymlinkGood.go:76:70:76:80 | selection of Name | provenance | | | UnsafeUnzipSymlinkGood.go:76:24:76:38 | selection of Linkname | UnsafeUnzipSymlinkGood.go:52:24:52:32 | definition of candidate | provenance | | | UnsafeUnzipSymlinkGood.go:76:70:76:80 | selection of Name | UnsafeUnzipSymlinkGood.go:52:24:52:32 | definition of candidate | provenance | | | ZipSlip.go:11:2:15:2 | range statement[1] | ZipSlip.go:12:24:12:29 | selection of Name | provenance | | -| ZipSlip.go:12:3:12:30 | ... := ...[0] | ZipSlip.go:14:20:14:20 | p | provenance | | -| ZipSlip.go:12:24:12:29 | selection of Name | ZipSlip.go:12:3:12:30 | ... := ...[0] | provenance | MaD:1 | +| ZipSlip.go:12:3:12:30 | ... := ...[0] | ZipSlip.go:14:20:14:20 | p | provenance | Sink:MaD:1 | +| ZipSlip.go:12:24:12:29 | selection of Name | ZipSlip.go:12:3:12:30 | ... := ...[0] | provenance | MaD:4 | | tarslip.go:15:2:15:30 | ... := ...[0] | tarslip.go:16:23:16:33 | selection of Name | provenance | | -| tarslip.go:16:23:16:33 | selection of Name | tarslip.go:16:14:16:34 | call to Dir | provenance | MaD:2 | -| tst.go:23:2:43:2 | range statement[1] | tst.go:29:20:29:23 | path | provenance | | +| tarslip.go:16:23:16:33 | selection of Name | tarslip.go:16:14:16:34 | call to Dir | provenance | MaD:5 Sink:MaD:2 | +| tst.go:23:2:43:2 | range statement[1] | tst.go:29:20:29:23 | path | provenance | Sink:MaD:1 | models -| 1 | Summary: path/filepath; ; false; Abs; ; ; Argument[0]; ReturnValue[0]; taint; manual | -| 2 | Summary: path; ; false; Dir; ; ; Argument[0]; ReturnValue; taint; manual | +| 1 | Sink: io/ioutil; ; false; WriteFile; ; ; Argument[0]; path-injection; manual | +| 2 | Sink: os; ; false; MkdirAll; ; ; Argument[0]; path-injection; manual | +| 3 | Sink: os; ; false; Readlink; ; ; Argument[0]; path-injection; manual | +| 4 | Summary: path/filepath; ; false; Abs; ; ; Argument[0]; ReturnValue[0]; taint; manual | +| 5 | Summary: path; ; false; Dir; ; ; Argument[0]; ReturnValue; taint; manual | nodes | UnsafeUnzipSymlinkGood.go:52:24:52:32 | definition of candidate | semmle.label | definition of candidate | | UnsafeUnzipSymlinkGood.go:61:31:61:62 | call to Join | semmle.label | call to Join | diff --git a/go/ql/test/query-tests/Security/CWE-078/CommandInjection.expected b/go/ql/test/query-tests/Security/CWE-078/CommandInjection.expected index 654bef77c22c..85e1a2e53f6b 100644 --- a/go/ql/test/query-tests/Security/CWE-078/CommandInjection.expected +++ b/go/ql/test/query-tests/Security/CWE-078/CommandInjection.expected @@ -39,7 +39,7 @@ edges | CommandInjection2.go:44:67:44:75 | imageName | CommandInjection2.go:44:34:44:88 | []type{args} [array] | provenance | | | CommandInjection2.go:44:67:44:75 | imageName | CommandInjection2.go:44:34:44:88 | call to Sprintf | provenance | FunctionModel | | CommandInjection.go:9:13:9:19 | selection of URL | CommandInjection.go:9:13:9:27 | call to Query | provenance | Src:MaD:5 MaD:6 | -| CommandInjection.go:9:13:9:27 | call to Query | CommandInjection.go:10:22:10:28 | cmdName | provenance | | +| CommandInjection.go:9:13:9:27 | call to Query | CommandInjection.go:10:22:10:28 | cmdName | provenance | Sink:MaD:7 | | GitSubcommands.go:11:13:11:19 | selection of URL | GitSubcommands.go:11:13:11:27 | call to Query | provenance | Src:MaD:5 MaD:6 | | GitSubcommands.go:11:13:11:27 | call to Query | GitSubcommands.go:13:31:13:37 | tainted | provenance | | | GitSubcommands.go:11:13:11:27 | call to Query | GitSubcommands.go:14:31:14:37 | tainted | provenance | | @@ -155,6 +155,7 @@ models | 4 | Summary: fmt; ; true; Sprintf; ; ; Argument[1].ArrayElement; ReturnValue; taint; manual | | 5 | Source: net/http; Request; true; URL; ; ; ; remote; manual | | 6 | Summary: net/url; URL; true; Query; ; ; Argument[receiver]; ReturnValue; taint; manual | +| 7 | Sink: os/exec; ; false; Command; ; ; Argument[0]; command-injection; manual | nodes | ArgumentInjection.go:9:10:9:16 | selection of URL | semmle.label | selection of URL | | ArgumentInjection.go:9:10:9:24 | call to Query | semmle.label | call to Query | diff --git a/go/ql/test/query-tests/Security/CWE-078/StoredCommand.expected b/go/ql/test/query-tests/Security/CWE-078/StoredCommand.expected index fa97b5b423e9..b1c1822ca707 100644 --- a/go/ql/test/query-tests/Security/CWE-078/StoredCommand.expected +++ b/go/ql/test/query-tests/Security/CWE-078/StoredCommand.expected @@ -1,13 +1,15 @@ +#select +| StoredCommand.go:14:22:14:28 | cmdName | StoredCommand.go:11:2:11:27 | ... := ...[0] | StoredCommand.go:14:22:14:28 | cmdName | This command depends on a $@. | StoredCommand.go:11:2:11:27 | ... := ...[0] | stored value | edges | StoredCommand.go:11:2:11:27 | ... := ...[0] | StoredCommand.go:13:2:13:5 | rows | provenance | | | StoredCommand.go:13:2:13:5 | rows | StoredCommand.go:13:12:13:19 | &... | provenance | FunctionModel | | StoredCommand.go:13:12:13:19 | &... | StoredCommand.go:13:12:13:19 | &... | provenance | | -| StoredCommand.go:13:12:13:19 | &... | StoredCommand.go:14:22:14:28 | cmdName | provenance | | +| StoredCommand.go:13:12:13:19 | &... | StoredCommand.go:14:22:14:28 | cmdName | provenance | Sink:MaD:1 | +models +| 1 | Sink: os/exec; ; false; Command; ; ; Argument[0]; command-injection; manual | nodes | StoredCommand.go:11:2:11:27 | ... := ...[0] | semmle.label | ... := ...[0] | | StoredCommand.go:13:2:13:5 | rows | semmle.label | rows | | StoredCommand.go:13:12:13:19 | &... | semmle.label | &... | | StoredCommand.go:14:22:14:28 | cmdName | semmle.label | cmdName | subpaths -#select -| StoredCommand.go:14:22:14:28 | cmdName | StoredCommand.go:11:2:11:27 | ... := ...[0] | StoredCommand.go:14:22:14:28 | cmdName | This command depends on a $@. | StoredCommand.go:11:2:11:27 | ... := ...[0] | stored value | diff --git a/go/ql/test/query-tests/Security/CWE-078/StoredCommand.qlref b/go/ql/test/query-tests/Security/CWE-078/StoredCommand.qlref index 9d5b9126095b..16b314cb23b5 100644 --- a/go/ql/test/query-tests/Security/CWE-078/StoredCommand.qlref +++ b/go/ql/test/query-tests/Security/CWE-078/StoredCommand.qlref @@ -1 +1,2 @@ -Security/CWE-078/StoredCommand.ql +query: Security/CWE-078/StoredCommand.ql +postprocess: TestUtilities/PrettyPrintModels.ql