mirror of
https://github.com/Chia-Network/chia-blockchain.git
synced 2024-11-20 17:56:45 +03:00
Annotate singleton_top_layer.py (#17358)
Annotate singleton_top_layer.py.
This commit is contained in:
parent
a3099b03c4
commit
41a09e92f0
@ -1,6 +1,6 @@
|
|||||||
from __future__ import annotations
|
from __future__ import annotations
|
||||||
|
|
||||||
from typing import Iterator, List, Optional, Tuple
|
from typing import Iterator, List, Optional, Tuple, cast
|
||||||
|
|
||||||
from chia.types.blockchain_format.coin import Coin
|
from chia.types.blockchain_format.coin import Coin
|
||||||
from chia.types.blockchain_format.program import Program
|
from chia.types.blockchain_format.program import Program
|
||||||
@ -175,7 +175,8 @@ def generate_launcher_coin(coin: Coin, amount: uint64) -> Coin:
|
|||||||
# Wrap inner puzzles that are not singleton specific to strip away "truths"
|
# Wrap inner puzzles that are not singleton specific to strip away "truths"
|
||||||
def adapt_inner_to_singleton(inner_puzzle: Program) -> Program:
|
def adapt_inner_to_singleton(inner_puzzle: Program) -> Program:
|
||||||
# (a (q . inner_puzzle) (r 1))
|
# (a (q . inner_puzzle) (r 1))
|
||||||
return Program.to([2, (1, inner_puzzle), [6, 1]])
|
# TODO: Remove cast when we improve typing
|
||||||
|
return cast(Program, Program.to([2, (1, inner_puzzle), [6, 1]]))
|
||||||
|
|
||||||
|
|
||||||
def adapt_inner_puzzle_hash_to_singleton(inner_puzzle_hash: bytes32) -> bytes32:
|
def adapt_inner_puzzle_hash_to_singleton(inner_puzzle_hash: bytes32) -> bytes32:
|
||||||
@ -185,57 +186,34 @@ def adapt_inner_puzzle_hash_to_singleton(inner_puzzle_hash: bytes32) -> bytes32:
|
|||||||
|
|
||||||
# Take standard coin and amount -> launch conditions & launcher coin solution
|
# Take standard coin and amount -> launch conditions & launcher coin solution
|
||||||
def launch_conditions_and_coinsol(
|
def launch_conditions_and_coinsol(
|
||||||
coin: Coin,
|
coin: Coin, inner_puzzle: Program, comment: List[Tuple[str, str]], amount: uint64
|
||||||
inner_puzzle: Program,
|
|
||||||
comment: List[Tuple[str, str]],
|
|
||||||
amount: uint64,
|
|
||||||
) -> Tuple[List[Program], CoinSpend]:
|
) -> Tuple[List[Program], CoinSpend]:
|
||||||
if (amount % 2) == 0:
|
if (amount % 2) == 0:
|
||||||
raise ValueError("Coin amount cannot be even. Subtract one mojo.")
|
raise ValueError("Coin amount cannot be even. Subtract one mojo.")
|
||||||
|
|
||||||
launcher_coin: Coin = generate_launcher_coin(coin, amount)
|
launcher_coin = generate_launcher_coin(coin, amount)
|
||||||
curried_singleton: Program = SINGLETON_MOD.curry(
|
curried_singleton = SINGLETON_MOD.curry(
|
||||||
(SINGLETON_MOD_HASH, (launcher_coin.name(), SINGLETON_LAUNCHER_HASH)),
|
(SINGLETON_MOD_HASH, (launcher_coin.name(), SINGLETON_LAUNCHER_HASH)), inner_puzzle
|
||||||
inner_puzzle,
|
|
||||||
)
|
)
|
||||||
|
|
||||||
launcher_solution = Program.to(
|
launcher_solution = Program.to([curried_singleton.get_tree_hash(), amount, comment])
|
||||||
[
|
create_launcher = Program.to([ConditionOpcode.CREATE_COIN, SINGLETON_LAUNCHER_HASH, amount])
|
||||||
curried_singleton.get_tree_hash(),
|
|
||||||
amount,
|
|
||||||
comment,
|
|
||||||
]
|
|
||||||
)
|
|
||||||
create_launcher = Program.to(
|
|
||||||
[
|
|
||||||
ConditionOpcode.CREATE_COIN,
|
|
||||||
SINGLETON_LAUNCHER_HASH,
|
|
||||||
amount,
|
|
||||||
],
|
|
||||||
)
|
|
||||||
assert_launcher_announcement = Program.to(
|
assert_launcher_announcement = Program.to(
|
||||||
[
|
[ConditionOpcode.ASSERT_COIN_ANNOUNCEMENT, std_hash(launcher_coin.name() + launcher_solution.get_tree_hash())]
|
||||||
ConditionOpcode.ASSERT_COIN_ANNOUNCEMENT,
|
|
||||||
std_hash(launcher_coin.name() + launcher_solution.get_tree_hash()),
|
|
||||||
],
|
|
||||||
)
|
)
|
||||||
|
|
||||||
conditions = [create_launcher, assert_launcher_announcement]
|
conditions = [create_launcher, assert_launcher_announcement]
|
||||||
|
|
||||||
launcher_coin_spend = make_spend(
|
launcher_coin_spend = make_spend(launcher_coin, SINGLETON_LAUNCHER, launcher_solution)
|
||||||
launcher_coin,
|
|
||||||
SINGLETON_LAUNCHER,
|
|
||||||
launcher_solution,
|
|
||||||
)
|
|
||||||
|
|
||||||
return conditions, launcher_coin_spend
|
return conditions, launcher_coin_spend
|
||||||
|
|
||||||
|
|
||||||
# Take a coin solution, return a lineage proof for their child to use in spends
|
# Take a coin solution, return a lineage proof for their child to use in spends
|
||||||
def lineage_proof_for_coinsol(coin_spend: CoinSpend) -> LineageProof:
|
def lineage_proof_for_coinsol(coin_spend: CoinSpend) -> LineageProof:
|
||||||
parent_name: bytes32 = coin_spend.coin.parent_coin_info
|
parent_name = coin_spend.coin.parent_coin_info
|
||||||
|
|
||||||
inner_puzzle_hash: Optional[bytes32] = None
|
inner_puzzle_hash = None
|
||||||
if coin_spend.coin.puzzle_hash != SINGLETON_LAUNCHER_HASH:
|
if coin_spend.coin.puzzle_hash != SINGLETON_LAUNCHER_HASH:
|
||||||
full_puzzle = Program.from_bytes(bytes(coin_spend.puzzle_reveal))
|
full_puzzle = Program.from_bytes(bytes(coin_spend.puzzle_reveal))
|
||||||
r = full_puzzle.uncurry()
|
r = full_puzzle.uncurry()
|
||||||
@ -244,44 +222,26 @@ def lineage_proof_for_coinsol(coin_spend: CoinSpend) -> LineageProof:
|
|||||||
_, inner_puzzle = list(args.as_iter())
|
_, inner_puzzle = list(args.as_iter())
|
||||||
inner_puzzle_hash = inner_puzzle.get_tree_hash()
|
inner_puzzle_hash = inner_puzzle.get_tree_hash()
|
||||||
|
|
||||||
amount: uint64 = uint64(coin_spend.coin.amount)
|
amount = uint64(coin_spend.coin.amount)
|
||||||
|
|
||||||
return LineageProof(
|
return LineageProof(parent_name, inner_puzzle_hash, amount)
|
||||||
parent_name,
|
|
||||||
inner_puzzle_hash,
|
|
||||||
amount,
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
# Return the puzzle reveal of a singleton with specific ID and innerpuz
|
# Return the puzzle reveal of a singleton with specific ID and innerpuz
|
||||||
def puzzle_for_singleton(
|
def puzzle_for_singleton(
|
||||||
launcher_id: bytes32, inner_puz: Program, launcher_hash: bytes32 = SINGLETON_LAUNCHER_HASH
|
launcher_id: bytes32, inner_puz: Program, launcher_hash: bytes32 = SINGLETON_LAUNCHER_HASH
|
||||||
) -> Program:
|
) -> Program:
|
||||||
return SINGLETON_MOD.curry(
|
return SINGLETON_MOD.curry((SINGLETON_MOD_HASH, (launcher_id, launcher_hash)), inner_puz)
|
||||||
(SINGLETON_MOD_HASH, (launcher_id, launcher_hash)),
|
|
||||||
inner_puz,
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
# Return a solution to spend a singleton
|
# Return a solution to spend a singleton
|
||||||
def solution_for_singleton(
|
def solution_for_singleton(lineage_proof: LineageProof, amount: uint64, inner_solution: Program) -> Program:
|
||||||
lineage_proof: LineageProof,
|
|
||||||
amount: uint64,
|
|
||||||
inner_solution: Program,
|
|
||||||
) -> Program:
|
|
||||||
if lineage_proof.inner_puzzle_hash is None:
|
if lineage_proof.inner_puzzle_hash is None:
|
||||||
parent_info = [
|
parent_info = [lineage_proof.parent_name, lineage_proof.amount]
|
||||||
lineage_proof.parent_name,
|
|
||||||
lineage_proof.amount,
|
|
||||||
]
|
|
||||||
else:
|
else:
|
||||||
parent_info = [
|
parent_info = [lineage_proof.parent_name, lineage_proof.inner_puzzle_hash, lineage_proof.amount]
|
||||||
lineage_proof.parent_name,
|
# TODO: Remove cast when we improve typing
|
||||||
lineage_proof.inner_puzzle_hash,
|
return cast(Program, Program.to([parent_info, amount, inner_solution]))
|
||||||
lineage_proof.amount,
|
|
||||||
]
|
|
||||||
|
|
||||||
return Program.to([parent_info, amount, inner_solution])
|
|
||||||
|
|
||||||
|
|
||||||
# Create a coin that a singleton can claim
|
# Create a coin that a singleton can claim
|
||||||
@ -292,22 +252,20 @@ def pay_to_singleton_puzzle(launcher_id: bytes32) -> Program:
|
|||||||
# Create a coin that a singleton can claim or that can be sent to another puzzle after a specified time
|
# Create a coin that a singleton can claim or that can be sent to another puzzle after a specified time
|
||||||
def pay_to_singleton_or_delay_puzzle(launcher_id: bytes32, delay_time: uint64, delay_ph: bytes32) -> Program:
|
def pay_to_singleton_or_delay_puzzle(launcher_id: bytes32, delay_time: uint64, delay_ph: bytes32) -> Program:
|
||||||
return P2_SINGLETON_OR_DELAYED_MOD.curry(
|
return P2_SINGLETON_OR_DELAYED_MOD.curry(
|
||||||
SINGLETON_MOD_HASH,
|
SINGLETON_MOD_HASH, launcher_id, SINGLETON_LAUNCHER_HASH, delay_time, delay_ph
|
||||||
launcher_id,
|
|
||||||
SINGLETON_LAUNCHER_HASH,
|
|
||||||
delay_time,
|
|
||||||
delay_ph,
|
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
# Solution for EITHER p2_singleton or the claiming spend case for p2_singleton_or_delayed_puzhash
|
# Solution for EITHER p2_singleton or the claiming spend case for p2_singleton_or_delayed_puzhash
|
||||||
def solution_for_p2_singleton(p2_singleton_coin: Coin, singleton_inner_puzhash: bytes32) -> Program:
|
def solution_for_p2_singleton(p2_singleton_coin: Coin, singleton_inner_puzhash: bytes32) -> Program:
|
||||||
return Program.to([singleton_inner_puzhash, p2_singleton_coin.name()])
|
# TODO: Remove cast when we improve typing
|
||||||
|
return cast(Program, Program.to([singleton_inner_puzhash, p2_singleton_coin.name()]))
|
||||||
|
|
||||||
|
|
||||||
# Solution for the delayed spend case for p2_singleton_or_delayed_puzhash
|
# Solution for the delayed spend case for p2_singleton_or_delayed_puzhash
|
||||||
def solution_for_p2_delayed_puzzle(output_amount: uint64) -> Program:
|
def solution_for_p2_delayed_puzzle(output_amount: uint64) -> Program:
|
||||||
return Program.to([output_amount, []])
|
# TODO: Remove cast when we improve typing
|
||||||
|
return cast(Program, Program.to([output_amount, []]))
|
||||||
|
|
||||||
|
|
||||||
# Get announcement conditions for singleton solution and full CoinSpend for the claimed coin
|
# Get announcement conditions for singleton solution and full CoinSpend for the claimed coin
|
||||||
@ -321,17 +279,11 @@ def claim_p2_singleton(
|
|||||||
assertion = Program.to([ConditionOpcode.ASSERT_COIN_ANNOUNCEMENT, std_hash(p2_singleton_coin.name() + b"$")])
|
assertion = Program.to([ConditionOpcode.ASSERT_COIN_ANNOUNCEMENT, std_hash(p2_singleton_coin.name() + b"$")])
|
||||||
announcement = Program.to([ConditionOpcode.CREATE_PUZZLE_ANNOUNCEMENT, p2_singleton_coin.name()])
|
announcement = Program.to([ConditionOpcode.CREATE_PUZZLE_ANNOUNCEMENT, p2_singleton_coin.name()])
|
||||||
if delay_time is None or delay_ph is None:
|
if delay_time is None or delay_ph is None:
|
||||||
puzzle: Program = pay_to_singleton_puzzle(launcher_id)
|
puzzle = pay_to_singleton_puzzle(launcher_id)
|
||||||
else:
|
else:
|
||||||
puzzle = pay_to_singleton_or_delay_puzzle(
|
puzzle = pay_to_singleton_or_delay_puzzle(launcher_id, delay_time, delay_ph)
|
||||||
launcher_id,
|
|
||||||
delay_time,
|
|
||||||
delay_ph,
|
|
||||||
)
|
|
||||||
claim_coinsol = make_spend(
|
claim_coinsol = make_spend(
|
||||||
p2_singleton_coin,
|
p2_singleton_coin, puzzle, solution_for_p2_singleton(p2_singleton_coin, singleton_inner_puzhash)
|
||||||
puzzle,
|
|
||||||
solution_for_p2_singleton(p2_singleton_coin, singleton_inner_puzhash),
|
|
||||||
)
|
)
|
||||||
return assertion, announcement, claim_coinsol
|
return assertion, announcement, claim_coinsol
|
||||||
|
|
||||||
|
@ -30,7 +30,6 @@ chia.wallet.puzzles.p2_delegated_puzzle
|
|||||||
chia.wallet.puzzles.p2_delegated_puzzle_or_hidden_puzzle
|
chia.wallet.puzzles.p2_delegated_puzzle_or_hidden_puzzle
|
||||||
chia.wallet.puzzles.p2_m_of_n_delegate_direct
|
chia.wallet.puzzles.p2_m_of_n_delegate_direct
|
||||||
chia.wallet.puzzles.p2_puzzle_hash
|
chia.wallet.puzzles.p2_puzzle_hash
|
||||||
chia.wallet.puzzles.singleton_top_layer
|
|
||||||
chia.wallet.puzzles.tails
|
chia.wallet.puzzles.tails
|
||||||
chia.wallet.trading.trade_store
|
chia.wallet.trading.trade_store
|
||||||
chia.wallet.transaction_record
|
chia.wallet.transaction_record
|
||||||
|
Loading…
Reference in New Issue
Block a user