From 65cadda48653d2452a7e41a47a60d2934e8fcb07 Mon Sep 17 00:00:00 2001 From: Alex Goodman Date: Wed, 14 Feb 2024 16:06:22 -0500 Subject: [PATCH] Survive indexing dead symlinks (#2645) * survive indexing branches that start with a bad symlink Signed-off-by: Alex Goodman * add log statement Signed-off-by: Alex Goodman --------- Signed-off-by: Alex Goodman --- syft/internal/fileresolver/directory_indexer.go | 7 +++++++ syft/internal/fileresolver/directory_indexer_test.go | 12 ++++++++++++ .../test-fixtures/bad-symlinks/root/place/fd | 1 + 3 files changed, 20 insertions(+) create mode 120000 syft/internal/fileresolver/test-fixtures/bad-symlinks/root/place/fd diff --git a/syft/internal/fileresolver/directory_indexer.go b/syft/internal/fileresolver/directory_indexer.go index 088aa8b7d9f..d5f5956f5e0 100644 --- a/syft/internal/fileresolver/directory_indexer.go +++ b/syft/internal/fileresolver/directory_indexer.go @@ -176,6 +176,13 @@ func isRealPath(root string) (bool, error) { func (r *directoryIndexer) indexBranch(root string, stager *progress.Stage) ([]string, error) { rootRealPath, err := filepath.EvalSymlinks(root) if err != nil { + var pathErr *os.PathError + if errors.As(err, &pathErr) { + // we can't index the path, but we shouldn't consider this to be fatal + // TODO: known-unknowns + log.WithFields("root", root, "error", err).Trace("unable to evaluate symlink while indexing branch") + return nil, nil + } return nil, err } diff --git a/syft/internal/fileresolver/directory_indexer_test.go b/syft/internal/fileresolver/directory_indexer_test.go index 3b9378c72ce..9e677423587 100644 --- a/syft/internal/fileresolver/directory_indexer_test.go +++ b/syft/internal/fileresolver/directory_indexer_test.go @@ -222,6 +222,18 @@ func TestDirectoryIndexer_index(t *testing.T) { } } +func TestDirectoryIndexer_index_survive_badSymlink(t *testing.T) { + // test-fixtures/bad-symlinks + // ├── root + // │ ├── place + // │ │ └── fd -> ../somewhere/self/fd + // │ └── somewhere + // ... + indexer := newDirectoryIndexer("test-fixtures/bad-symlinks/root/place/fd", "test-fixtures/bad-symlinks/root/place/fd") + _, _, err := indexer.build() + require.NoError(t, err) +} + func TestDirectoryIndexer_SkipsAlreadyVisitedLinkDestinations(t *testing.T) { var observedPaths []string pathObserver := func(_, p string, _ os.FileInfo, _ error) error { diff --git a/syft/internal/fileresolver/test-fixtures/bad-symlinks/root/place/fd b/syft/internal/fileresolver/test-fixtures/bad-symlinks/root/place/fd new file mode 120000 index 00000000000..24486cb375f --- /dev/null +++ b/syft/internal/fileresolver/test-fixtures/bad-symlinks/root/place/fd @@ -0,0 +1 @@ +../somewhere/self/fd \ No newline at end of file