mirror of
https://github.com/securego/gosec.git
synced 2024-12-25 03:55:54 +00:00
Use the gosec issue in the go analysers
This commit is contained in:
parent
b1fd94881e
commit
f850069114
4 changed files with 42 additions and 52 deletions
16
analyzer.go
16
analyzer.go
|
@ -377,8 +377,8 @@ func (gosec *Analyzer) CheckAnalyzers(pkg *packages.Package) {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
if result != nil {
|
if result != nil {
|
||||||
if aissue, ok := result.(*analyzers.Issue); ok {
|
if aissue, ok := result.(*issue.Issue); ok {
|
||||||
gosec.updateIssues(toGosecIssue(aissue), false, []issue.SuppressionInfo{})
|
gosec.updateIssues(aissue, false, []issue.SuppressionInfo{})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -596,18 +596,6 @@ func (gosec *Analyzer) updateIssues(issue *issue.Issue, ignored bool, suppressio
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func toGosecIssue(aissue *analyzers.Issue) *issue.Issue {
|
|
||||||
return &issue.Issue{
|
|
||||||
File: aissue.File,
|
|
||||||
Line: aissue.Line,
|
|
||||||
Col: aissue.Col,
|
|
||||||
RuleID: aissue.AnalyzerID,
|
|
||||||
What: aissue.What,
|
|
||||||
Confidence: issue.Score(aissue.Confidence),
|
|
||||||
Severity: issue.Score(aissue.Severity),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Report returns the current issues discovered and the metrics about the scan
|
// Report returns the current issues discovered and the metrics about the scan
|
||||||
func (gosec *Analyzer) Report() ([]*issue.Issue, *Metrics, map[string][]Error) {
|
func (gosec *Analyzer) Report() ([]*issue.Issue, *Metrics, map[string][]Error) {
|
||||||
return gosec.issues, gosec.stats, gosec.errors
|
return gosec.issues, gosec.stats, gosec.errors
|
||||||
|
|
|
@ -15,6 +15,7 @@
|
||||||
package analyzers
|
package analyzers
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"github.com/securego/gosec/v2/issue"
|
||||||
"golang.org/x/tools/go/analysis"
|
"golang.org/x/tools/go/analysis"
|
||||||
"golang.org/x/tools/go/analysis/passes/buildssa"
|
"golang.org/x/tools/go/analysis/passes/buildssa"
|
||||||
"golang.org/x/tools/go/ssa"
|
"golang.org/x/tools/go/ssa"
|
||||||
|
@ -45,7 +46,7 @@ func runSSRF(pass *analysis.Pass) (interface{}, error) {
|
||||||
ssaResult.Logger.Printf("callee: %s\n", callee)
|
ssaResult.Logger.Printf("callee: %s\n", callee)
|
||||||
return newIssue(pass.Analyzer.Name,
|
return newIssue(pass.Analyzer.Name,
|
||||||
"not implemeted",
|
"not implemeted",
|
||||||
pass.Fset, instr.Call.Pos(), Low, High), nil
|
pass.Fset, instr.Call.Pos(), issue.Low, issue.High), nil
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -18,8 +18,10 @@ import (
|
||||||
"fmt"
|
"fmt"
|
||||||
"go/token"
|
"go/token"
|
||||||
"log"
|
"log"
|
||||||
|
"os"
|
||||||
"strconv"
|
"strconv"
|
||||||
|
|
||||||
|
"github.com/securego/gosec/v2/issue"
|
||||||
"golang.org/x/tools/go/analysis"
|
"golang.org/x/tools/go/analysis"
|
||||||
"golang.org/x/tools/go/analysis/passes/buildssa"
|
"golang.org/x/tools/go/analysis/passes/buildssa"
|
||||||
)
|
)
|
||||||
|
@ -32,32 +34,6 @@ type SSAAnalyzerResult struct {
|
||||||
SSA *buildssa.SSA
|
SSA *buildssa.SSA
|
||||||
}
|
}
|
||||||
|
|
||||||
// Score type used by severity and confidence values
|
|
||||||
// TODO: remove this duplicated type
|
|
||||||
type Score int
|
|
||||||
|
|
||||||
const (
|
|
||||||
// Low severity or confidence
|
|
||||||
Low Score = iota
|
|
||||||
// Medium severity or confidence
|
|
||||||
Medium
|
|
||||||
// High severity or confidence
|
|
||||||
High
|
|
||||||
)
|
|
||||||
|
|
||||||
// Issue is returned by a gosec rule if it discovers an issue with the scanned code.
|
|
||||||
// TODO: remove this duplicated type
|
|
||||||
type Issue struct {
|
|
||||||
Severity Score `json:"severity"` // issue severity (how problematic it is)
|
|
||||||
Confidence Score `json:"confidence"` // issue confidence (how sure we are we found it)
|
|
||||||
AnalyzerID string `json:"analyzer_id"` // Human readable explanation
|
|
||||||
What string `json:"details"` // Human readable explanation
|
|
||||||
File string `json:"file"` // File name we found it in
|
|
||||||
Code string `json:"code"` // Impacted code line
|
|
||||||
Line string `json:"line"` // Line number in file
|
|
||||||
Col string `json:"column"` // Column number in line
|
|
||||||
}
|
|
||||||
|
|
||||||
// BuildDefaultAnalyzers returns the default list of analyzers
|
// BuildDefaultAnalyzers returns the default list of analyzers
|
||||||
func BuildDefaultAnalyzers() []*analysis.Analyzer {
|
func BuildDefaultAnalyzers() []*analysis.Analyzer {
|
||||||
return []*analysis.Analyzer{
|
return []*analysis.Analyzer{
|
||||||
|
@ -78,18 +54,43 @@ func getSSAResult(pass *analysis.Pass) (*SSAAnalyzerResult, error) {
|
||||||
return ssaResult, nil
|
return ssaResult, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func newIssue(analyzerID string, desc string, fileSet *token.FileSet, pos token.Pos, severity Score, confidence Score) *Issue {
|
// newIssue creates a new gosec issue
|
||||||
|
func newIssue(analyzerID string, desc string, fileSet *token.FileSet,
|
||||||
|
pos token.Pos, severity, confidence issue.Score) *issue.Issue {
|
||||||
file := fileSet.File(pos)
|
file := fileSet.File(pos)
|
||||||
line := file.Line(pos)
|
line := file.Line(pos)
|
||||||
col := file.Position(pos).Column
|
col := file.Position(pos).Column
|
||||||
// TODO: extract the code snippet and map the CWE
|
|
||||||
return &Issue{
|
return &issue.Issue{
|
||||||
|
RuleID: analyzerID,
|
||||||
File: file.Name(),
|
File: file.Name(),
|
||||||
Line: strconv.Itoa(line),
|
Line: strconv.Itoa(line),
|
||||||
Col: strconv.Itoa(col),
|
Col: strconv.Itoa(col),
|
||||||
Severity: severity,
|
Severity: severity,
|
||||||
Confidence: confidence,
|
Confidence: confidence,
|
||||||
AnalyzerID: analyzerID,
|
|
||||||
What: desc,
|
What: desc,
|
||||||
|
Cwe: issue.GetCweByRule(analyzerID),
|
||||||
|
Code: issueCodeSnippet(fileSet, pos),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func issueCodeSnippet(fileSet *token.FileSet, pos token.Pos) string {
|
||||||
|
file := fileSet.File(pos)
|
||||||
|
|
||||||
|
start := (int64)(file.Line(pos))
|
||||||
|
if start-issue.SnippetOffset > 0 {
|
||||||
|
start = start - issue.SnippetOffset
|
||||||
|
}
|
||||||
|
end := (int64)(file.Line(pos))
|
||||||
|
end = end + issue.SnippetOffset
|
||||||
|
|
||||||
|
var code string
|
||||||
|
if file, err := os.Open(file.Name()); err == nil {
|
||||||
|
defer file.Close() // #nosec
|
||||||
|
code, err = issue.CodeSnippet(file, start, end)
|
||||||
|
if err != nil {
|
||||||
|
return err.Error()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return code
|
||||||
|
}
|
||||||
|
|
|
@ -144,11 +144,8 @@ func (c Score) String() string {
|
||||||
return "UNDEFINED"
|
return "UNDEFINED"
|
||||||
}
|
}
|
||||||
|
|
||||||
// codeSnippet extracts a code snippet based on the ast reference
|
// CodeSnippet extracts a code snippet based on the ast reference
|
||||||
func codeSnippet(file *os.File, start int64, end int64, n ast.Node) (string, error) {
|
func CodeSnippet(file *os.File, start int64, end int64) (string, error) {
|
||||||
if n == nil {
|
|
||||||
return "", fmt.Errorf("invalid AST node provided")
|
|
||||||
}
|
|
||||||
var pos int64
|
var pos int64
|
||||||
var buf bytes.Buffer
|
var buf bytes.Buffer
|
||||||
scanner := bufio.NewScanner(file)
|
scanner := bufio.NewScanner(file)
|
||||||
|
@ -189,11 +186,14 @@ func New(fobj *token.File, node ast.Node, ruleID, desc string, severity, confide
|
||||||
col := strconv.Itoa(fobj.Position(node.Pos()).Column)
|
col := strconv.Itoa(fobj.Position(node.Pos()).Column)
|
||||||
|
|
||||||
var code string
|
var code string
|
||||||
if file, err := os.Open(fobj.Name()); err == nil {
|
if node == nil {
|
||||||
|
code = "invalid AST node provided"
|
||||||
|
}
|
||||||
|
if file, err := os.Open(fobj.Name()); err == nil && node != nil {
|
||||||
defer file.Close() // #nosec
|
defer file.Close() // #nosec
|
||||||
s := codeSnippetStartLine(node, fobj)
|
s := codeSnippetStartLine(node, fobj)
|
||||||
e := codeSnippetEndLine(node, fobj)
|
e := codeSnippetEndLine(node, fobj)
|
||||||
code, err = codeSnippet(file, s, e, node)
|
code, err = CodeSnippet(file, s, e)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
code = err.Error()
|
code = err.Error()
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue