"fmt"
"io/ioutil"
"os"
+ "syscall"
"testing"
"time"
)
}
}
+// TestPutTouch
+// Test that when applying PUT to a block that already exists,
+// the block's modification time is updated.
+func TestPutTouch(t *testing.T) {
+ v := TempUnixVolume(t, false)
+ defer _teardown(v)
+
+ if err := v.Put(TEST_HASH, TEST_BLOCK); err != nil {
+ t.Error(err)
+ }
+
+ // We'll verify { t0 < threshold < t1 }, where t0 is the
+ // existing block's timestamp on disk before Put() and t1 is
+ // its timestamp after Put().
+ threshold := time.Now().Add(-time.Second)
+
+ // Set the stored block's mtime far enough in the past that we
+ // can see the difference between "timestamp didn't change"
+ // and "timestamp granularity is too low".
+ {
+ oldtime := time.Now().Add(-20 * time.Second).Unix()
+ if err := syscall.Utime(v.blockPath(TEST_HASH),
+ &syscall.Utimbuf{oldtime, oldtime}); err != nil {
+ t.Error(err)
+ }
+
+ // Make sure v.Mtime() agrees the above Utime really worked.
+ if t0, err := v.Mtime(TEST_HASH); err != nil || t0.IsZero() || !t0.Before(threshold) {
+ t.Errorf("Setting mtime failed: %v, %v", t0, err)
+ }
+ }
+
+ // Write the same block again.
+ if err := v.Put(TEST_HASH, TEST_BLOCK); err != nil {
+ t.Error(err)
+ }
+
+ // Verify threshold < t1
+ t1, err := v.Mtime(TEST_HASH)
+ if err != nil {
+ t.Error(err)
+ }
+ if t1.Before(threshold) {
+ t.Errorf("t1 %v must be >= threshold %v after v.Put ",
+ t1, threshold)
+ }
+}
+
// Serialization tests: launch a bunch of concurrent
//
// TODO(twp): show that the underlying Read/Write operations executed