Skip to content

Commit

Permalink
add fuzzing test
Browse files Browse the repository at this point in the history
  • Loading branch information
tarunKoyalwar committed Sep 29, 2023
1 parent f5132c8 commit ae4731e
Show file tree
Hide file tree
Showing 4 changed files with 411 additions and 25 deletions.
3 changes: 3 additions & 0 deletions .github/workflows/build-test.yml
Original file line number Diff line number Diff line change
Expand Up @@ -26,3 +26,6 @@ jobs:
- name: Race Condition Tests
if: ${{ matrix.os != 'windows-latest' }} # false positives in windows
run: go test -race ./...

- name: Fuzz File Read # fuzz tests need to be run separately
run: go test -fuzztime=10s -fuzz=FuzzSafeOpen -run "FuzzSafeOpen" ./file/...
74 changes: 51 additions & 23 deletions file/clean_test.go
Original file line number Diff line number Diff line change
@@ -1,34 +1,62 @@
package fileutil

import (
"path/filepath"
"io"
"os"
"strings"
"testing"
)

func FuzzCleanPath(f *testing.F) {
// // Define your custom payloads here
// customPayloads := []string{
// "../../etc/passwd",
// "/absolute/path/to/file",
// "./relative/path",
// // Add more payloads as needed
// }

// // Use each custom payload for fuzzing
// for _, payload := range customPayloads {
// f.Add(payload)
// }

f.Fuzz(func(t *testing.T, inputPath string) {
result, err := CleanPath(inputPath)
if err != nil {
t.Fatal(err)
func FuzzSafeOpen(f *testing.F) {

// ==========setup==========

bin, err := os.ReadFile("tests/path-traversal.txt")
if err != nil {
f.Fatalf("failed to read file: %s", err)
}

fuzzPayloads := strings.Split(string(bin), "\n")

file, err := os.CreateTemp("", "*")
if err != nil {
f.Fatal(err)
}
_, _ = file.WriteString("pwned!")
_ = file.Close()

defer func(tmp string) {
if err = os.Remove(tmp); err != nil {
panic(err)
}
}(file.Name())

// You can add more assertions here based on your requirements
// For example, you might want to check if the returned path is absolute
if !filepath.IsAbs(result) {
t.Errorf("CleanPath(%q) returned a non-absolute path", result)
// ==========fuzzing==========

for _, payload := range fuzzPayloads {
f.Add(strings.ReplaceAll(payload, "{FILE}", f.Name()), f.Name())

}
f.Fuzz(func(t *testing.T, fuzzPath string, targetPath string) {
cleaned, err := CleanPath(fuzzPath)
if err != nil {
// Ignore errors
return
}
if cleaned != targetPath {
// cleaned path is different from target file
// so verify if 'path' is actually valid and not random chars
result, err := SafeOpen(cleaned)
if err != nil {
// Ignore errors
return
}
defer result.Close()
bin, _ := io.ReadAll(result)
if string(bin) == "pwned!" {
t.Fatalf("pwned! cleaned=%s ,input=%s", cleaned, fuzzPath)
}
}

})
}
4 changes: 2 additions & 2 deletions file/file_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -56,8 +56,8 @@ func TestDeleteFilesOlderThan(t *testing.T) {
// create a temporary folder with a couple of files
fo, err := os.MkdirTemp("", "")
require.Nil(t, err, "couldn't create folder: %s", err)
ttl := time.Duration(5 * time.Second)
sleepTime := time.Duration(10 * time.Second)
ttl := time.Duration(1 * time.Second)
sleepTime := time.Duration(3 * time.Second)

// defer temporary folder removal
defer os.RemoveAll(fo)
Expand Down
Loading

0 comments on commit ae4731e

Please sign in to comment.