From b19e24e9e0808f9801e5e81a74a34a016172992c Mon Sep 17 00:00:00 2001 From: terence tsao Date: Wed, 17 Oct 2018 16:00:23 -0700 Subject: [PATCH] Implemented Update Ancestor Hashes Function (#660) --- beacon-chain/types/block.go | 12 ++++++++++++ beacon-chain/types/block_test.go | 27 +++++++++++++++++++++++++++ 2 files changed, 39 insertions(+) diff --git a/beacon-chain/types/block.go b/beacon-chain/types/block.go index 90fa7b8c5..b3ab12c7a 100644 --- a/beacon-chain/types/block.go +++ b/beacon-chain/types/block.go @@ -210,6 +210,18 @@ func (b *Block) IsValid( return true } +// UpdateAncestorHashes updates the skip list of ancestor block hashes. +// i'th item is 2**i'th ancestor for i = 0, ..., 31. +func UpdateAncestorHashes(parentAncestorHashes [][32]byte, parentSlotNum uint64, parentHash [32]byte) [][32]byte { + newAncestorHashes := parentAncestorHashes + for i := range parentAncestorHashes { + if (parentSlotNum % (1 << uint64(i))) == 0 { + newAncestorHashes[i] = parentHash + } + } + return newAncestorHashes +} + // isAttestationValid validates an attestation in a block. // Attestations are cross-checked against validators in CrystallizedState.ShardAndCommitteesForSlots. // In addition, the signature is verified by constructing the list of parent hashes using ActiveState.RecentBlockHashes. diff --git a/beacon-chain/types/block_test.go b/beacon-chain/types/block_test.go index 946206466..9cb5d84a0 100644 --- a/beacon-chain/types/block_test.go +++ b/beacon-chain/types/block_test.go @@ -161,3 +161,30 @@ func TestIsAttestationSlotNumberValid(t *testing.T) { t.Errorf("attestation slot number could be less than or equal to parent block's slot number") } } + +func TestUpdateAncestorHashes(t *testing.T) { + parentHashes := make([][32]byte, 32) + for i := 0; i < 32; i++ { + parentHashes[i] = hashutil.Hash([]byte{byte(i)}) + } + + tests := []struct { + a uint64 + b [32]byte + c int + }{ + {a: 1, b: [32]byte{'a'}, c: 0}, + {a: 2, b: [32]byte{'b'}, c: 1}, + {a: 4, b: [32]byte{'c'}, c: 2}, + {a: 8, b: [32]byte{'d'}, c: 3}, + {a: 16, b: [32]byte{'e'}, c: 4}, + {a: 1 << 29, b: [32]byte{'f'}, c: 29}, + {a: 1 << 30, b: [32]byte{'g'}, c: 30}, + {a: 1 << 31, b: [32]byte{'h'}, c: 31}, + } + for _, tt := range tests { + if UpdateAncestorHashes(parentHashes, tt.a, tt.b)[tt.c] != tt.b { + t.Errorf("Failed to update ancestor hash at index %d. Wanted: %v, got: %v", tt.c, tt.b, UpdateAncestorHashes(parentHashes, tt.a, tt.b)[tt.c]) + } + } +}