Merge pull request #202 from sauyon/incomplete-hostname-fix

IncompleteHostname: disallow unescaped dot before TLD
This commit is contained in:
Max Schaefer
2019-12-10 08:17:32 +00:00
committed by GitHub Enterprise
7 changed files with 43 additions and 42 deletions

View File

@@ -13,3 +13,4 @@
|-----------------------------------------------------|------------------------------|-----------------------------------------------------------|
| Reflected cross-site scripting (`go/reflected-xss`) | Fewer results | Untrusted input flowing into an HTTP header definition is no longer flagged, since this is often harmless. |
| Useless assignment to field (`go/useless-assignment-to-field`) | Fewer false positives | The query now conservatively handles fields promoted through embedded pointer types. |
| Incomplete regular expression for hostnames (`go/incomplete-hostname-regexp`) | More results | The query now flags unescaped dots before the TLD in a hostname regex. |

View File

@@ -1,16 +1,16 @@
package main
import (
"errors"
"regexp"
"net/http"
"errors"
"net/http"
"regexp"
)
func checkRedirect(req *http.Request, via []*http.Request) error {
// BAD: the host of `url` may be controlled by an attacker
re := "^((www|beta).)?example.com/"
if matched, _ := regexp.MatchString(re, req.URL.Host); matched {
return nil
}
return errors.New("Invalid redirect")
// BAD: the host of `req.URL` may be controlled by an attacker
re := "^((www|beta).)?example.com/"
if matched, _ := regexp.MatchString(re, req.URL.Host); matched {
return nil
}
return errors.New("Invalid redirect")
}

View File

@@ -26,7 +26,7 @@ predicate isIncompleteHostNameRegexpPattern(string pattern, string hostPart) {
"(?<!\\\\)[.]" +
// immediately followed by a sequence of subdomains, perhaps with some regex characters mixed in,
// followed by a known TLD
"([():|?a-z0-9-]+(\\\\)?[.]" + commonTLD() + ")" + ".*", 1)
"(([():|?a-z0-9-]+(\\\\)?[.])?" + commonTLD() + ")" + ".*", 1)
}
class Config extends DataFlow::Configuration {

View File

@@ -1,16 +1,16 @@
package main
import (
"errors"
"regexp"
"net/http"
"errors"
"net/http"
"regexp"
)
func checkRedirectGood(req *http.Request, via []*http.Request) error {
// GOOD: the host of `url` must be `example.com`, `www.example.com` or `beta.example.com`
re := "^((www|beta)\\.)?example.com/"
if matched, _ := regexp.MatchString(re, req.URL.Host); matched {
return nil
}
return errors.New("Invalid redirect")
// GOOD: the host of `req.URL` must be `example.com`, `www.example.com` or `beta.example.com`
re := "^((www|beta)\\.)?example\\.com/"
if matched, _ := regexp.MatchString(re, req.URL.Host); matched {
return nil
}
return errors.New("Invalid redirect")
}

View File

@@ -1,9 +1,9 @@
edges
| IncompleteHostnameRegexp.go:11:11:11:39 | "^((www\|beta).)?example.com/" : string | IncompleteHostnameRegexp.go:12:41:12:42 | re |
| IncompleteHostnameRegexp.go:11:8:11:36 | "^((www\|beta).)?example.com/" : string | IncompleteHostnameRegexp.go:12:38:12:39 | re |
nodes
| IncompleteHostnameRegexp.go:11:11:11:39 | "^((www\|beta).)?example.com/" : string | semmle.label | "^((www\|beta).)?example.com/" : string |
| IncompleteHostnameRegexp.go:12:41:12:42 | re | semmle.label | re |
| IncompleteHostnameRegexp.go:11:8:11:36 | "^((www\|beta).)?example.com/" : string | semmle.label | "^((www\|beta).)?example.com/" : string |
| IncompleteHostnameRegexp.go:12:38:12:39 | re | semmle.label | re |
| main.go:12:15:12:39 | `https://www.example.com` | semmle.label | `https://www.example.com` |
#select
| IncompleteHostnameRegexp.go:11:11:11:39 | "^((www\|beta).)?example.com/" : string | IncompleteHostnameRegexp.go:11:11:11:39 | "^((www\|beta).)?example.com/" : string | IncompleteHostnameRegexp.go:12:41:12:42 | re | This regular expression has an unescaped dot before ')?example.com', so it might match more hosts than expected when used $@. | IncompleteHostnameRegexp.go:12:41:12:42 | re | here |
| main.go:12:15:12:39 | `https://www.example.com` | main.go:12:15:12:39 | `https://www.example.com` | main.go:12:15:12:39 | `https://www.example.com` | This regular expression has an unescaped dot before 'example.com', so it might match more hosts than expected when used $@. | main.go:12:15:12:39 | `https://www.example.com` | here |
| IncompleteHostnameRegexp.go:11:8:11:36 | "^((www\|beta).)?example.com/" : string | IncompleteHostnameRegexp.go:11:8:11:36 | "^((www\|beta).)?example.com/" : string | IncompleteHostnameRegexp.go:12:38:12:39 | re | This regular expression has an unescaped dot before 'com', so it might match more hosts than expected when used $@. | IncompleteHostnameRegexp.go:12:38:12:39 | re | here |
| main.go:12:15:12:39 | `https://www.example.com` | main.go:12:15:12:39 | `https://www.example.com` | main.go:12:15:12:39 | `https://www.example.com` | This regular expression has an unescaped dot before 'com', so it might match more hosts than expected when used $@. | main.go:12:15:12:39 | `https://www.example.com` | here |

View File

@@ -1,16 +1,16 @@
package main
import (
"errors"
"regexp"
"net/http"
"errors"
"net/http"
"regexp"
)
func checkRedirect(req *http.Request, via []*http.Request) error {
// BAD: the host of `url` may be controlled by an attacker
re := "^((www|beta).)?example.com/"
if matched, _ := regexp.MatchString(re, req.URL.Host); matched {
return nil
}
return errors.New("Invalid redirect")
// BAD: the host of `req.URL` may be controlled by an attacker
re := "^((www|beta).)?example.com/"
if matched, _ := regexp.MatchString(re, req.URL.Host); matched {
return nil
}
return errors.New("Invalid redirect")
}

View File

@@ -1,16 +1,16 @@
package main
import (
"errors"
"regexp"
"net/http"
"errors"
"net/http"
"regexp"
)
func checkRedirectGood(req *http.Request, via []*http.Request) error {
// GOOD: the host of `url` must be `example.com`, `www.example.com` or `beta.example.com`
re := "^((www|beta)\\.)?example.com/"
if matched, _ := regexp.MatchString(re, req.URL.Host); matched {
return nil
}
return errors.New("Invalid redirect")
// GOOD: the host of `req.URL` must be `example.com`, `www.example.com` or `beta.example.com`
re := "^((www|beta)\\.)?example\\.com/"
if matched, _ := regexp.MatchString(re, req.URL.Host); matched {
return nil
}
return errors.New("Invalid redirect")
}