summaryrefslogtreecommitdiffhomepage
path: root/tai64n
diff options
context:
space:
mode:
Diffstat (limited to 'tai64n')
-rw-r--r--tai64n/tai64n.go26
-rw-r--r--tai64n/tai64n_test.go21
2 files changed, 47 insertions, 0 deletions
diff --git a/tai64n/tai64n.go b/tai64n/tai64n.go
new file mode 100644
index 0000000..da5257c
--- /dev/null
+++ b/tai64n/tai64n.go
@@ -0,0 +1,26 @@
+package tai64n
+
+import (
+ "bytes"
+ "encoding/binary"
+ "time"
+)
+
+const TimestampSize = 12
+const base = uint64(4611686018427387914)
+
+type Timestamp [TimestampSize]byte
+
+func Now() Timestamp {
+ var tai64n Timestamp
+ now := time.Now()
+ secs := base + uint64(now.Unix())
+ nano := uint32(now.UnixNano())
+ binary.BigEndian.PutUint64(tai64n[:], secs)
+ binary.BigEndian.PutUint32(tai64n[8:], nano)
+ return tai64n
+}
+
+func (t1 Timestamp) After(t2 Timestamp) bool {
+ return bytes.Compare(t1[:], t2[:]) > 0
+}
diff --git a/tai64n/tai64n_test.go b/tai64n/tai64n_test.go
new file mode 100644
index 0000000..389b65c
--- /dev/null
+++ b/tai64n/tai64n_test.go
@@ -0,0 +1,21 @@
+package tai64n
+
+import (
+ "testing"
+ "time"
+)
+
+/* Testing the essential property of the timestamp
+ * as used by WireGuard.
+ */
+func TestMonotonic(t *testing.T) {
+ old := Now()
+ for i := 0; i < 10000; i++ {
+ time.Sleep(time.Nanosecond)
+ next := Now()
+ if !next.After(old) {
+ t.Error("TAI64N, not monotonically increasing on nano-second scale")
+ }
+ old = next
+ }
+}