def honest_attest_policy(params, step, sL, s): # Collect all attestations formed for slot s. # `state` is at w-[s+1] state = s['beacon_state'] current_epoch = get_current_epoch(state) previous_epoch = get_previous_epoch(state) # `validator_epoch` is the epoch of slot s. # - If the state is already ahead by one epoch, this is given by `previous_epoch` # - Otherwise it is `current_epoch` if state.slot == compute_start_slot_at_epoch(current_epoch): validator_epoch = previous_epoch else: validator_epoch = current_epoch active_validator_indices = get_active_validator_indices( state, validator_epoch) slot_attestations = [] for validator_index in active_validator_indices: # For each validator, check which committee they belong to (committee, committee_index, committee_slot) = get_committee_assignment(state, validator_epoch, validator_index) # If they belong to a committee attesting for slot s, we ask them to form an attestation # using `honest_attest` defined above. if committee_slot + 1 == state.slot: print("validator attesting", validator_index, "for slot", committee_slot) attestation = honest_attest(state, validator_index) slot_attestations.append(attestation) return ({'slot_attestations': slot_attestations})
def propose_policy(params, step, sL, s): start = time.time() network = s['network'] produced_blocks = [[] for i in range(0, len(network.sets))] attestation_indices = [] for info_set_index, info_set in enumerate(network.sets): if log: print("Looking at info set index =", info_set_index, "time =", time.time() - start) state = info_set.beacon_state current_epoch = specs.get_current_epoch(state) previous_epoch = specs.get_previous_epoch(state) # `validator_epoch` is the epoch of slot s-1. # - If the state is already ahead by one epoch, this is given by `previous_epoch` # - Otherwise it is `current_epoch` if state.slot == specs.compute_start_slot_at_epoch(current_epoch): validator_epoch = previous_epoch else: validator_epoch = current_epoch active_validator_indices = specs.get_active_validator_indices( state, validator_epoch) if log: print("Obtained active validator sets", time.time() - start) proposer_index = specs.get_beacon_proposer_index(state) if proposer_index not in info_set.validators: continue proposer_knowledge = nt.knowledge_set(network, proposer_index) attestations = [ net_item[1].item for net_item in proposer_knowledge["attestations"] ] attestation_indices += [ net_item[0] for net_item in proposer_knowledge["attestations"] ] if log: print("time before aggregation", time.time() - start) attestations = aggregate_attestations(state, attestations) if log: print("time after aggregation", time.time() - start) block = honest_block_proposal(state, attestations, proposer_index) if log: print("time after block proposal", time.time() - start) produced_blocks[info_set_index].append(block) if log: print("time after appending", time.time() - start) if log: print("propose_policy time = ", time.time() - start) return ({ 'blocks': produced_blocks, 'attestation_indices': attestation_indices })
def percent_attesting_previous_epoch(state): if specs.get_current_epoch(state) <= specs.GENESIS_EPOCH + 1: if log: print("not processing justification and finalization") return 0.0 previous_epoch = specs.get_previous_epoch(state) matching_target_attestations = specs.get_matching_target_attestations( state, previous_epoch) # Previous epoch return float( specs.get_attesting_balance(state, matching_target_attestations) ) / specs.get_total_active_balance(state) * 100
def attest_policy(params, step, sL, s): start = time.time() network = s['network'] produced_attestations = [[] for i in range(0, len(network.sets))] for info_set_index, info_set in enumerate(network.sets): state = info_set.beacon_state current_epoch = specs.get_current_epoch(state) previous_epoch = specs.get_previous_epoch(state) # `validator_epoch` is the epoch of slot s-1. # - If the state is already ahead by one epoch, this is given by `previous_epoch` # - Otherwise it is `current_epoch` if state.slot == specs.compute_start_slot_at_epoch(current_epoch): validator_epoch = previous_epoch else: validator_epoch = current_epoch active_validator_indices = specs.get_active_validator_indices( state, validator_epoch) number_of_committees = specs.get_committee_count_at_slot( state, state.slot - 1) for committee_index in range(number_of_committees): committee = specs.get_beacon_committee(state, state.slot - 1, committee_index) for validator_index in committee: if validator_index not in info_set.validators: continue attestation = honest_attest(state, validator_index) produced_attestations[info_set_index].append( [validator_index, attestation]) if log: print("--------------") if log: print("attest_policy time = ", time.time() - start) return ({'attestations': produced_attestations})
def honest_attest(state, validator_index): # Given state w-[s+1], validators in committees of slot s form their attestations # In several places here, we need to check whether s+1 is the first slot of a new epoch. current_epoch = get_current_epoch(state) previous_epoch = get_previous_epoch(state) # Since everyone is honest, we can assume that validators attesting during some epoch e # choose the first block of e as their target, and the first block of e-1 as their source checkpoint. # # So let's assume we are making an attestation at slot s in epoch e: # # - If the `state` variable is at epoch e, then the first block of e-1 is a checkpoint held in # `state.current_justified_checkpoint`. The target checkpoint root is obtained by calling # `get_block_root(state, current_epoch)` (since current_epoch = e). # # - If the `state` variable is at epoch e+1, then the first block of e-1 is a checkpoint held in # `state.previous_justified_checkpoint`, since in the meantime the first block of e was justified. This # is the case when s is the last slot of epoch $e$. The target checkpoint root is obtained by calling # `get_block_root(state, previous_epoch)` (since current_epoch = e+1). # # ... still here? if state.slot == compute_start_slot_at_epoch(current_epoch): # `committee_slot` is equal to s (committee, committee_index, committee_slot) = get_committee_assignment(state, previous_epoch, validator_index) # Since we are at state w-[s+1], we can get the block root of the block at slot s. block_root = get_block_root_at_slot(state, committee_slot) src_checkpoint = Checkpoint( epoch=state.previous_justified_checkpoint.epoch, root=state.previous_justified_checkpoint.root) tgt_checkpoint = Checkpoint(epoch=previous_epoch, root=get_block_root(state, previous_epoch)) else: # `committee_slot` is equal to s (committee, committee_index, committee_slot) = get_committee_assignment(state, current_epoch, validator_index) # Since we are at state w-[s+1], we can get the block root of the block at slot s. block_root = get_block_root_at_slot(state, committee_slot) src_checkpoint = Checkpoint( epoch=state.current_justified_checkpoint.epoch, root=state.current_justified_checkpoint.root) tgt_checkpoint = Checkpoint(epoch=current_epoch, root=get_block_root(state, current_epoch)) att_data = AttestationData(index=committee_index, slot=committee_slot, beacon_block_root=block_root, source=src_checkpoint, target=tgt_checkpoint) print("attestation for source", src_checkpoint.epoch, "and target", tgt_checkpoint.epoch) # For now we disregard aggregation of attestations. # Some validators are chosen as aggregators: they take a bunch of identical attestations # and join them together in one object, with `aggregation_bits` identifying which validators # are part of the aggregation. committee_size = len(committee) index_in_committee = committee.index(validator_index) aggregation_bits = Bitlist[MAX_VALIDATORS_PER_COMMITTEE](*([0] * committee_size)) aggregation_bits[ index_in_committee] = True # set the aggregation bits of the validator to True attestation = Attestation(aggregation_bits=aggregation_bits, data=att_data) return attestation