@@ -19,8 +19,10 @@ fn main() {
1919** What this means:**
2020
2121- Every contract has a ` main() ` function
22- - ` main() ` must return a boolean (implicitly true here)
23- - No side effects - pure functional programming
22+ - if ` main() ` does not abort, it is considered to have succeeded; you can think
23+ of "did the function reach its end" as an implicit boolean return
24+ - No side effects other than aborts and read-only access to witness data and the transaction environment
25+ (no state)
2426
2527### Compiling Contracts
2628
@@ -31,9 +33,9 @@ SimplicityHL compiles to Simplicity bytecode through several stages:
31331 . ** Parse** - Source code to AST
32342 . ** Type Check** - Verify types are correct
33353 . ** Translate** - AST to Simplicity combinators
34- 4 . ** Commit** - Generate CMR (program hash)
3536
36- ** Result:** A 32-byte CMR that uniquely identifies your contract.
37+ ** Result:** A Simplicity program, identified by its unique 32-byte Commitment Merkle Root (CMR).
38+ See "What is the CMR?" below for more information.
3739
3840---
3941
@@ -43,15 +45,16 @@ SimplicityHL compiles to Simplicity bytecode through several stages:
4345
4446** On-chain:**
4547```
46- Transaction → Simplicity VM → Your Program + Witness → true/false
48+ Transaction → Simplicity VM → Your Program + Witness → abort/pass
4749```
4850
49- ** If true :** Transaction is valid
50- ** If false :** Transaction is rejected
51+ * ** If aborts :** Transaction is rejected
52+ * ** Otherwise :** Transaction is valid
5153
52- ** No state:** Contracts are stateless - they validate, not execute arbitrary code.
54+ ** No state:** Contracts are stateless - they validate only
5355
54- ** Termination:** All execution terminates (guaranteed to complete).
56+ ** Total:** Every program runs in finite time for all inputs (and it is efficiently possible
57+ to compute bounds on this time; see "Cost and Resource Bounds" below
5558
5659### Witness Data
5760
@@ -236,7 +239,7 @@ fn main() {
236239
237240** Use case:** Single-signature contract (P2PK)
238241
239- ### Pattern: Time Lock
242+ ### Pattern: Absolute Time Lock
240243
241244``` rust
242245fn main () {
@@ -247,7 +250,7 @@ fn main() {
247250
248251** Use case:** Timelocked payments, vesting
249252
250- ### Pattern: Time Lock with Distance
253+ ### Pattern: Relative Time Lock
251254
252255``` rust
253256fn main () {
@@ -312,17 +315,18 @@ When your contract executes, it has access to the transaction via jets.
312315
313316---
314317
315- ## Understanding CMR
318+ ## Understanding Commitment Merkle Roots (CMRs)
316319
317- ### What is CMR?
320+ ### What is the CMR?
318321
319- CMR (Commitment Merkle Root) is a 32-byte hash that uniquely identifies your Simplicity program.
322+ A CMR (Commitment Merkle Root) is a 32-byte hash that uniquely identifies your Simplicity program.
320323
321324** Properties:**
322325
323326- Same code = same CMR (deterministic)
324- - Different code = different CMR
325- - CMR commits to entire program structure
327+ - Different code = different CMR (cryptographically binding)
328+ - CMR commits to entire program structure, ** excluding** witness data and program data attached to the ` disconnect ` combinator
329+ - Same CMR = same contract = same address
326330
327331** Code reference:** [ ` rust-simplicity/src/merkle/cmr.rs ` ] ( https://github.com/BlockstreamResearch/rust-simplicity/blob/master/src/merkle/cmr.rs )
328332
@@ -332,12 +336,6 @@ CMR (Commitment Merkle Root) is a 32-byte hash that uniquely identifies your Sim
3323362 . Combinators form a Merkle tree
3333373 . CMR is the root hash
334338
335- ** Why it matters:**
336-
337- - Contracts are identified by CMR
338- - Same CMR = same contract = same address
339- - Verified during execution
340-
341339---
342340
343341## From Contract to Address
@@ -349,9 +347,7 @@ CMR (Commitment Merkle Root) is a 32-byte hash that uniquely identifies your Sim
349347```
350348Your Contract (.simf)
351349 ↓ Compile
352- Simplicity Bytecode
353- ↓ Commit
354- CMR (32 bytes)
350+ Simplicity Bytecode (identified by its CMR)
355351 ↓ Create Taproot Tree
356352 Merkle Root
357353 ↓ Combine with Internal Key
@@ -372,17 +368,19 @@ Your Contract (.simf)
372368
373369### What Gets Signed
374370
375- When spending a Simplicity contract, signatures commit to a ** sighash** .
371+ When spending a Simplicity contract, signatures commit to a ** sighash** . A sighash commits to
372+ an arbitrary set of transaction data; typically users want to use the ` SIGHASH_ALL ` sighash
373+ which commits to the entire transaction and its inputs.
376374
377375** Code reference:** [ ` rust-simplicity/src/policy/sighash.rs ` ] ( https://github.com/BlockstreamResearch/rust-simplicity/blob/master/src/policy/sighash.rs#L83-L94 )
378376
379- ** Sighash includes:**
377+ ** ` SIGHASH_ALL ` includes:**
380378
381379- All transaction inputs
382380- All transaction outputs
383381- Locktime
384382- Sequence numbers
385- - ** Genesis hash** ( network identifier)
383+ - Genesis hash (which acts as a network identifier)
386384- Spent UTXO data
387385
388386** Computation:**
@@ -405,7 +403,7 @@ let sighash: [u8; 32] = tx_env.c_tx_env().sighash_all();
405403let msg : u256 = jet :: sig_all_hash (); // Gets the sighash
406404```
407405
408- ** Why genesis hash matters: **
406+ ** Why include the genesis hash? **
409407
410408Liquid Testnet:
411409```
@@ -417,9 +415,9 @@ Liquid Mainnet:
4174151466275836220db2944ca059a3a10ef6fd2ea684b0688d2c3792968888a206003
418416```
419417
420- ** Different genesis hash = different sighash = signatures won't work across networks. **
421-
422- This prevents replay attacks .
418+ Including the genesis hash in the signature hash ensures that a given signature can
419+ only work on the network it is intended for, preventing confusion between blockchains
420+ (such as a test network and a production network) .
423421
424422---
425423
@@ -469,7 +467,7 @@ tx.input[0].witness = TxInWitness {
469467
470468** Limits:**
471469
472- - Maximum cost: ` 2^20 ` (1,048,576)
470+ - Maximum cost: ` 2^20 ` (1,048,576) weight units
473471- Exceeding this makes transaction invalid
474472
475473** Tools can check contract cost** and show resource usage statistics.
@@ -491,7 +489,7 @@ if let Some(padding) = bounds.cost.get_padding(&script_witness) {
491489}
492490```
493491
494- ** Development tools** handle padding automatically.
492+ Development tools handle padding automatically.
495493
496494---
497495
0 commit comments