aboutsummaryrefslogtreecommitdiff
path: root/backup/fsck_test.go
diff options
context:
space:
mode:
Diffstat (limited to 'backup/fsck_test.go')
-rw-r--r--backup/fsck_test.go157
1 files changed, 157 insertions, 0 deletions
diff --git a/backup/fsck_test.go b/backup/fsck_test.go
new file mode 100644
index 0000000..f42dab3
--- /dev/null
+++ b/backup/fsck_test.go
@@ -0,0 +1,157 @@
+package backup
+
+import (
+ "code.laria.me/petrific/logging"
+ "code.laria.me/petrific/objects"
+ "code.laria.me/petrific/storage/memory"
+ "testing"
+)
+
+func TestHealthy(t *testing.T) {
+ st := memory.NewMemoryStorage()
+ st.Set(objid_emptyfile, objects.OTFile, obj_emptyfile)
+ st.Set(objid_fooblob, objects.OTBlob, obj_fooblob)
+ st.Set(objid_foofile, objects.OTFile, obj_foofile)
+ st.Set(objid_emptytree, objects.OTTree, obj_emptytree)
+ st.Set(objid_subtree, objects.OTTree, obj_subtree)
+ st.Set(objid_testtree, objects.OTTree, obj_testtree)
+
+ problems := make(chan FsckProblem)
+ var err error
+ go func() {
+ err = Fsck(st, nil, true, problems, logging.NewNopLog())
+ close(problems)
+ }()
+
+ for p := range problems {
+ t.Errorf("Unexpected problem: %s", p)
+ }
+
+ if err != nil {
+ t.Errorf("Unexpected error: %s", err)
+ }
+}
+
+var (
+ // snapshot with missing tree object
+ obj_corrupt_snapshot_1 = []byte("" +
+ "snapshot 162\n" +
+ "== BEGIN SNAPSHOT ==\n" +
+ "archive foo\n" +
+ "date 2018-01-06T22:42:00+01:00\n" +
+ "tree sha3-256:f000000000000000000000000000000000000000000000000000000000000000\n" +
+ "== END SNAPSHOT ==\n")
+ objid_corrupt_snapshot_1 = objects.MustParseObjectId("sha3-256:e33ad8ed4ef309099d593d249b36f2a5377dd26aeb18479695763fec514f519e")
+
+ missing_objid_corrupt_snapshot_1 = objects.MustParseObjectId("sha3-256:f000000000000000000000000000000000000000000000000000000000000000")
+
+ obj_corrupt_snapshot_2 = []byte("" +
+ "snapshot 162\n" +
+ "== BEGIN SNAPSHOT ==\n" +
+ "archive foo\n" +
+ "date 2018-01-06T22:45:00+01:00\n" +
+ "tree sha3-256:086f877d9e0760929c0a528ca3a01a7a19c03176a132cc6f4894c69b5943d543\n" +
+ "== END SNAPSHOT ==\n")
+ objid_corrupt_snapshot_2 = objects.MustParseObjectId("sha3-256:d5da78d96bb1bc7bff1f7cee509dba084b54ff4b9af0ed23a6a14437765ac81f")
+
+ obj_corrupt_tree = []byte("tree 431\n" +
+ "name=invalidhash&ref=sha3-256:8888888888888888888888888888888888888888888888888888888888888888&type=file\n" +
+ "name=invalidserialization&ref=sha3-256:7c3c1c331531a80d0e37a6066a6a4e4881eb897f1d76aeffd86a3bd96f0c054f&type=file\n" +
+ "name=lengthmismatch&ref=sha3-256:caea41322f4e02d68a15abe3a867c9ab507674a1f70abc892a162c5b3a742349&type=file\n" +
+ "name=missingobj&ref=sha3-256:ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff&type=file\n")
+ objid_corrupt_tree = objects.MustParseObjectId("sha3-256:086f877d9e0760929c0a528ca3a01a7a19c03176a132cc6f4894c69b5943d543")
+
+ invalid_objid = objects.MustParseObjectId("sha3-256:8888888888888888888888888888888888888888888888888888888888888888")
+
+ missing_objid_corrupt_tree = objects.MustParseObjectId("sha3-256:ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff")
+
+ obj_corrupt_file_invalidhash = obj_emptyfile
+ objid_corrupt_file_invalidhash = objects.MustParseObjectId("sha3-256:8888888888888888888888888888888888888888888888888888888888888888")
+
+ obj_corrupt_file_invalidserialization = []byte("file 9\nsize=123\n")
+ objid_corrupt_file_invalidserialization = objects.MustParseObjectId("sha3-256:7c3c1c331531a80d0e37a6066a6a4e4881eb897f1d76aeffd86a3bd96f0c054f")
+
+ obj_corrupt_blob_lengthmismatch = []byte("blob 2\nx\n")
+ objid_corrupt_blob_lengthmismatch = objects.MustParseObjectId("sha3-256:c9f04ca8fb21c7abb6221060b4e2a332686d0f6be872bdeb85cdc5fe3f2743ca")
+
+ obj_corrupt_file_lengthmismatch = []byte("" +
+ "file 88\n" +
+ "blob=sha3-256:c9f04ca8fb21c7abb6221060b4e2a332686d0f6be872bdeb85cdc5fe3f2743ca&size=100\n")
+ objid_corrupt_file_lengthmismatch = objects.MustParseObjectId("sha3-256:caea41322f4e02d68a15abe3a867c9ab507674a1f70abc892a162c5b3a742349")
+)
+
+func TestCorrupted(t *testing.T) {
+ st := memory.NewMemoryStorage()
+ st.Set(objid_corrupt_snapshot_1, objects.OTSnapshot, obj_corrupt_snapshot_1)
+ st.Set(objid_corrupt_snapshot_2, objects.OTSnapshot, obj_corrupt_snapshot_2)
+ st.Set(objid_corrupt_tree, objects.OTTree, obj_corrupt_tree)
+ st.Set(objid_corrupt_file_invalidhash, objects.OTFile, obj_corrupt_file_invalidhash)
+ st.Set(objid_corrupt_file_invalidserialization, objects.OTFile, obj_corrupt_file_invalidserialization)
+ st.Set(objid_corrupt_blob_lengthmismatch, objects.OTBlob, obj_corrupt_blob_lengthmismatch)
+ st.Set(objid_corrupt_file_lengthmismatch, objects.OTFile, obj_corrupt_file_lengthmismatch)
+
+ problems := make(chan FsckProblem)
+ var err error
+ go func() {
+ err = Fsck(st, nil, true, problems, logging.NewNopLog())
+ close(problems)
+ }()
+
+ var seen_snapshot_1_problem,
+ seen_invalidhash,
+ seen_invalidserialization,
+ seen_lengthmismatch,
+ seen_missing_file bool
+
+ for p := range problems {
+ if p.Id.Equals(missing_objid_corrupt_snapshot_1) && p.ProblemType == FsckStorageError {
+ seen_snapshot_1_problem = true
+ continue
+ }
+
+ if p.Id.Equals(invalid_objid) && p.ProblemType == FsckStorageError {
+ seen_invalidhash = true
+ continue
+ }
+
+ if p.Id.Equals(objid_corrupt_file_invalidserialization) && p.ProblemType == FsckDeserializationError {
+ seen_invalidserialization = true
+ continue
+ }
+
+ if p.Id.Equals(objid_corrupt_blob_lengthmismatch) &&
+ p.ProblemType == FsckUnexpectedBlobSize &&
+ p.HaveSize == 2 && p.WantSize == 100 {
+
+ seen_lengthmismatch = true
+ continue
+ }
+
+ if p.Id.Equals(missing_objid_corrupt_tree) && p.ProblemType == FsckStorageError {
+ seen_missing_file = true
+ continue
+ }
+
+ t.Errorf("Unexpected problem: %s", p)
+ }
+
+ if err != nil {
+ t.Errorf("Unexpected error: %s", err)
+ }
+
+ if !seen_snapshot_1_problem {
+ t.Error("missing problem snapshot_1_problem")
+ }
+ if !seen_invalidhash {
+ t.Error("missing problem invalidhash")
+ }
+ if !seen_invalidserialization {
+ t.Error("missing problem invalidserialization")
+ }
+ if !seen_lengthmismatch {
+ t.Error("missing problem lengthmismatch")
+ }
+ if !seen_missing_file {
+ t.Error("missing problem missing_file")
+ }
+}