on master help sign in
Revert "Various fixes and improvements."

This reverts commit 96049c509fba2f7b35d05bddfc0cb807f53fc5b8.

commitbdbb3ccc387a3dd3dd589cc2eea8352879aa59f2 authorC. Guy Yarvin <cgyarvin@gmail.com> dateFri 22 Apr 2016, 10:38 (11 years ago) parent96049c5
135 files changed+5462−96
docs/programming/hoon/catalog.md+14−14 docs/programming/hoon/catalog/bar-core.md+29 docs/programming/hoon/catalog/bar-core/cab-door.md+69 docs/programming/hoon/catalog/bar-core/cen-core.md+41 docs/programming/hoon/catalog/bar-core/dot-trap.md+52 docs/programming/hoon/catalog/bar-core/hep-loop.md+42 docs/programming/hoon/catalog/bar-core/tar-gill.md+47 docs/programming/hoon/catalog/bar-core/tis-gate.md+42 docs/programming/hoon/catalog/buc-mold.md+26 docs/programming/hoon/catalog/buc-mold/cab-shoe.md+41 docs/programming/hoon/catalog/buc-mold/cen-book.md+42 docs/programming/hoon/catalog/buc-mold/col-bank.md+41 docs/programming/hoon/catalog/buc-mold/hep-lamb.md+35 docs/programming/hoon/catalog/buc-mold/ket-bush.md+37 docs/programming/hoon/catalog/buc-mold/pat-claw.md+39 docs/programming/hoon/catalog/buc-mold/tis-coat.md+35 docs/programming/hoon/catalog/buc-mold/wut-pick.md+45 docs/programming/hoon/catalog/cen-call.md+27 docs/programming/hoon/catalog/cen-call/cab-keep.md+34 docs/programming/hoon/catalog/cen-call/dot-lace.md+24 docs/programming/hoon/catalog/cen-call/hep-call.md+43 docs/programming/hoon/catalog/cen-call/ket-calq.md+23 docs/programming/hoon/catalog/cen-call/lus-calt.md+23 docs/programming/hoon/catalog/cen-call/sig-open.md+32 docs/programming/hoon/catalog/cen-call/tis-make.md+43 docs/programming/hoon/catalog/col-cell.md+24 docs/programming/hoon/catalog/col-cell/cab-scon.md+24 docs/programming/hoon/catalog/col-cell/hep-cons.md+42 docs/programming/hoon/catalog/col-cell/ket-conq.md+28 docs/programming/hoon/catalog/col-cell/lus-cont.md+28 docs/programming/hoon/catalog/col-cell/sig-conl.md+33 docs/programming/hoon/catalog/col-cell/tar-conp.md+36 docs/programming/hoon/catalog/dot-nock.md+11 docs/programming/hoon/catalog/dot-nock/ket-wish.md+23 docs/programming/hoon/catalog/dot-nock/lus-bump.md+29 docs/programming/hoon/catalog/dot-nock/tar-nock.md+38 docs/programming/hoon/catalog/dot-nock/tis-same.md+35 docs/programming/hoon/catalog/dot-nock/wut-deep.md+24 docs/programming/hoon/catalog/ket-cast.md+24 docs/programming/hoon/catalog/ket-cast/bar-iron.md+39 docs/programming/hoon/catalog/ket-cast/hep-cast.md+41 docs/programming/hoon/catalog/ket-cast/lus-like.md+25 docs/programming/hoon/catalog/ket-cast/pam-zinc.md docs/programming/hoon/catalog/ket-cast/sig-burn.md+22 docs/programming/hoon/catalog/ket-cast/tis-name.md+32 docs/programming/hoon/catalog/ket-cast/wut-lead.md+37 docs/programming/hoon/catalog/misc.md+50 docs/programming/hoon/catalog/misc/base.md docs/programming/hoon/catalog/misc/buc-bunt.md+5 docs/programming/hoon/catalog/misc/bust.md docs/programming/hoon/catalog/misc/dbug.md docs/programming/hoon/catalog/misc/hand.md docs/programming/hoon/catalog/misc/knit.md docs/programming/hoon/catalog/misc/leaf.md docs/programming/hoon/catalog/misc/limb.md docs/programming/hoon/catalog/misc/lost.md docs/programming/hoon/catalog/misc/rock.md docs/programming/hoon/catalog/misc/sand.md docs/programming/hoon/catalog/misc/tell.md docs/programming/hoon/catalog/misc/tune.md docs/programming/hoon/catalog/misc/wing.md docs/programming/hoon/catalog/misc/yell.md docs/programming/hoon/catalog/sem-make.md+22 docs/programming/hoon/catalog/sem-make/col-wad.md+30 docs/programming/hoon/catalog/sem-make/fas-nub.md+19 docs/programming/hoon/catalog/sem-make/sem-fry.md+48 docs/programming/hoon/catalog/sem-make/sig-dip.md+62 docs/programming/hoon/catalog/sig-hint.md+36 docs/programming/hoon/catalog/sig-hint/bar-show.md+27 docs/programming/hoon/catalog/sig-hint/buc-poll.md+26 docs/programming/hoon/catalog/sig-hint/cab-lurk.md+27 docs/programming/hoon/catalog/sig-hint/cen-fast.md+93 docs/programming/hoon/catalog/sig-hint/fas-funk.md+28 docs/programming/hoon/catalog/sig-hint/gal-thin.md+30 docs/programming/hoon/catalog/sig-hint/gar-hint.md+36 docs/programming/hoon/catalog/sig-hint/lus-memo.md+43 docs/programming/hoon/catalog/sig-hint/pam-dump.md+27 docs/programming/hoon/catalog/sig-hint/tis-ddup.md+34 docs/programming/hoon/catalog/sig-hint/wut-warn.md+29 docs/programming/hoon/catalog/sig-hint/zap-peep.md+29 docs/programming/hoon/catalog/tis-flow.md+31 docs/programming/hoon/catalog/tis-flow/bar-new.md+38 docs/programming/hoon/catalog/tis-flow/col-fix.md+28 docs/programming/hoon/catalog/tis-flow/dot-set.md+35 docs/programming/hoon/catalog/tis-flow/fas-var.md+35 docs/programming/hoon/catalog/tis-flow/gal-rap.md+28 docs/programming/hoon/catalog/tis-flow/gar-per.md+24 docs/programming/hoon/catalog/tis-flow/hep-nip.md+33 docs/programming/hoon/catalog/tis-flow/ket-sip.md+40 docs/programming/hoon/catalog/tis-flow/lus-pin.md+32 docs/programming/hoon/catalog/tis-flow/sem-rev.md+28 docs/programming/hoon/catalog/tis-flow/tar-aka.md+37 docs/programming/hoon/catalog/wut-test.md+31 docs/programming/hoon/catalog/wut-test/bar-or.md+30 docs/programming/hoon/catalog/wut-test/col-if.md+42 docs/programming/hoon/catalog/wut-test/dot-lest.md+39 docs/programming/hoon/catalog/wut-test/gal-deny.md+27 docs/programming/hoon/catalog/wut-test/gar-sure.md+26 docs/programming/hoon/catalog/wut-test/hep-case.md+49 docs/programming/hoon/catalog/wut-test/ket-ifcl.md+35 docs/programming/hoon/catalog/wut-test/lus-deft.md+41 docs/programming/hoon/catalog/wut-test/pam-and.md+30 docs/programming/hoon/catalog/wut-test/pat-ifat.md+31 docs/programming/hoon/catalog/wut-test/sig-ifno.md+32 docs/programming/hoon/catalog/wut-test/tis-fits.md+40 docs/programming/hoon/catalog/wut-test/zap-not.md+32 docs/programming/hoon/catalog/zap-wild.md+23 docs/programming/hoon/catalog/zap-wild/gar-wrap.md+27 docs/programming/hoon/catalog/zap-wild/tis-code.md+26 docs/programming/hoon/catalog/zap-wild/wut-need.md+27 docs/programming/hoon/catalog/zap-wild/zap-fail.md+26 docs/programming/hoon/cheat-sheets.md+9 docs/programming/hoon/cheat-sheets/hoon.md+532 docs/programming/hoon/cheat-sheets/odors.md+686 docs/programming/hoon/cheat-sheets/pronunciation.md+68 docs/programming/hoon/concepts.md+5−19 docs/programming/hoon/demo.md+2−2 docs/programming/hoon/examples.md+1−2 docs/programming/hoon/library.md+4−3 docs/programming/hoon/mint.md+27 docs/programming/hoon/noun.md+37 docs/programming/hoon/philosophy.md+19−15 docs/programming/hoon/basic.md → docs/programming/hoon/span.md+31−23 docs/programming/hoon/troubleshooting.md+1−2 docs/programming/hoon/twig.md+8−12 docs/programming/hoon/twig/atom.md+1−2 docs/programming/hoon/twig/call.md+121 docs/programming/hoon/twig/cast.md+53 docs/programming/hoon/twig/cell.md+83 docs/programming/hoon/twig/core.md+90 docs/programming/hoon/twig/flow.md+143 docs/programming/hoon/twig/limb.md+1−2 docs/programming/hoon/twig/mold.md+136 docs/programming/hoon/twig/nock.md+36 docs/programming/hoon/twig/test.md+143
docs/programming/hoon/catalog.md+14−14
@@ -1,76 +1,76 @@
11---
22sort: 10
3−title: Twig reference
3+title: Stems catalog
44---
55
6−# Twig reference
6+# Stems
77
8−#### A catalog of all twig stems:
8+#### A catalog of all Hoon stems:
99
1010<div class="book">
1111
1212## `$ buc` (mold)
1313
14−<list src="../twig/buc-mold" dataPreview="true" className="runes" childIsFragment="true"></list>
14+<list src="buc-mold" dataPreview="true" className="runes" childIsFragment="true"></list>
1515
1616---
1717
1818## `| bar` (core)
1919
20−<list src="../twig/bar-core" dataPreview="true" className="runes" childIsFragment="true"></list>
20+<list src="bar-core" dataPreview="true" className="runes" childIsFragment="true"></list>
2121
2222---
2323
2424## `: col` (cell)
2525
26−<list src="../twig/col-cell" dataPreview="true" className="runes" childIsFragment="true"></list>
26+<list src="col-cell" dataPreview="true" className="runes" childIsFragment="true"></list>
2727
2828---
2929
3030## `% cen` (call)
3131
32−<list src="../twig/cen-call" dataPreview="true" className="runes" childIsFragment="true"></list>
32+<list src="cen-call" dataPreview="true" className="runes" childIsFragment="true"></list>
3333
3434---
3535
3636## `. dot` (nock)
3737
38−<list src="../twig/dot-nock" dataPreview="true" className="runes" childIsFragment="true"></list>
38+<list src="dot-nock" dataPreview="true" className="runes" childIsFragment="true"></list>
3939
4040---
4141
4242## `^ ket` (cast)
4343
44−<list src="../twig/ket-cast" dataPreview="true" className="runes" childIsFragment="true"></list>
44+<list src="ket-cast" dataPreview="true" className="runes" childIsFragment="true"></list>
4545
4646---
4747
4848## `~ sig` (hint)
4949
50−<list src="../twig/sig-hint" dataPreview="true" className="runes" childIsFragment="true"></list>
50+<list src="sig-hint" dataPreview="true" className="runes" childIsFragment="true"></list>
5151
5252---
5353
5454## `; sem` (make)
5555
56−<list src="../twig/sem-make" dataPreview="true" className="runes" childIsFragment="true"></list>
56+<list src="sem-make" dataPreview="true" className="runes" childIsFragment="true"></list>
5757
5858---
5959
6060## `= tis` (flow)
6161
62−<list src="../twig/tis-flow" dataPreview="true" className="runes" childIsFragment="true"></list>
62+<list src="tis-flow" dataPreview="true" className="runes" childIsFragment="true"></list>
6363
6464---
6565
6666## `? wut` (test)
6767
68−<list src="../twig/wut-test" dataPreview="true" className="runes" childIsFragment="true"></list>
68+<list src="wut-test" dataPreview="true" className="runes" childIsFragment="true"></list>
6969
7070---
7171
7272## `! zap` (wild)
7373
74−<list src="../twig/zap-wild" dataPreview="true" className="runes" childIsFragment="true"></list>
74+<list src="zap-wild" dataPreview="true" className="runes" childIsFragment="true"></list>
7575
7676</div>
docs/programming/hoon/catalog/bar-core.mdnew file+29
@@ -0,0 +1,29 @@
1+---
2+sort: 1
3+---
4+
5+# `| bar` (core)
6+
7+<list dataPreview="true" className="runes" linkToFragments="true"></list>
8+
9+<kids className="runes"></kids>
10+
11+## Twigs
12+
13+```
14+|%
15+++ foot
16+ $% {$dry p/twig}
17+ {$wet p/twig}
18+ ==
19+::
20+++ twig
21+ $% {$door p/moss q/(map term foot)} :: |_
22+ {$core p/(map term foot)} :: |%
23+ {$trap p/twig} :: |.
24+ {$loop p/twig} :: |-
25+ {$gill p/moss q/twig} :: |*
26+ {$gate p/moss q/twig} :: |=
27+ ==
28+--
29+```
docs/programming/hoon/catalog/bar-core/cab-door.mdnew file+69
@@ -0,0 +1,69 @@
1+---
2+sort: 5
3+---
4+
5+# `:door, |_, "buccab", {$door p/moss q/(map term foot)}`
6+
7+Form a door, a many-armed core with payload `{sample context}`.
8+
9+## Expands to
10+
11+```
12+:new p
13+:core
14+ q
15+==
16+```
17+
18+## Syntax
19+
20+Regular: *1-fixed*, then *battery*.
21+
22+## Discussion
23+
24+A door is the general case of a gate (function). A gate is a
25+door with only one arm, the empty name `$`.
26+
27+Other languages have no real equivalent of a door, but we often
28+see the pattern of multiple functions with the same argument
29+list, or with shared argument structure. In Hoon, this shared
30+structure becomes a door.
31+
32+Calling a door is just like calling a gate, but the caller needs
33+to specify the arm. For instance, to call the gate `foo` as a
34+door, instead of `(foo bar)` we would write `~($ foo bar)`. This
35+is an irregular form for `:open($ foo bar)`, `%~`, "censig".
36+
37+## Examples
38+
39+A trivial door:
40+
41+```
42+/~zod:dojo> =mol |_ a/@ud
43+ ++ succ +(a)
44+ ++ prev (dec a)
45+ --
46+/~zod:dojo> ~(succ mol 1)
47+2
48+/~zod:dojo> ~(succ mol ~(succ mol ~(prev mol 5)))
49+6
50+```
51+
52+A more interesting door, from the kernel library:
53+
54+```
55+++ ne
56+ |_ tig=@
57+ ++ d (add tig '0')
58+ ++ x ?:((gte tig 10) (add tig 87) d)
59+ ++ v ?:((gte tig 10) (add tig 87) d)
60+ ++ w ?:(=(tig 63) '~' ?:(=(tig 62) '-' ?:((gte tig 36) (add tig 29) x)))
61+ --
62+```
63+
64+The `ne` door prints a digit in base 10, 16, 32 or 64:
65+
66+```
67+~zod:dojo> `@t`~(x ne 12)
68+'c'
69+```
docs/programming/hoon/catalog/bar-core/cen-core.mdnew file+41
@@ -0,0 +1,41 @@
1+---
2+sort: 1
3+---
4+
5+# `:core, |%, "barcen", {$core p/(map term foot)}`
6+
7+Form a core `{battery payload}` with subject as the payload.
8+
9+## Produces
10+
11+A core with battery `p`. Payload is the subject.
12+
13+## Syntax
14+
15+Regular: *battery*.
16+
17+## Discussion
18+
19+A core is like an "object" in a conventional language, but its
20+attributes (*arms*) are functions on the core, not the core and
21+an argument. A "method" on a core is an arm producing a gate.
22+gate.
23+
24+## Examples
25+
26+A trivial core:
27+
28+```
29+~zod:dojo> =foo =+ x 58
30+ |%
31+ ++ n (add 42 x)
32+ ++ g |= b/@
33+ (add b n)
34+ --
35+~zod:dojo> n.foo
36+100
37+~zod:dojo> (g.foo 1)
38+101
39+```
40+
41+In this trivial example, `g` id ther
docs/programming/hoon/catalog/bar-core/dot-trap.mdnew file+52
@@ -0,0 +1,52 @@
1+---
2+sort: 3
3+---
4+
5+# `:trap. |., "bardot", {$trap p/twig}`
6+
7+Form a trap, a core with one arm `$`.
8+
9+## Expands to
10+
11+```
12+:core
13+++ $ p
14+--
15+```
16+
17+## Syntax
18+
19+Regular: *1-fixed*.
20+
21+## Discussion
22+
23+A trap is a deferred computation.
24+
25+## Examples
26+
27+A trivial trap:
28+
29+```
30+~zod:dojo> =foo |.(42)
31+~zod:dojo> $:foo
32+42
33+~zod:dojo> (foo)
34+42
35+```
36+
37+A more interesting trap:
38+
39+```
40+~zod:dojo> =foo :var reps 10
41+ :var step 0
42+ :var outp 0
43+ :trap
44+ :if =(step reps)
45+ outp
46+ :moar(outp (add outp 2), step +(step))
47+~zod:dojo> (foo)
48+20
49+```
50+
51+Note that we can use `:moar()` or `$()` to recurse back into the
52+trap, since it's a core with an `$` arm.
docs/programming/hoon/catalog/bar-core/hep-loop.mdnew file+42
@@ -0,0 +1,42 @@
1+---
2+sort: 4
3+---
4+
5+# `:loop, |-, "barhep", {$loop p/twig}`
6+
7+Form a trap (a core with one dry arm `$`) and kick it.
8+
9+## Expands to
10+
11+```
12+:rap $
13+:core
14+++ $ p
15+--
16+```
17+
18+## Syntax
19+
20+Regular: *1-fixed*.
21+
22+## Examples
23+
24+A trivial loop doesn't even recurse:
25+
26+```
27+~zod:dojo> |-(42)
28+42
29+```
30+
31+The classic loop is a decrement:
32+
33+```
34+~zod:dojo> =foo :var a 42
35+ :var b 0
36+ :loop
37+ :if =(a +(b))
38+ b
39+ :moar(b +(b))
40+~zod:dojo> foo
41+41
42+```
docs/programming/hoon/catalog/bar-core/tar-gill.mdnew file+47
@@ -0,0 +1,47 @@
1+---
2+sort: 6
3+---
4+
5+# `:gill, |*, "bartar", {$gill p/moss q/twig}`
6+
7+Form a gill, a wet one-armed core with payload `{sample context}`.
8+
9+## Expands to
10+
11+```
12+:new p
13+:core
14++- $
15+ q
16+--
17+```
18+
19+## Syntax
20+
21+Regular: *2-fixed*.
22+
23+## Discussion
24+
25+In a normal (dry) gate, your argument is converted into the
26+sample type. In a generic (wet) gate or gill, your argument type
27+passes through the function, rather as if it was a macro (there
28+is still only one copy of the code, however).
29+
30+Genericity is a powerful and dangerous tool. Use gills only if
31+you think you know what you're doing.
32+
33+## Examples
34+
35+Wet and dry gates in a nutshell:
36+
37+```
38+~zod:dojo> =foo :gate({a/* b/*} [b a])
39+~zod:dojo> =bar :gill({a/* b/*} [b a])
40+~zod:dojo> (foo %cat %dog)
41+[6.778.724 7.627.107]
42+~zod:dojo> (bar %cat %dog)
43+[%dog %cat]
44+```
45+
46+The dry gate does not preserve the span of `a` and `b`; the wet
47+gate does.
docs/programming/hoon/catalog/bar-core/tis-gate.mdnew file+42
@@ -0,0 +1,42 @@
1+---
2+sort: 2
3+---
4+
5+# `:gate, |=, "bartis", {$gate p/moss q/twig}`
6+
7+Form a gate, a dry one-armed core with payload `{sample context}`.
8+
9+## Expands to
10+
11+```
12+:new p
13+:core
14+++ $
15+ q
16+--
17+```
18+
19+## Syntax
20+
21+Regular: *2-fixed*.
22+
23+## Discussion
24+
25+## Examples
26+
27+A trivial gate:
28+
29+```
30+~zod:dojo> =foo |=(a/@ +(a))
31+~zod:dojo> (foo 20)
32+21
33+```
34+
35+A slightly less trivial gate:
36+
37+```
38+~zod:dojo> =foo :gate {a/@ b/@}
39+ (add a b)
40+~zod:dojo> (foo 20 400)
41+420
42+```
docs/programming/hoon/catalog/buc-mold.mdnew file+26
@@ -0,0 +1,26 @@
1+---
2+sort: 2
3+---
4+
5+# `$ buc` (mold)
6+
7+<list dataPreview="true" className="runes" linkToFragments="true"></list>
8+
9+<kids className="runes"></kids>
10+
11+## Twigs
12+
13+```
14+|%
15+++ twig
16+ $% {$claw p/moss q/moss} :: $@
17+ {$shoe p/twig} :: $_
18+ {$bank p/(list moss)} :: $:
19+ {$book p/(list moss)} :: $%
20+ {$lamb p/moss q/moss} :: $-
21+ {$bush p/moss q/moss} :: $^
22+ {$pick p/(list moss)} :: $?
23+ {$coat p/term q/moss} :: $=
24+ ==
25+--
26+```
docs/programming/hoon/catalog/buc-mold/cab-shoe.mdnew file+41
@@ -0,0 +1,41 @@
1+---
2+sort: 1
3+preview: Form a mold
4+---
5+
6+# `:shoe $_ "buccab" {$shoe p/twig}`
7+
8+Form a mold which normalizes to an example.
9+
10+## Expands to
11+
12+```
13+:gate *
14+p
15+```
16+
17+## Syntax
18+
19+Regular: *1-fixed*.
20+
21+Irregular: `_foo` is `:shoe(foo)`.
22+
23+## Discussion
24+
25+A shoe discards the sample it's supposededly normalizing, and
26+produces its example instead.
27+
28+## Examples
29+
30+```
31+~zod:dojo> =foo :shoe([%foobar %moobaz])
32+
33+~zod:dojo> (foo %foo %bar)
34+[%foobar %moobaz]
35+
36+~zod:dojo> `foo`[%foobar %moobaz]
37+[%foobar %moobaz]
38+
39+~zod:dojo $:foo
40+[%foobar %moobaz]
41+```
docs/programming/hoon/catalog/buc-mold/cen-book.mdnew file+42
@@ -0,0 +1,42 @@
1+---
2+sort: 2
3+---
4+
5+# `:book, $%, "buctis", {$book p/(list {{aura @} moss})}`
6+
7+Form a mold which normalizes a union distinguished by a head atom.
8+
9+## Normalizes to
10+
11+For any item `i` in `p`, a cell whose head is the atom `q.p.i.p`,
12+and whose tail recognizes `q.i.p`.
13+
14+Void if `p` is empty.
15+
16+## Defaults to
17+
18+For the first item `i` in `p`, the cell `[q.p.i.p $:q.i.p]`.
19+Crashes if `p` is empty.
20+
21+## Syntax
22+
23+Regular form: *2-running*.
24+
25+## Discussion
26+
27+A book is a tagged union, an extremely common data model.
28+
29+Each item in a book is called a "page." Make sure the first page
30+in the book terminates, or the default will be an infinite loop!
31+
32+## Examples
33+
34+```
35+~zod:dojo> =foo :book({$foo p/@ud q/@ud} {$bar p/@ud})
36+
37+~zod:dojo> (foo [%bar 37])
38+[%bar p=37]
39+
40+~zod:dojo> $:foo
41+[%foo p=0 q=0]~
42+```
docs/programming/hoon/catalog/buc-mold/col-bank.mdnew file+41
@@ -0,0 +1,41 @@
1+---
2+sort: 3
3+---
4+
5+# `:bank, $:, "buccol", {$bank p/(list moss)}`
6+
7+Form a mold which recognizes a tuple.
8+
9+## Normalizes
10+
11+The tuple the length of `p`, normalizing each item, defaulting
12+where the tuple does not match.
13+
14+Void if `p` is empty.
15+
16+## Defaults to
17+
18+The tuple the length of `p`, defaulting each items.
19+
20+Crashes if `p` is empty.
21+
22+## Syntax
23+
24+Regular: *running*.
25+
26+Irregular: `{a b c}` is `:bank(a b c)`.
27+
28+## Examples
29+
30+```
31+~zod:dojo> =foo :bank(p/@ud q/@tas)
32+
33+~zod:dojo> (foo 33 %foo)
34+[p=33 q=%foo]
35+
36+~zod:dojo> `foo`[33 %foo]
37+[p=33 q=%foo]
38+
39+~zod:dojo> $:foo
40+[p=0 q=%$]
41+```
docs/programming/hoon/catalog/buc-mold/hep-lamb.mdnew file+35
@@ -0,0 +1,35 @@
1+---
2+sort: 4
3+---
4+
5+# `:lamb, $-, "buchep", {$lamb p/moss q/moss}`
6+
7+Form a mold which normalizes to an example gate.
8+
9+## Expands to
10+
11+```
12+:shoe
13+:iron
14+:gate p
15+$:q
16+```
17+
18+## Syntax
19+
20+Regular: *2-fixed*.
21+
22+## Discussion
23+
24+Since a lamb is a shoe, it is not useful for normalizing, just
25+for its signature. In particular, the existence of lambs does
26+let us send gates or other cores over the network!
27+
28+## Examples
29+
30+```
31+~zod:dojo> =foo :lamb($foo $bar)
32+
33+~zod:dojo> ($:foo %foo)
34+%bar
35+```
docs/programming/hoon/catalog/buc-mold/ket-bush.mdnew file+37
@@ -0,0 +1,37 @@
1+---
2+sort: 5
3+---
4+
5+# `:bush, $^, "bucket", {$bush p/moss q/moss}`
6+
7+Form a mold which normalizes a union distinguished by head depth.
8+
9+## Normalizes to
10+
11+Default, if the sample is an atom; `p`, if the head of the sample
12+is an atom; `q` otherwise.
13+
14+## Defaults to
15+
16+The default of `p`.
17+
18+## Syntax
19+
20+Regular: *2-fixed*.
21+
22+## Examples
23+
24+```
25+~zod:dojo> =a :book({$foo p/@ud q/@ud} {$bar p/@ud})
26+
27+~zod:dojo> =b :bush({a a} a)
28+
29+~zod:dojo> (b [[%bar 33] [%foo 19 22]])
30+[[%bar p=33] [%foo p=19 q=22]]
31+
32+~zod:dojo> (b [%foo 19 22])
33+[%foo p=19 q=22]
34+
35+~zod:dojo> $:b
36+[%bar p=0]
37+```
docs/programming/hoon/catalog/buc-mold/pat-claw.mdnew file+39
@@ -0,0 +1,39 @@
1+---
2+sort: 6
3+---
4+
5+# `:claw, $@, "bucpat", {$claw p/moss q/moss}`
6+
7+Form a mold which normalizes a union distinguished by depth.
8+
9+## Normalizes to
10+
11+Default, if the sample is an atom; `p`, if the head of the sample
12+is an atom; `q` otherwise.
13+
14+## Defaults to
15+
16+The default of `p`.
17+
18+## Syntax
19+
20+Regular: *2-fixed*.
21+
22+Product: a mold which applies `p` if its sample is an atom,
23+`q` if its sample is a cell.
24+
25+Regular form: *2-fixed*.
26+
27+Example:
28+```
29+~zod:dojo> =a :claw($foo :bank(p/$bar q/@ud))
30+
31+~zod:dojo> (a %foo)
32+%foo
33+
34+~zod:dojo> `a`[%bar 99]
35+[p=%bar q=99]
36+
37+~zod:dojo> $:a
38+[%foo p=0 q=0]
39+```
docs/programming/hoon/catalog/buc-mold/tis-coat.mdnew file+35
@@ -0,0 +1,35 @@
1+---
2+sort: 7
3+---
4+
5+# `:coat, $=, "buctis", {$coat p/@tas q/moss}`
6+
7+Form a mold which wraps a face around another mold.
8+
9+## Expands to
10+
11+```
12+:gate *
13+:name(p :call(q +6))
14+```
15+
16+## Syntax
17+
18+Regular: *2-fixed*.
19+
20+Irregular: `foo/bar` is `:coat(foo bar)`.
21+
22+## Discussion
23+
24+Note that the Hoon compiler is at least slightly clever about
25+compiling molds, and almost never has to actually put in a gate
26+layer (as seen in the expansion above) to apply a coat.
27+
28+## Examples
29+
30+```
31+~zod:dojo> =a :coat(p $foo)
32+
33+~zod:dojo> (a %bar)
34+p=%foo
35+```
docs/programming/hoon/catalog/buc-mold/wut-pick.mdnew file+45
@@ -0,0 +1,45 @@
1+---
2+sort: 8
3+---
4+
5+# `:pick, $?, "bucwut", {$? p/(list moss)}`
6+
7+Form a mold which normalizes a general union.
8+
9+## Normalizes to
10+
11+The first item in `p` which normalizes the sample to itself;
12+otherwise, default.
13+
14+Void, if `p` is empty.
15+
16+## Defaults to
17+
18+The first item in `p`.
19+
20+## Syntax
21+
22+Regular: *running*.
23+
24+Irregular: `?(%foo %bar)` is `$?(%foo %bar)`.
25+
26+## Discussion
27+
28+For a union of atoms, a pick is fine. For more complex nouns,
29+always try to use a book, claw or bush, at least if you expect
30+your mold to be used as a normalizer.
31+
32+## Examples
33+
34+```
35+~zod:dojo> =a ?($foo $bar $baz)
36+
37+~zod:dojo> (a %baz)
38+%baz
39+
40+~zod:dojo> (a [37 45])
41+%foo
42+
43+~zod:dojo> $:a
44+$foo
45+```
docs/programming/hoon/catalog/cen-call.mdnew file+27
@@ -0,0 +1,27 @@
1+---
2+sort: 4
3+---
4+
5+# `% cen` (call)
6+
7+<list dataPreview="true" className="runes" linkToFragments="true"></list>
8+
9+<kids className="runes"></kids>
10+
11+## Twigs
12+
13+```
14+|%
15+++ twig
16+ $% {$bunt p/twig} :: %$
17+ {$keep p/wing q/(list (pair wing twig))} :: %_
18+ {$lace p/twig q/twig} :: %.
19+ {$call p/twig q/(list twig)} :: %-
20+ {$bake p/wing q/twig r/(list (pair wing twig))} :: %*
21+ {$calq p/twig q/twig r/twig s/twig} :: %^
22+ {$calt p/twig q/twig r/twig} :: %+
23+ {$open p/wing q/twig r/(list twig)} :: %~
24+ {$make p/wing q/(list (pair wing twig))} :: %=
25+ ==
26+--
27+```
docs/programming/hoon/catalog/cen-call/cab-keep.mdnew file+34
@@ -0,0 +1,34 @@
1+---
2+sort: 2
3+---
4+
5+# `:keep, %_, centis, {$keep p/wing q/(list (pair wing seed))}`
6+
7+Take a wing (attribute path) with changes, preserving type.
8+
9+## Expands to
10+
11+:like(p :make(p q))
12+
13+## Syntax
14+
15+Regular: *1-fixed*, then *jogging*.
16+
17+## Discussion
18+
19+`:keep` is different from `:make` because `:make` can change the
20+span of a limb with mutations.
21+
22+## Examples
23+
24+```
25+~zod:dojo> =foo [p=42 q=6]
26+~zod:dojo> foo(p %bar)
27+[p=%bar q=6]
28+~zod:dojo> foo(p [55 99])
29+[p=[55 99] q=6]
30+~zod:dojo> %_(foo p %bar)
31+[p=7.496.034 99]
32+~zod:dojo> %_(foo p [55 99])
33+! nest-fail
34+```
docs/programming/hoon/catalog/cen-call/dot-lace.mdnew file+24
@@ -0,0 +1,24 @@
1+---
2+sort: 5
3+---
4+
5+# `:lace, %., "cendot", {$lace p/seed q/seed}`
6+
7+Call a gate (function), reversed.
8+
9+## Expands to
10+
11+`:call(q p)`.
12+
13+## Syntax
14+
15+Regular: *2-fixed*.
16+
17+## Examples
18+
19+```
20+~zod:dojo> =add-triple |=({a/@ b/@ c/@} :(add a b c))
21+~zod:dojo> %.([1 2 3] add-triple)
22+6
23+```
24+
docs/programming/hoon/catalog/cen-call/hep-call.mdnew file+43
@@ -0,0 +1,43 @@
1+---
2+sort: 4
3+---
4+
5+# `:call, %-, "cenhep", {$call p/seed q/seed}`
6+
7+Call a gate (function).
8+
9+## Expands to
10+
11+`:open($ p q)`.
12+
13+## Syntax
14+
15+Regular: *2-fixed*.
16+
17+Irregular: `(a)` is `$:a`; `(a b c d)` is `:call(a [b c d])`.
18+
19+## Discussion
20+
21+`$call` is a function call; `p` is the function (`gate`), `q` the
22+argument. `$call` is a special case of `$open`, and a gate is a
23+special case of a door.
24+
25+In a gate, the modified core has only one anonymous arm; in a
26+door it gets a full battery. Intuitively, a gate defines one
27+algorithm it can compute upon its sample, `+6`. A door defines
28+many such algorithms.
29+
30+In classical languages, doors correspond to groups of functions
31+with the same argument list, or at least sharing a prefix. In
32+Hoon, this shared sample is likely to be pulled into a door.
33+
34+## Examples
35+
36+```
37+~zod:dojo> =add-triple |=({a/@ b/@ c/@} :(add a b c))
38+~zod:dojo> (add-triple 1 2 3)
39+6
40+~zod:dojo> %-(add-triple [1 2 3])
41+6
42+```
43+
docs/programming/hoon/catalog/cen-call/ket-calq.mdnew file+23
@@ -0,0 +1,23 @@
1+---
2+sort: 7
3+---
4+
5+# `:calq, %^, "cenket", {$calq p/seed q/seed r/seed s/seed}`
6+
7+Call a gate (function), with a triple sample.
8+
9+## Expands to
10+
11+`:call(p [q r s])`.
12+
13+## Syntax
14+
15+Regular: *4-fixed*.
16+
17+## Examples
18+
19+```
20+~zod:dojo> =add-triple |=({a/@ b/@ c/@} :(add a b c))
21+~zod:dojo> %^(add-triple 1 2 3)
22+6
23+```
docs/programming/hoon/catalog/cen-call/lus-calt.mdnew file+23
@@ -0,0 +1,23 @@
1+---
2+sort: 6
3+---
4+
5+# `:calt, %+, "cenlus", {$calt p/seed q/seed r/seed}`
6+
7+Call a gate (function), with a cell sample.
8+
9+## Expands to
10+
11+`:call(p [q r])`.
12+
13+## Syntax
14+
15+Regular: *3-fixed*.
16+
17+## Examples
18+
19+```
20+~zod:dojo> =add-triple |=({a/@ b/@ c/@} :(add a b c))
21+~zod:dojo> %+(add-triple 1 [2 3])
22+6
23+
docs/programming/hoon/catalog/cen-call/sig-open.mdnew file+32
@@ -0,0 +1,32 @@
1+---
2+sort: 3
3+---
4+
5+# `:open, %~, "censig", {$cnsg p/wing q/twig r/twig}
6+
7+## Expands to
8+
9+```
10+:rap(p :make(q +6 r))
11+```
12+
13+## Syntax
14+
15+Regular: *3-fixed*.
16+
17+Irregular: `~(a b c)` is `%~(a b c)`; `~(a b c d e)` is `%~(a b
18+[c d e])`.
19+
20+## Discussion
21+
22+`:open` is the general case of a function call, `:call`. In
23+both, we replace the sample (`+6`) of a core. In `:call` the
24+core is a gate and we
25+
26+Most languages do not have cores, doors, or `:open`. "Just
27+learn to step outside your linear, Western way of thinking."
28+
29+## Examples
30+
31+See [`:door`](../bar-core/cab-door).
32+
docs/programming/hoon/catalog/cen-call/tis-make.mdnew file+43
@@ -0,0 +1,43 @@
1+---
2+sort: 1
3+---
4+
5+# `:make, %=, centis, {$make p/wing q/(list (pair wing seed))}`
6+
7+Take a wing (attribute path) with changes.
8+
9+## Produces
10+
11+`p`, modified by the change list `q`.
12+
13+If `p` resolves to a leg, `q` is a list of changes to that leg.
14+If `p` resolves to an arm, `q` is a list of changes to the core
15+containing that arm. We compute the arm on the modified core.
16+
17+## Syntax
18+
19+Regular: *1-fixed*, then *jogging*.
20+
21+Irregular: `foo(x 1, y 2, z 3)` is `:make(foo x 1, y 2, z 3)`.
22+
23+## Discussion
24+
25+Note that `p` is a wing, not a twig. Knowing that a function
26+call `(foo bar)` involves making `foo`, replacing its sample
27+at slot `+6` with `bar`, and taking the `$` limb, you might think
28+`(foo bar)` would mean `:(make foo +6 bar)`.
29+
30+But it's actually `:pin(foo :(make $ +2 +6 bar))`. Even if `foo`
31+is a wing, we would just be mutating `+6` within the core that
32+defines the `foo` arm. Instead we want to modify the *product*
33+of `foo` -- the gate -- so we have to pin it into the subject.
34+
35+## Examples
36+
37+```
38+~zod:dojo> =foo [p=5 q=6]
39+~zod:dojo> foo(p 42)
40+[p=42 q=6]
41+~zod:dojo> foo(+3 99)
42+[p=5 99]
43+```
docs/programming/hoon/catalog/col-cell.mdnew file+24
@@ -0,0 +1,24 @@
1+---
2+sort: 3
3+---
4+
5+# `: col` (cell)
6+
7+<list dataPreview="true" className="runes" linkToFragments="true"></list>
8+
9+<kids className="runes"></kids>
10+
11+## Twigs
12+
13+```
14+|%
15+++ twig
16+ $% {$scon p/twig q/twig} :: :_
17+ {$conq p/twig q/twig r/twig s/twig} :: :^
18+ {$cons p/twig q/twig} :: :-
19+ {$cont p/twig q/twig r/twig} :: :+
20+ {$conl p/(list twig)} :: :~
21+ {$conp p/(list twig)} :: :*
22+ ==
23+--
24+```
docs/programming/hoon/catalog/col-cell/cab-scon.mdnew file+24
@@ -0,0 +1,24 @@
1+---
2+sort: 6
3+---
4+
5+# `:scon, :_, "colcab", {$scon p/twig q/twig}`
6+
7+Construct a cell, inverted.
8+
9+## Expands to
10+
11+```
12+:cons(q p)
13+```
14+
15+## Syntax
16+
17+Regular: *2-fixed*.
18+
19+## Examples
20+
21+```
22+~zod:dojo> :_(1 2)
23+[2 1]
24+```
docs/programming/hoon/catalog/col-cell/hep-cons.mdnew file+42
@@ -0,0 +1,42 @@
1+---
2+sort: 1
3+---
4+
5+# `:cons, :-, "colhep", {$cons p/twig q/twig}`
6+
7+Construct a cell (2-tuple).
8+
9+## Produces
10+
11+The cell of `p` and `q`.
12+
13+## Syntax
14+
15+Regular: *2-fixed*.
16+
17+Irregular: `[a b]` is `:cons(a b)`.
18+
19+Irregular: `[a b c]` is `[a [b c]]`.
20+
21+Irregular: `a^b^c` is `[a b c]`.
22+
23+Irregular: `a+b` is `[%a b]`.
24+
25+Irregular: `\`a` is `[~ a]`.
26+
27+Irregular: `~[a b]` is `[a b ~]`.
28+
29+Irregular: `[a b c]~` is `[[a b c] ~]`.
30+
31+## Discussion
32+
33+Hoon twigs actually use the same "autocons" pattern as Nock
34+formulas. If you're assembling twigs (which usually only the
35+compiler does), `[a b]` is the same as `[%cons a b]`.
36+
37+## Examples
38+
39+```
40+~zod:dojo> :-(1 2)
41+[1 2]
42+```
docs/programming/hoon/catalog/col-cell/ket-conq.mdnew file+28
@@ -0,0 +1,28 @@
1+---
2+sort: 3
3+---
4+
5+# `:conq, :^, "colket", {$conq p/twig q/twig r/twig s/twig}`
6+
7+Construct a quadruple (4-tuple).
8+
9+## Expands to
10+
11+```
12+:cons(p :cons(q :cons(r s)))
13+```
14+
15+## Syntax
16+
17+Regular: *4-fixed*.
18+
19+## Examples
20+
21+```
22+/~zod:dojo> :^(1 2 3 4)
23+[1 2 3 4]
24+/~zod:dojo> :^ 5 6
25+ 7
26+ 8
27+[5 6 7 8]
28+```
docs/programming/hoon/catalog/col-cell/lus-cont.mdnew file+28
@@ -0,0 +1,28 @@
1+---
2+sort: 2
3+---
4+
5+# `:cont, :+, "collus", {$cont p/twig q/twig r/twig}`
6+
7+Construct a triple (3-tuple).
8+
9+## Expands to:
10+
11+```
12+:cons(p :cons(q r))
13+```
14+
15+## Syntax
16+
17+Regular: *3-fixed*.
18+
19+## Examples
20+
21+```
22+/~zod:dojo> :+ 1
23+ 2
24+ 3
25+[1 2 3]
26+/~zod:dojo> :+(%a ~ 'b')
27+[%a ~ 'b']
28+```
docs/programming/hoon/catalog/col-cell/sig-conl.mdnew file+33
@@ -0,0 +1,33 @@
1+---
2+sort: 5
3+---
4+
5+# `:conl, :~, "colsig", {$conl p/(list seed)}`
6+
7+Construct a null-terminated list.
8+
9+## Expands to
10+
11+```
12+|-(?~(p ~ :cons(i.p $(p t.p))))
13+```
14+
15+## Syntax
16+
17+Regular: *running*.
18+
19+## Examples
20+
21+```
22+~zod:dojo> :~(5 3 4 2 1)
23+[5 3 4 2 1 ~]
24+~zod:dojo> ~[5 3 4 2 1]
25+[5 3 4 2 1 ~]
26+~zod:dojo> :~ 5
27+ 3
28+ 4
29+ 2
30+ 1
31+ ==
32+[5 3 4 2 1 ~]
33+```
docs/programming/hoon/catalog/col-cell/tar-conp.mdnew file+36
@@ -0,0 +1,36 @@
1+---
2+sort: 4
3+---
4+
5+# `:conp, :*, "coltar" {$conp p/(list twig)}`
6+
7+Construct an n-tuple.
8+
9+## Expands to
10+
11+```
12+|-(?~(p !! ?~(t.p i.p :cons(i.p $(p t.p)))))
13+```
14+
15+## Syntax
16+
17+Regular: *running*.
18+
19+## Examples
20+```
21+/~zod:dojo> :*(5 3 4 1 4 9 0 ~ 'a')
22+[5 3 4 1 4 9 0 ~ 'a']
23+/~zod:dojo> [5 3 4 1 4 9 0 ~ 'a']
24+[5 3 4 1 4 9 0 ~ 'a']
25+/~zod:dojo> :* 5
26+ 3
27+ 4
28+ 1
29+ 4
30+ 9
31+ 0
32+ ~
33+ 'a'
34+ ==
35+[5 3 4 1 4 9 0 ~ 'a']
36+```
docs/programming/hoon/catalog/dot-nock.mdnew file+11
@@ -0,0 +1,11 @@
1+---
2+sort: 5
3+---
4+
5+# `. dot` (nock)
6+
7+##### Run some nock.
8+
9+<list dataPreview="true" className="runes" linkToFragments="true"></list>
10+
11+<kids className="runes"></kids>
docs/programming/hoon/catalog/dot-nock/ket-wish.mdnew file+23
@@ -0,0 +1,23 @@
1+---
2+sort: 5
3+---
4+
5+# `:wish, .^, "dotket", {$wish p/moss q/seed}`
6+
7+Load data from the Arvo namespace with Nock `11`.
8+
9+## Produces
10+
11+The noun whose name is `q`, cast to the icon of `p`.
12+
13+## Discussion
14+
15+Nock has no `11` instruction, of course. But the virtual Nock
16+used to run userspace code does. Nock `11` loads from a
17+typed immutable namespace defined by its virtual context.
18+
19+We don't remold dynamically nouns in a `:wish`, but we do check
20+that the type of the value nests in `p`.
21+
22+## Examples
23+
docs/programming/hoon/catalog/dot-nock/lus-bump.mdnew file+29
@@ -0,0 +1,29 @@
1+---
2+sort: 3
3+---
4+
5+# `:bump, .+, "dotlus", {$bump p/seed}`
6+
7+Increment an atom with Nock `4`.
8+
9+## Produces
10+
11+`p` plus `1` if `p` is an atom; otherwise, crashes. The product
12+atom has no aura.
13+
14+## Syntax
15+
16+Regular: *1-fixed*.
17+
18+Irregular: `+(6)` is `.+(6)`.
19+
20+## Examples
21+
22+```
23+~zod:dojo> +(6)
24+7
25+~zod:dojo> +(%foo)
26+7.303.015
27+~zod:dojo> +([1 2])
28+! nest-fail
29+```
docs/programming/hoon/catalog/dot-nock/tar-nock.mdnew file+38
@@ -0,0 +1,38 @@
1+---
2+sort: 1
3+---
4+
5+# `:nock, .*, "dottar", {$nock p/twig q/twig}`
6+
7+Compute the Nock function.
8+
9+## Produces
10+
11+Nock of formula `q` and subject `p`, with span `%noun`.
12+
13+## Syntax
14+
15+Regular: *2-fixed*.
16+
17+## Discussion
18+
19+Note that `:nock` can be used to bypass the type system,
20+though its product contains no type information. It's
21+perfectly practical to use Hoon as a typeless language.
22+
23+## Examples
24+
25+```
26+~zod:dojo> .*([20 30] [0 2])
27+20
28+~zod:dojo> .*(33 [4 0 1])
29+34
30+~zod:dojo> .*(|.(50) [9 2 0 1])
31+50
32+~zod:dojo> .*(12 [7 [`1 [4 `1]] [`2 `3 `2]])
33+[12 13 12]
34+~zod:dojo> .*(~ [5 1^4 [4 1^3]])
35+0
36+~zod:dojo> .*(~ [5 1^5 [4 1^3]])
37+1
38+```
docs/programming/hoon/catalog/dot-nock/tis-same.mdnew file+35
@@ -0,0 +1,35 @@
1+---
2+sort: 4
3+---
4+
5+# `:same, .=, "dottis", {$same p/twig q/twig}`
6+
7+Test for equality with Nock `5`.
8+
9+## Produces
10+
11+`&`, `%.y`, `0` if `p` equals `q`; otherwise `|`, `%.n`, `1`.
12+
13+## Syntax
14+
15+Regular: *2-fixed*.
16+
17+Irregular: `=(a b)` is `.=(a b)`.
18+
19+## Discussion
20+
21+Like Nock equality, `:same` tests if two nouns are the same,
22+ignoring invisible pointer structure. Because in a conventional
23+noun implementation each noun has a lazy short hash, comparisons
24+are fast unless the hash needs to be computed, or we are comparing
25+separate copies of identical nouns. (Comparing large duplicates
26+is a common cause of performance bugs.)
27+
28+## Examples
29+
30+```
31+~zod:dojo> =(0 0)
32+%.y
33+~zod:dojo> =(1 2)
34+%.n
35+```
docs/programming/hoon/catalog/dot-nock/wut-deep.mdnew file+24
@@ -0,0 +1,24 @@
1+---
2+sort: 2
3+---
4+
5+# `:deep, .?, "dotwut", {$deep p/twig}`
6+
7+Test for cell or atom with Nock `3`.
8+
9+## Produces
10+
11+`&`, `%.y`, `0` if `p` is a cell; otherwise `|`, `%.n`, `1`.
12+
13+## Syntax
14+
15+Regular: *1-fixed*.
16+
17+## Examples
18+
19+```
20+~zod:dojo> .?(~)
21+%.n
22+~zod:dojo> .?([2 3])
23+%.y
24+```
docs/programming/hoon/catalog/ket-cast.mdnew file+24
@@ -0,0 +1,24 @@
1+---
2+sort: 6
3+---
4+
5+# `^ ket` (cast)
6+
7+<list dataPreview="true" className="runes" linkToFragments="true"></list>
8+
9+<kids className="runes"></kids>
10+
11+## Twigs
12+
13+```
14+|%
15+++ twig
16+ $% {$iron p/twig} :: ^|
17+ {$like p/twig q/twig} :: ^+
18+ {$cast p/twig q/twig} :: ^-
19+ {$zinc p/twig} :: ^&
20+ {$burn p/twig} :: ^~
21+ {$name p/toga q/twig} :: ^=
22+ {$lead p/twig} :: ^?
23+ ==
24+--
docs/programming/hoon/catalog/ket-cast/bar-iron.mdnew file+39
@@ -0,0 +1,39 @@
1+---
2+sort: 5
3+---
4+
5+# `:iron ^| "ketbar" {$iron p/seed}`
6+
7+Convert a gold core to a contravariant core (write-only sample).
8+
9+## Produces
10+
11+`p` as an iron core; crash if not a gold core.
12+
13+## Syntax
14+
15+Regular: *1-fixed*.
16+
17+## Discussion
18+
19+An iron core is an opaque function (gate or door).
20+
21+Theorem: if span `x` nests within span `a`, and span `y` nests
22+within span `b`, a core accepting `b` and producing `x` nests
23+within a iron core accepting `y` and producing `a`.
24+
25+Informally, a function fits an interface if the function has a
26+more specific result and/or a less specific argument than the
27+interface.
28+
29+## Examples
30+
31+The prettyprinter shows the core metal (`.` gold, `|` iron):
32+
33+```
34+~zod:dojo> |=(@ 1)
35+<1.gcq [@ @n <250.yur 41.wda 374.hzt 100.kzl 1.ypj %151>]>
36+~zod:dojo> ^|(|=(@ 1))
37+<1|gcq [@ @n <250.yur 41.wda 374.hzt 100.kzl 1.ypj %151>]>
38+```
39+
docs/programming/hoon/catalog/ket-cast/hep-cast.mdnew file+41
@@ -0,0 +1,41 @@
1+---
2+sort: 2
3+---
4+
5+# `:cast ^- "kethep" {$cast p/moss q/seed}`
6+
7+Cast by construction (mold).
8+
9+## Expands to
10+
11+```
12+:like(:bunt(p) q)
13+```
14+
15+## Syntax
16+
17+Regular: *2-fixed*
18+
19+## Discussion
20+
21+It's a good practice to put a `:cast` at the top of every arm
22+(including gates, loops, etc). This cast is strictly necessary
23+only in the presence of head recursion (otherwise you'll get a
24+`rest-loop` error, or if you really screw up spectacularly an
25+infinite loop in the compiler).
26+
27+## Examples
28+
29+``
30+~zod:dojo> (add 90 7)
31+97
32+~zod:dojo> `@t`(add 90 7)
33+'a'
34+~zod:dojo> ^-(@t (add 90 7))
35+'a'
36+/~zod:dojo> =foo |= a/@tas
37+ ^- (unit @ta)
38+ `a
39+/~zod:dojo> (foo 97)
40+[~ ~.a]
41+```
docs/programming/hoon/catalog/ket-cast/lus-like.mdnew file+25
@@ -0,0 +1,25 @@
1+---
2+sort: 1
3+---
4+
5+# `:like ^+ "ketlus" {$like p/seed q/seed}`
6+
7+Cast by example (seed).
8+
9+## Produces
10+
11+The value of `p` with the span of `q`, if the span of `p` nests
12+within the span of `q`. Otherwise, `nest-fail`.
13+
14+## Syntax
15+
16+Regular: *2-fixed*.
17+
18+Irregular: `\`_foo\`bar` is `:like(foo bar)`.
19+
20+## Examples
21+
22+```
23+~zod:dojo> :like('text' 97)
24+'a'
25+```
docs/programming/hoon/catalog/ket-cast/pam-zinc.mdnew file

No changes to the content.

docs/programming/hoon/catalog/ket-cast/sig-burn.mdnew file+22
@@ -0,0 +1,22 @@
1+# `:burn`, `^~`, "ketsig", `{$burn p/twig}`
2+
3+Try executing `p` at compile time.
4+
5+Tries to execute `p` statically at compile time. If this
6+fails, `p` remains dynamic. Primarily useful for
7+optimization: when a value is static, `^~` can simplify the compilation.
8+
9+Regular form *1-fixed*
10+
11+Examples
12+--------
13+
14+ /~zod:dojo> (make '|-(42)')
15+ [%8 p=[%1 p=[1 42]] q=[%9 p=2 q=[%0 p=1]]]
16+ /~zod:dojo> (make '^~(|-(42))')
17+ [%1 p=42]
18+
19+Here we use `++make` to examine the nock generated for a particular
20+computation. We start with a simple kicked trap, `|-`, that just
21+generates the static value `42`. When we wrap our `|-` in a `^~` you can
22+see that our compilation is much simpler.
docs/programming/hoon/catalog/ket-cast/tis-name.mdnew file+32
@@ -0,0 +1,32 @@
1+---
2+sort: 3
3+---
4+
5+# `:name ^= "kettis" {$name p/toga q/seed}`
6+
7+Name a value.
8+
9+## Produces
10+
11+If `p` is a term, the product `q` with span `[%face p q]`. `p`
12+may also be a tuple of terms, or a term-toga pair; the span of
13+`q` must divide evenly into cells to match it.
14+
15+## Syntax
16+
17+Regular: *2-fixed*.
18+
19+Irregular: `foo=bar` is `:name(foo bar)`.
20+
21+## Examples
22+```
23+~zod:dojo> a=1
24+a=1
25+~zod:dojo> ^= a
26+ 1
27+a=1
28+~zod:dojo> [b c d]=[1 2 3 4]
29+[b=1 c=2 d=[3 4]]
30+~zod:dojo> [b c d=[x y]]=[1 2 3 4]
31+[b=1 c=2 d=[x=3 y4]]
32+```
docs/programming/hoon/catalog/ket-cast/wut-lead.mdnew file+37
@@ -0,0 +1,37 @@
1+---
2+sort: 4
3+---
4+
5+# `:lead ^? "ketwut" {$lead p/seed}`
6+
7+Convert any core to a bivariant core (opaque payload).
8+
9+## Produces
10+
11+`p` as a lead core; crash if not a core.
12+
13+## Syntax
14+
15+Regular: *1-fixed*.
16+
17+## Discussion
18+
19+A lead core is an opaque generator.
20+
21+Theorem: if span `x` nests within span `a`, a lead core producing
22+`x` nests within a lead core producing `a`.
23+
24+Informally, a more specific generator can be used as a less
25+specific generator.
26+
27+## Examples
28+
29+The prettyprinter shows the core metal (`.` gold, `?` lead):
30+
31+```
32+~zod:dojo> |=(@ 1)
33+<1.gcq [@ @n <250.yur 41.wda 374.hzt 100.kzl 1.ypj %151>]>
34+~zod:dojo> ^?(|=(@ 1))
35+<1?gcq [@ @n <250.yur 41.wda 374.hzt 100.kzl 1.ypj %151>]>
36+```
37+
docs/programming/hoon/catalog/misc.mdnew file+50
@@ -0,0 +1,50 @@
1+---
2+sort: 12
3+---
4+
5+# Irregular leaves
6+
7+<list dataPreview="true" className="runes" linkToFragments="true"></list>
8+
9+<kids className="runes"></kids>
10+
11+## Twigs
12+
13+```
14+|%
15+++ base :: base mold
16+ $@ $? $noun :: any noun
17+ $cell :: any cell
18+ $bean :: loobean
19+ $void :: no nouns
20+ $null :: ~ == 0
21+ == ::
22+ {$atom p/odor} :: atom
23+:: ::
24+++ pint {p/{p/@ q/@} q/{p/@ q/@}} :: line+column range
25+++ spot {p/path q/pint} :: range in file
26+++ woof $@(@ {$~ p/twig}) :: string w/embed
27+:: ::
28+++ tune :: complex face
29+ $: p/(map term (unit twig)) :: definitions
30+ q/(list twig) :: bridges
31+ == ::
32+:: ::
33+++ twig ::
34+ $% {$base p/base} :: base
35+ {$bust p/base} :: bunt base
36+ {$dbug p/spot q/twig} :: debug info in trace
37+ {$hand p/span q/nock} :: premade result
38+ {$knit p/(list woof)} :: assemble string
39+ {$leaf p/(pair term @)} :: symbol
40+ {$limb p/term} :: pulls limb p
41+ {$lost p/twig} :: not to be taken
42+ {$rock p/term q/*} :: fixed constant
43+ {$sand p/term q/*} :: unfixed constant
44+ {$tell p/(list twig)} :: render as tape
45+ {$tune p/$@(term tune)} :: face on subject
46+ {$wing p/wing} :: pulls p
47+ {$yell p/(list twig)} :: render as tank
48+ ==
49+--
50+```
docs/programming/hoon/catalog/misc/base.mdnew file

No changes to the content.

docs/programming/hoon/catalog/misc/buc-bunt.mdnew file+5
@@ -0,0 +1,5 @@
1+---
2+sort: 7
3+---
4+
5+`:bunt`, {$bunt p/moss}
docs/programming/hoon/catalog/misc/bust.mdnew file

No changes to the content.

docs/programming/hoon/catalog/misc/dbug.mdnew file

No changes to the content.

docs/programming/hoon/catalog/misc/hand.mdnew file

No changes to the content.

docs/programming/hoon/catalog/misc/knit.mdnew file

No changes to the content.

docs/programming/hoon/catalog/misc/leaf.mdnew file

No changes to the content.

docs/programming/hoon/catalog/misc/limb.mdnew file

No changes to the content.

docs/programming/hoon/catalog/misc/lost.mdnew file

No changes to the content.

docs/programming/hoon/catalog/misc/rock.mdnew file

No changes to the content.

docs/programming/hoon/catalog/misc/sand.mdnew file

No changes to the content.

docs/programming/hoon/catalog/misc/tell.mdnew file

No changes to the content.

docs/programming/hoon/catalog/misc/tune.mdnew file

No changes to the content.

docs/programming/hoon/catalog/misc/wing.mdnew file

No changes to the content.

docs/programming/hoon/catalog/misc/yell.mdnew file

No changes to the content.

docs/programming/hoon/catalog/sem-make.mdnew file+22
@@ -0,0 +1,22 @@
1+---
2+sort: 9
3+---
4+
5+# `; sem` (make)
6+
7+<list dataPreview="true" className="runes" linkToFragments="true"></list>
8+
9+<kids className="runes"></kids>
10+
11+## Twigs
12+
13+```
14+|%
15+++ twig
16+ $% {$wad p/twig q/(list twig)} :: ;:
17+ {$nub p/twig} :: ;/
18+ {$dip p/twig q/(list twig)} :: ;~
19+ {$fry p/twig q/twig} :: ;;
20+ ==
21+--
22+```
docs/programming/hoon/catalog/sem-make/col-wad.mdnew file+30
@@ -0,0 +1,30 @@
1+---
2+sort: 3
3+---
4+
5+# `:wad ;: "semcol" {$wad p/seed q/(list seed)}`
6+
7+Call binary function as n-ary function.
8+
9+## Expands to
10+
11+```
12+|-(?~(q !! ?~(t.q !! ?~(t.t.q :call(p i.q i.t.q) :call(p i.q $(q t.q))))))
13+```
14+
15+## Syntax
16+
17+Regular: *1-fixed*, then *running*.
18+
19+Irregular: `:(add a b c)` is `;:(add a b c)`.
20+
21+## Examples
22+
23+```
24+~zod:dojo> (add 3 (add 4 5))
25+12
26+~zod:dojo> ;:(add 3 4 5)
27+12
28+~zod:dojo> :(add 3 4 5)
29+12
30+```
docs/programming/hoon/catalog/sem-make/fas-nub.mdnew file+19
@@ -0,0 +1,19 @@
1+---
2+sort: 4
3+---
4+
5+# `:nub ;/ "semfas" {$nub p/seed}`
6+
7+Tape as XML element.
8+
9+## Expands to
10+
11+```
12+[%$ [%$ p ~] ~]
13+```
14+
15+## Examples
16+```
17+~zod/try=> :/("foo"
18+[[%$ [%$ "foo] ~] ~]
19+```
docs/programming/hoon/catalog/sem-make/sem-fry.mdnew file+48
@@ -0,0 +1,48 @@
1+---
2+sort: 1
3+---
4+
5+# `:fry ;; "semsem" {$fry p/moss q/seed}`
6+
7+Normalize with a mold, asserting fixpoint.
8+
9+## Expands to
10+
11+```
12+:pin(:name(a (p q)) :sure(=(a (p a)) a))
13+```
14+
15+## Syntax
16+
17+Regular: *2-fixed*.
18+
19+## Examples
20+
21+Fails because of auras:
22+
23+```
24+~zod:dojo> ^-(tape ~[97 98 99])
25+! nest-fail
26+! exit
27+```
28+
29+Succeeds because molds don't care about auras:
30+
31+```
32+~zod:dojo> ;;(tape ~[97 98 99])
33+"abc"
34+```
35+
36+Succeeds because the mold normalizes:
37+
38+```
39+~zod:dojo> (tape [50 51 52])
40+"23"
41+```
42+
43+Fails because not a fixpoint:
44+
45+```
46+~zod:dojo> ;;(tape [50 51 52])
47+! exit
48+```
docs/programming/hoon/catalog/sem-make/sig-dip.mdnew file+62
@@ -0,0 +1,62 @@
1+---
2+sort: 2
3+---
4+
5+# `:dip`, `;~`, "semsig" `{$dip p/seed q/(list seed)}`
6+
7+Glue a pipeline together with a product-sample adapter.
8+
9+## Produces
10+
11+The gates in `q` connected together using the gate `p`, which
12+transforms a `q` product and a `q` gate into a `q` sample.
13+
14+## Discussion
15+
16+Apparently `:dip` is a "Kleisli arrow." Whatevs. It's also
17+a close cousin of the infamous "monad." Don't let that bother
18+you either. Hoon doesn't know anything about category theory,
19+so you don't need to either.
20+
21+`:dip` is often used in parsers, but is not only for parsers.
22+
23+## Syntax
24+
25+Regular: *1-fixed*, then *running*.
26+
27+## Examples
28+
29+A simple "parser." `trip` converts a `cord` (atomic string) to
30+a `tape` (linked string).
31+
32+```
33+~zod:dojo> =cmp |=({a/tape b/$-(char tape)] `tape`?~(a ~ (weld (b i.a) t.a)))
34+~zod:dojo> ;~(cmp trip)
35+<1.xef [a=@ <374.hzt 100.kzl 1.ypj %164>]>
36+~zod:dojo> (;~(cmp trip) 'a')
37+"a"
38+```
39+
40+With just one gate in the pipeline `q`, the glue `p` is unused:
41+
42+```
43+~zod:dojo> (;~(cmp trip |=(a/@ ~[a a])) 'a')
44+"aa"
45+~zod:dojo> (;~(cmp trip |=(a/@ ~[a a])) '')
46+""
47+```
48+
49+But for multiple gates, we need it to connect the pipeline:
50+
51+```
52+~zod:dojo> (;~(cmp trip ;~(cmp |=(a/@ ~[a a]) |=(a/@ <(dec a)>))) 'b')
53+"97b"
54+~zod:dojo> (;~(cmp trip |=(a/@ ~[a a]) |=(a/@ <(dec a)>)) 'b')
55+"97b"
56+~zod:dojo> (;~(cmp trip |=(a/@ ~[a a]) |=(a/@ <(dec a)>)) '')
57+""
58+~zod:dojo> (;~(cmp trip |=(a/@ ~[a a]) |=(a/@ <(dec a)>)) 'a')
59+"96a"
60+~zod:dojo> (;~(cmp trip |=(a/@ ~[a a]) |=(a/@ <(dec a)>)) 'acd')
61+"96acd"
62+```
docs/programming/hoon/catalog/sig-hint.mdnew file+36
@@ -0,0 +1,36 @@
1+---
2+sort: 7
3+---
4+
5+# `~ sig` (hint)
6+
7+<list dataPreview="true" className="runes" linkToFragments="true"></list>
8+
9+<kids className="runes"></kids>
10+
11+## Twigs
12+
13+```
14+|%
15+++ chum :: jet hint
16+ $? lef/term :: jet name
17+ {std/term kel/@} :: kelvin version
18+ {ven/term pro/term kel/@} :: vendor and product
19+ {ven/term pro/term ver/@ kel/@} :: all of the above
20+ == ::
21+:: ::
22+++ twig ::
23+ $% {$show p/twig q/twig} :: ~|
24+ {$lurk p/twig q/twig} :: ~_
25+ {$fast p/chum q/twig r/tyre s/twig} :: ~%
26+ {$funk p/chum q/twig} :: ~/
27+ {$thin p/$@(term {p/term q/twig}) q/twig} :: ~<
28+ {$hint p/$@(term {p/term q/twig}) q/twig} :: ~>
29+ {$poll p/term q/twig} :: ~$
30+ {$memo p/@ q/twig} :: ~+
31+ {$dump p/@ud q/twig r/twig} :: ~&
32+ {$ddup p/twig q/twig} :: ~=
33+ {$warn p/@ud q/twig r/twig s/twig} :: ~?
34+ {$peep p/twig q/twig} :: ~!
35+ ==
36+--
docs/programming/hoon/catalog/sig-hint/bar-show.mdnew file+27
@@ -0,0 +1,27 @@
1+---
2+sort: 2
3+---
4+
5+# `:show ~| "sigbar" {$show p/seed q/seed}`
6+
7+Tracing printf.
8+
9+## Expands to
10+
11+`q`.
12+
13+## Convention
14+
15+Prettyprints `p` in stack trace if `q` crashes.
16+
17+## Syntax
18+
19+Regular: *2-fixed*.
20+
21+## Examples
22+
23+```
24+~zod:dojo> ~|('sample error message' !!)
25+'sample error message'
26+ford: build failed
27+```
docs/programming/hoon/catalog/sig-hint/buc-poll.mdnew file+26
@@ -0,0 +1,26 @@
1+---
2+sort: 12
3+---
4+
5+# `:poll ~$ "sigbuc" {$poll p/term q/seed}`
6+
7+Profiling hit counter.
8+
9+## Expands to
10+
11+`q`.
12+
13+## Convention
14+
15+If profiling is on, adds 1 to the hit counter for `p`.
16+
17+## Syntax
18+
19+Regular: *2-fixed*.
20+
21+## Examples
22+
23+```
24+~zod:dojo> ~$(%foo 3)
25+3
26+```
docs/programming/hoon/catalog/sig-hint/cab-lurk.mdnew file+27
@@ -0,0 +1,27 @@
1+---
2+sort: 3
3+---
4+
5+# `:lurk ~_ "sigcab" {$lurk p/seed q/seed}`
6+
7+User-formatted tracing printf.
8+
9+## Expands to
10+
11+`q`.
12+
13+## Convention
14+
15+Shows `p` in stacktrace if `q` crashes.
16+
17+## Discussion
18+
19+`p` must produce a `tank` (prettyprint source).
20+
21+## Examples
22+
23+```
24+~zod:dojo> ~_([%leaf "sample error message"] !!)
25+"sample error message"
26+ford: build failed
27+```
docs/programming/hoon/catalog/sig-hint/cen-fast.mdnew file+93
@@ -0,0 +1,93 @@
1+---
2+sort: 10
3+---
4+
5+# `:fast ~% "sigcen" {$fast p/term q/wing r/(list {term seed}) s/seed}`
6+
7+General jet hint.
8+
9+## Expands to
10+
11+`s`.
12+
13+## Convention
14+
15+Register a core with name `p`, with parent at leg `q`, exporting
16+the named formulas `r`, constructed by `s`.
17+
18+## Syntax
19+
20+Regular: *4-fixed*. For `r`, use `~` if empty. Otherwise, *jogging*
21+between opening and closing `==`.
22+
23+## Discussion
24+
25+`:fast` is for registering cores. A registered core declares its
26+formal identity to the interpreter, which may or may not be able
27+to recognize and/or accelerate it.
28+
29+Registered cores are are organized in a containment hierarchy.
30+The parent core is at any leg within the child core. When we
31+register a core, we state the leg to its parent, in the form of
32+wing `q`. We assume the parent is already registered -- as it
33+must be, if (a) we registered it on creation, (b) the child was
34+created by an arm defined on the parent.
35+
36+(Cores are actually managed by their formula/battery. Any
37+function call will create a new core with a new sample, but
38+batteries are constant. But it is not sufficient to match the
39+battery -- matching the semantics constrains the payload as well,
40+since the semantics of a battery may depend on any parent core
41+and/or payload constant.)
42+
43+The purpose of registration is always performance-related. It
44+may involve (a) a special-purpose optimizer or "jet", written
45+for a specific core and checked with a Merkle hash; (b) a
46+general-purpose hotspot optimizer or "JIT"; or (c) merely a
47+hotspot declaration for profiling.
48+
49+As always with hints, the programmer has no idea which of (a),
50+(b), and (c) will be applied. She should use `:fast`
51+indiscriminately on all hotspots, bottlenecks, etc, real or
52+suspected.
53+
54+The list `r` is a way for the Hoon programmer to help jet
55+implementors with named Nock formulas that act on the core.
56+In complex systems, jet implementations are often partial and
57+want to call back into userspace.
58+
59+The child core contains the parent, of course. When we register
60+a core, we state the leg to its parent, in the form of wing `q`.
61+We assume that the parent -- any core within the payload -- is
62+already registered.
63+
64+must already be registered.
65+The interpreter can thus
66+
67+`p` is the name of this core within its parent; `q` is a the leg
68+
69+Registers a jet in core `s` so that it can be called when that code is run.
70+
71+Regularm form: *4-fixed*
72+
73+## Examples
74+
75+Here's the AES
76+
77+ ++ aesc :: AES-256
78+ ~% %aesc + ~
79+ |%
80+ ++ en :: ECB enc
81+ ~/ %en
82+ |= {a/@I b/@H} ^- @uxH
83+ =+ ahem
84+ (be & (ex a) b)
85+ ++ de :: ECB dec
86+ ~/ %de
87+ |= {a/@I b/@H} ^- @uxH
88+ =+ ahem
89+ (be | (ix (ex a)) b)
90+ --
91+
92+Here we label the entire `++aesc` core for optimization. You can see the
93+jet in `jets/e/aesc.c`.
docs/programming/hoon/catalog/sig-hint/fas-funk.mdnew file+28
@@ -0,0 +1,28 @@
1+---
2+sort: 1
3+
4+# `:funk ~/ "sigfas" {$funk p/term q/twig}`
5+
6+Jet hint for a gate whose context is a registered core.
7+
8+## Expands to
9+
10+```
11+:fast(p +7 ~ q)
12+```
13+
14+## Syntax
15+
16+Regular: *2-fixed*.
17+
18+## Examples
19+
20+From the kernel:
21+```
22+++ add
23+ ~/ %add
24+ |= {a/@ b/@}
25+ ^- @
26+ ?: =(0 a) b
27+ $(a (dec a), b +(b))
28+```
docs/programming/hoon/catalog/sig-hint/gal-thin.mdnew file+30
@@ -0,0 +1,30 @@
1+---
2+sort: 6
3+---
4+
5+# :thin ~< "siggal" {$thin p/$@(term {p/term q/twig}) q/twig}
6+
7+Raw hint, applied to the result of computation.
8+
9+## Expands to
10+
11+`q`.
12+
13+## Syntax
14+
15+Regular: *2-fixed*. For the dynamic form, write `%term.twig`.
16+
17+## Discussion
18+
19+`:thin` is only used for jet hints (`:funk` and `:fast`) at the
20+moment; we are not telling the interpreter something about the
21+computation we're about to perform, but rather about the result.
22+
23+## Examples
24+
25+```
26+~zod:dojo> (make '~<(%a 42)')
27+[%7 p=[%1 p=42] q=[%10 p=97 q=[%0 p=1]]]
28+~zod:dojo> (make '~<(%a.+(.) 42)')
29+[%7 p=[%1 p=42] q=[%10 p=[p=97 q=[%4 p=[%0 p=1]]] q=[%0 p=1]]]
30+```
docs/programming/hoon/catalog/sig-hint/gar-hint.mdnew file+36
@@ -0,0 +1,36 @@
1+---
2+sort: 5
3+---
4+
5+# `:hint ~> "siggar", {$hint p/$@(term {p/term q/twig}) q/twig}`
6+
7+Raw hint, applied before computation.
8+
9+## Expands to
10+
11+`q`.
12+
13+## Syntax
14+
15+Regular: *2-fixed*. For the dynamic form, write `%term.twig`.
16+
17+## Discussion
18+
19+Hoon has no way of telling what hints are used and what aren't.
20+Hints are all conventions at the interpreter level.
21+
22+## Examples
23+
24+```
25+~zod:dojo> ~>(%a 42)
26+42
27+```
28+
29+Running the compiler:
30+
31+```
32+~zod:dojo> (make '~>(%a 42)')
33+[%10 p=97 q=[%1 p=42]]
34+~zod:dojo> (make '~>(%a.+(2) 42)')
35+[%10 p=[p=97 q=[%4 p=[%1 p=2]]] q=[%1 p=42]]
36+```
docs/programming/hoon/catalog/sig-hint/lus-memo.mdnew file+43
@@ -0,0 +1,43 @@
1+---
2+sort: 7
3+---
4+
5+# :memo ~+ "siglus" {$memo p/seed}`
6+
7+Cache a computation.
8+
9+## Expands to
10+
11+`p`.
12+
13+## Convention
14+
15+Caches the formula and subject of `p` in a local cache (generally
16+transient in the current event).
17+
18+## Syntax
19+
20+Regular: *1-fixed*.
21+
22+## Examples
23+
24+This may pause for a second:
25+
26+```
27+~zod:dojo> %.(25 |=(a/@ ?:((lth a 2) 1 (add $(a (sub a 2)) $(a (dec a))))))
28+121.393
29+```
30+
31+This may make you want to press ^C:
32+
33+```
34+~zod:dojo> %.(30 |=(a/@ ?:((lth a 2) 1 (add $(a (sub a 2)) $(a (dec a))))))
35+1.346.269
36+```
37+
38+This should work fine:
39+
40+```
41+~zod:dojo> %.(100 |=(a/@ ~+(?:((lth a 2) 1 (add $(a (sub a 2)) $(a (dec a)))))))
42+573.147.844.013.817.084.101
43+```
docs/programming/hoon/catalog/sig-hint/pam-dump.mdnew file+27
@@ -0,0 +1,27 @@
1+---
2+sort: 1
3+---
4+
5+# `:dump ~& "sigpam" {$dump p/seed q/seed}`
6+
7+Debugging printf.
8+
9+## Expands to
10+
11+`q`.
12+
13+## Convention
14+
15+Prettyprints `p` on the console before computing `q`.
16+
17+## Syntax
18+
19+Regular: *2-fixed*.
20+
21+## Examples
22+
23+```
24+~zod:dojo> ~&('halp' ~)
25+'halp'
26+~
27+```
docs/programming/hoon/catalog/sig-hint/tis-ddup.mdnew file+34
@@ -0,0 +1,34 @@
1+---
2+sort: 8
3+---
4+
5+# `:ddup ~= "sigtis" {$ddup p/seed q/seed}`
6+
7+Detect a duplicate.
8+
9+## Expands to
10+
11+`q`.
12+
13+## Convention
14+
15+If `p` equals `q`, produce `p` instead of `q`.
16+
17+## Discussion
18+
19+Duplicates are especially bad news in Hoon, because comparing them
20+takes O(n) time. Use `~=` to kill them as they breed.
21+
22+## Examples
23+
24+This code traverses a tree and replaces all instances of `42` with
25+`420`:
26+
27+```
28+~zod:dojo> =foo |= a/(tree)
29+ ?~(a ~ ~=(a [?:(=(n.a 42) 420 n.a) $(a l.a) $(a r.a)]))
30+~zod:dojo> (foo 42 ~ ~)
31+[420 ~ ~]
32+```
33+
34+Without `~=`, it would build a copy of a completely unchanged tree. Sad!
docs/programming/hoon/catalog/sig-hint/wut-warn.mdnew file+29
@@ -0,0 +1,29 @@
1+---
2+sort: 4
3+---
4+
5+# `:warn ~? "sigwut" `{$warn p/twig q/twig r/twig}`
6+
7+Conditional debugging printf.
8+
9+## Expands to
10+
11+`r`.
12+
13+## Convention
14+
15+If `p` is true, prettyprints `q` on the console before computing `r`.
16+
17+## Syntax
18+
19+Regular: *4-fixed*.
20+
21+## Examples
22+
23+```
24+~zod:dojo> ~?((gth 1 2) 'oops' ~)
25+~
26+~zod:dojo> ~?((gth 1 0) 'oops' ~)
27+'oops'
28+~
29+```
docs/programming/hoon/catalog/sig-hint/zap-peep.mdnew file+29
@@ -0,0 +1,29 @@
1+---
2+sort: 9
3+---
4+
5+# `:peep ~! "sigzap" {$peep p/seed q/seed}`
6+
7+Print type on compilation fail.
8+
9+## Expands to
10+
11+`q`.
12+
13+## Convention
14+
15+If compilation of `q` fails, prints the span of `p` in the trace.
16+
17+## Syntax
18+
19+Regular: *2-fixed*.
20+
21+## Examples
22+
23+```
24+~zod:dojo> a
25+! -find.a
26+~zod:dojo> ~!('foo' a)
27+! @t
28+! find.a
29+```
docs/programming/hoon/catalog/tis-flow.mdnew file+31
@@ -0,0 +1,31 @@
1+---
2+sort: 8
3+---
4+
5+# `= tis` (flow)
6+
7+<list dataPreview="true" className="runes" linkToFragments="true"></list>
8+
9+<kids className="runes"></kids>
10+
11+## Twigs
12+
13+```
14+|%
15+++ taco $@(term (pair term twig)) :: optional face
16+++ twig ::
17+ $% {$new p/twig q/twig} :: =|
18+ {$fix p/(list (pair wing twig)) q/twig} :: =:
19+ {$var p/taco q/twig r/twig} :: =/
20+ {$rev p/taco q/twig r/twig} :: =;
21+ {$set p/wing q/twig r/twig} :: =.
22+ {$rap p/twig q/twig} :: =<
23+ {$nip p/twig q/twig} :: =-
24+ {$per p/twig q/twig} :: =>
25+ {$sip p/taco q/wing r/twig s/twig} :: =^
26+ {$pin p/twig q/twig} :: =+
27+ {$tow p/(list twig)} :: =~
28+ {$aka p/term q/twig r/twig} :: =*
29+ ==
30+--
31+```
docs/programming/hoon/catalog/tis-flow/bar-new.mdnew file+38
@@ -0,0 +1,38 @@
1+---
2+sort: 5
3+---
4+
5+# `:new, =|, "tisbar", {$new p/moss q/seed}`
6+
7+Combine a defaulted mold with the subject.
8+
9+## Expands to
10+
11+```
12+:pin(:bunt(p) q)
13+```
14+
15+## Syntax
16+
17+Regular: *2-fixed*.
18+
19+## Discussion
20+
21+`:new` "declares a variable" which is "uninitialized," presumably
22+because you'll set it in a loop or similar.
23+
24+A common mistake is to forget that since `p` is moldy,
25+`:new(foo=@ bar)` is wrong; you mean `:new(foo/@ bar)`, since
26+`foo=@` is `:name(foo @)` (putting a face on a seed) and `foo/@`
27+is `:coat(foo @)` (wrapping a face around a mold).
28+
29+## Examples
30+
31+```
32+~zod:dojo> =foo |= a/@
33+ =| b/@
34+ =- :(add a b c)
35+ c=2
36+~zod:dojo> (foo 5)
37+7
38+```
docs/programming/hoon/catalog/tis-flow/col-fix.mdnew file+28
@@ -0,0 +1,28 @@
1+---
2+sort: 9
3+---
4+
5+# `:fix, =:, "tiscol", {$fix p/(list (pair wing twig)) q/twig}`
6+
7+Mutate multiple legs in the subject.
8+
9+## Expands to
10+
11+```
12+:per(:keep(. p q) r)
13+```
14+
15+## Syntax
16+
17+Regular: *jogging*, then *1-fixed*.
18+
19+## Examples
20+
21+```
22+~zod:dojo> =+ a=[b=1 c=2]
23+ =: c.a 4
24+ b.a 3
25+ ==
26+ a
27+[b=3 c=4]
28+```
docs/programming/hoon/catalog/tis-flow/dot-set.mdnew file+35
@@ -0,0 +1,35 @@
1+---
2+sort: 8
3+---
4+
5+# `:set, =., "tisdot", {$set p/wing q/seed r/seed}`
6+
7+Mutate a leg in the subject.
8+
9+## Expands to
10+
11+```
12+:per(:keep(. p q) r)
13+```
14+
15+## Syntax
16+
17+Regular: *3-fixed*.
18+
19+## Discussion
20+
21+As usual, we are not actually mutating the subject, just creating
22+a new subject with a changed value. Note that the mutation uses
23+`:keep` (`%_`), so the type doesn't change.
24+
25+## Examples
26+
27+```
28+~zod:dojo> =+ a=[b=1 c=2]
29+ =. b.a 3
30+ a
31+[b=3 c=2]
32+~zod:dojo> =+ a=[b=1 c=2]
33+ =.(b.a 3 a)
34+[b=3 c=2]
35+```
docs/programming/hoon/catalog/tis-flow/fas-var.mdnew file+35
@@ -0,0 +1,35 @@
1+---
2+sort: 6
3+---
4+
5+# `:var, =/, "tisfas", {$var p/taco q/twig r/twig}`
6+
7+Combine a named and/or typed noun with the subject.
8+
9+## Expands to
10+
11+```
12+?@(p :pin(:name(p q) r) :pin(:cast(:(coat p) q) r)
13+```
14+
15+## Syntax
16+
17+Regular: *3-fixed*.
18+
19+## Discussion
20+
21+`p` can be either a symbol or a symbol/mold. If it's just a
22+symbol, `:var` "declares a type-inferred variable." It has a
23+mold, `:var` "declares a type-checked variable."
24+
25+## Examples
26+
27+```
28+~zod:dojo> =foo |= a/@
29+ =/ b 1
30+ =/ c/@ 2
31+ :(add a b c)
32+~zod:dojo> (foo 5)
33+8
34+```
35+
docs/programming/hoon/catalog/tis-flow/gal-rap.mdnew file+28
@@ -0,0 +1,28 @@
1+---
2+sort: 2
3+---
4+
5+# `:rap, =<, "tisgal", {$rap p/twig q/twig}`
6+
7+Compose two twigs, inverted.
8+
9+## Expands to
10+
11+```
12+:per(q p)
13+```
14+
15+## Syntax
16+
17+Regular: *2-fixed*.
18+
19+Irregular: `foo:bar` is `:rap(foo bar)`.
20+
21+## Examples
22+
23+```
24+~zod:dojo> b:[a=1 b=2 c=3]
25+2
26+~zod:dojo> [. .]:(add 2 4)
27+[6 6]
28+```
docs/programming/hoon/catalog/tis-flow/gar-per.mdnew file+24
@@ -0,0 +1,24 @@
1+---
2+sort: 1
3+---
4+
5+# `:per, =>, "tisgar", {$per p/twig q/twig}`
6+
7+Compose two twigs.
8+
9+## Produces
10+
11+`q`, compiled against the product of `p`.
12+
13+## Syntax
14+
15+Regular: *2-fixed*.
16+
17+## Examples
18+
19+```
20+~zod:dojo> =>([a=1 b=2 c=3] b)
21+2
22+~zod:dojo> =>((add 2 4) [. .])
23+[6 6]
24+```
docs/programming/hoon/catalog/tis-flow/hep-nip.mdnew file+33
@@ -0,0 +1,33 @@
1+---
2+sort: 4
3+---
4+
5+# `:nip, =-, "tishep", {$pin p/seed q/seed}`
6+
7+Combine a new noun with the subject, inverted.
8+
9+## Expands to
10+
11+```
12+:per(:cons(q .) p)
13+```
14+
15+## Syntax
16+
17+Regular: *2-fixed*.
18+
19+## Discussion
20+
21+`:nip` looks better than `:pin` when the twig you're pinning
22+is much smaller than the twig that uses it.
23+
24+## Examples
25+
26+```
27+~zod:dojo> =foo |= a/@
28+ =+ :name(b 1)
29+ =- :(add a b c)
30+ c=2
31+~zod:dojo> (foo 5)
32+8
33+```
docs/programming/hoon/catalog/tis-flow/ket-sip.mdnew file+40
@@ -0,0 +1,40 @@
1+---
2+sort: 10
3+---
4+
5+# `:sip, =^, "tisket", {$sip p/taco q/wing r/twig s/twig}`
6+
7+Pin the head of a pair; mutate a leg with the tail.
8+
9+## Expands to
10+
11+```
12+:var(p -.r :set(q +.r s))
13+```
14+
15+## Syntax
16+
17+Regular: *4-fixed*.
18+
19+## Discussion
20+
21+We use `:sip` when we have a state machine with a function that
22+produces a cell, whose head is a result and whose tail is a new
23+state. We want to use the head as a new variable, and stuff the
24+tail back into wherever we stored the old state.
25+
26+This may also remind you of Haskell's State monad.
27+
28+## Examples
29+
30+The `og` core is a stateful pseudo-random number generator.
31+We have to change the core state every time we generate a
32+random number, so we need to `:sip`:
33+
34+```
35+~zod:dojo> =+ rng=~(. og 420)
36+ =^ r1 rng (rads:rng 100)
37+ =^ r2 rng (rads:rng 100)
38+ [r1 r2]
39+[99 46]
40+```
docs/programming/hoon/catalog/tis-flow/lus-pin.mdnew file+32
@@ -0,0 +1,32 @@
1+---
2+sort: 3
3+---
4+
5+# `:pin, =+, "tislus", {$pin p/seed q/seed}`
6+
7+Combine a new noun with the subject.
8+
9+## Expands to
10+
11+```
12+:per(:cons(p .) q)
13+```
14+
15+## Syntax
16+
17+Regular: *2-fixed*.
18+
19+## Discussion
20+
21+`:pin` is the simplest way of "declaring a variable."
22+
23+## Examples
24+
25+```
26+~zod:dojo> =foo |= a/@
27+ =+ :name(b 1)
28+ =+ c=2
29+ :(add a b c)
30+~zod:dojo> (foo 5)
31+8
32+```
docs/programming/hoon/catalog/tis-flow/sem-rev.mdnew file+28
@@ -0,0 +1,28 @@
1+---
2+sort: 7
3+---
4+
5+# `:rev, =;, "tissem", {$rev p/taco q/twig r/twig}`
6+
7+Combine a named and/or typed noun with the subject, inverted.
8+
9+## Expands to
10+
11+```
12+?@(p :pin(:name(p r) q) :pin(:cast(:(coat p) r) q)
13+```
14+
15+## Syntax
16+
17+Regular: *3-fixed*.
18+
19+## Examples
20+
21+```
22+~zod:dojo> =foo :gate a/@
23+ :var b 1
24+ :rev c/@ :(add a b c)
25+ 2
26+~zod:dojo> (foo 5)
27+8
28+```
docs/programming/hoon/catalog/tis-flow/tar-aka.mdnew file+37
@@ -0,0 +1,37 @@
1+---
2+sort: 11
3+---
4+
5+# `:aka, =*, "tistar", {$aka p/term q/seed r/seed}`
6+
7+Define an alias.
8+
9+## Produces
10+
11+`r`, compiled with a subject in which `p` is aliased to `q`.
12+
13+## Syntax
14+
15+Regular: *3-fixed*.
16+
17+## Discussion
18+
19+The difference between aliasing and pinning is that the subject
20+noun stays the same; the alias is just recorded in its span.
21+`q` is calculated every time you use the `p` alias, of course.
22+
23+## Examples
24+
25+```
26+~zod:dojo>
27+ =+ a=1
28+ =* b a
29+ [a b]
30+[1 1]
31+~zod:dojo>
32+ =+ a=1
33+ =* b a
34+ =. a 2
35+ [a b]
36+[2 2]
37+```
docs/programming/hoon/catalog/wut-test.mdnew file+31
@@ -0,0 +1,31 @@
1+---
2+sort: 10
3+---
4+
5+# `? wut` (test)
6+
7+<list dataPreview="true" className="runes" linkToFragments="true"></list>
8+
9+<kids className="runes"></kids>
10+
11+## Twigs
12+
13+```
14+|%
15+++ twig
16+ $% {$or p/(list twig)} :: ?|
17+ {$case p/wing q/(list (pair twig twig))} :: ?-
18+ {$if p/twig q/twig r/twig} :: ?:
19+ {$lest p/twig q/twig r/twig} :: ?.
20+ {$ifcl p/wing q/twig r/twig} :: ?^
21+ {$deny p/twig q/twig} :: ?<
22+ {$sure p/twig q/twig} :: ?>
23+ {$deft p/wing q/twig r/(list (pair twig twig))} :: ?+
24+ {$and p/(list twig)} :: ?&
25+ {$ifat p/wing q/twig r/twig} :: ?@
26+ {$ifno p/wing q/twig r/twig} :: ?~
27+ {$fits p/twig q/wing} :: ?=
28+ {$not p/twig} :: ?!
29+ ==
30+--
31+```
docs/programming/hoon/catalog/wut-test/bar-or.mdnew file+30
@@ -0,0 +1,30 @@
1+---
2+sort: 9
3+---
4+
5+# `:or`, `?|`, "wutbar" `{$or p/(list seed)}`
6+
7+Logical or.
8+
9+## Expands to
10+
11+```
12+:ifno p
13+ |
14+:if i.p
15+ &
16+:moar(p t.p)
17+```
18+
19+## Syntax
20+
21+Regular: *running*.
22+
23+Irregular: `|(foo bar baz)` is `?|(foo bar baz)`.
24+
25+## Examples
26+
27+```
28+~zod:dojo> |(=(6 42) =(42 42))
29+%.y
30+```
docs/programming/hoon/catalog/wut-test/col-if.mdnew file+42
@@ -0,0 +1,42 @@
1+---
2+sort: 1
3+---
4+
5+# `:if, ?:, "wutcol", `{$if p/seed q/seed r/seed}`
6+
7+Branch on a boolean test.
8+
9+## Produces
10+
11+If `p` produces yes, then `q`. If `p` produces no, `r`.
12+If `p` is not a boolean, compiler yells at you.
13+
14+The subjects of `q` and `r` are constrained to match any
15+pattern-matching algebra in `p`. The analysis, which is
16+conservative, understands any combination of `:fits`
17+(`?=`), `:and` (`?&`), `:or` (`?|`), and `:not` (`?!`),
18+and reduces the subject appropriately when compiling.
19+
20+If test analysis reveals that either branch is not taken,
21+or if `p` is not a boolean, compilation fails. However,
22+an untaken branch can be indicated with the `:lost` twig.
23+
24+## Syntax
25+
26+Regular: *3-fixed*.
27+
28+## Discussion
29+
30+Short-circuiting in boolean tests works as you'd expect
31+and includes the expected inference. For instance,
32+if you write `:(and a b)`, `b` is only executed if `a` is
33+positive, and compiled with that assumption.
34+
35+Note also that all other branching twigs reduce to `:if`.
36+
37+## Examples
38+
39+```
40+~zod:dojo> ?:((gth 1 2) 3 4)
41+4
42+```
docs/programming/hoon/catalog/wut-test/dot-lest.mdnew file+39
@@ -0,0 +1,39 @@
1+---
2+sort: 2
3+---
4+
5+# `:lest`, `?.`, "wutdot" `{$lest p/twig q/twig r/twig}`
6+
7+Branch on a boolean test, inverted.
8+
9+## Expands to
10+
11+```
12+:if p
13+ r
14+q
15+```
16+
17+## Syntax
18+
19+Regular: *3-fixed*.
20+
21+## Discussion
22+
23+As usual with inverted forms, use `:lest` when the positive
24+twig of an `:if` is much heavier than the negative twig.
25+
26+## Examples
27+
28+```
29+~zod:dojo> ?.((gth 1 2) 3 4)
30+3
31+~zod:dojo> ?.(?=(%a 'a') %not-a %yup)
32+%yup
33+~zod:dojo> ?. %.y
34+ 'this false case is less heavy than the true case'
35+ ?: =(2 3)
36+ 'two not equal to 3'
37+ 'but see how \'r is much heavier than \'q?'
38+'but see how \'r is much heavier than \'q?'
39+```
docs/programming/hoon/catalog/wut-test/gal-deny.mdnew file+27
@@ -0,0 +1,27 @@
1+---
2+sort: 10
3+---
4+
5+# `:deny, ?<, "wutgal", {$deny p/seed q/seed}`
6+
7+Negative assertion.
8+
9+## Expands to
10+
11+```
12+:if p
13+ :zpzp
14+q
15+```
16+
17+## Syntax
18+
19+Regular: *2-fixed*.
20+
21+## Examples
22+
23+```
24+~zod:dojo> ?<(=(3 4) %foo)
25+%foo
26+```
27+
docs/programming/hoon/catalog/wut-test/gar-sure.mdnew file+26
@@ -0,0 +1,26 @@
1+---
2+sort: 11
3+---
4+
5+# `:sure, ?<, "wutgar", {$sure p/seed q/seed}`
6+
7+Positive assertion.
8+
9+## Expands to
10+
11+```
12+:lest p
13+ :zpzp
14+q
15+```
16+
17+## Syntax
18+
19+Regular: *2-fixed*.
20+
21+## Examples
22+
23+```
24+~zod:dojo> ?>(=(3 3) %foo)
25+%foo
26+```
docs/programming/hoon/catalog/wut-test/hep-case.mdnew file+49
@@ -0,0 +1,49 @@
1+---
2+sort: 12
3+---
4+
5+# `:case, ?-, "wuthep", {$case p/wing q/(list (pair moss seed))}`
6+
7+Switch against a union, with no default.
8+
9+## Expands to
10+
11+```
12+:ifno q
13+ :lost
14+:if :fits(p.i.q p)
15+ q.i.q
16+:moar(q t.q)
17+```
18+
19+## Syntax
20+
21+Regular: *1-fixed*, then *jogging*.
22+
23+## Discussion
24+
25+The compiler makes sure that your code neither misses a case of
26+the union, nor includes a double case that isn't there. This is
27+not special handling for `:case`, just a consequence of the
28+semantics of `:if`, which `:case` reduces to.
29+
30+A missing case will throw the `mint-lost` error. An extra case
31+will throw `mint-vain`. (Ecclesiastes did nothing wrong.)
32+
33+## Examples
34+
35+```
36+~zod:dojo> =cor |= vat/?($a $b)
37+ ?- vat
38+ $a 20
39+ $b 42
40+ ==
41+~zod:dojo> (cor %a)
42+20
43+~zod:dojo> (cor %b)
44+42
45+~zod:dojo> (cor %c)
46+! nest-fail
47+```
48+
49+
docs/programming/hoon/catalog/wut-test/ket-ifcl.mdnew file+35
@@ -0,0 +1,35 @@
1+---
2+sort: 5
3+---
4+
5+# `:ifcl, ?^, "wutket", {$ifcl p/wing q/twig r/twig}`
6+
7+Branch on whether a wing of the subject is null.
8+
9+## Expands to
10+
11+```
12+:if :fits(^ p)
13+ q
14+r
15+```
16+
17+## Syntax
18+
19+Regular: *3-fixed*.
20+
21+## Discussion
22+
23+Regular form: *3-fixed*
24+
25+## Examples
26+
27+```
28+~zod:dojo> ?^(0 1 2)
29+! mint-vain
30+! exit
31+~zod:dojo> ?^(`*`0 1 2)
32+2
33+~zod:dojo> ?^(`*`[1 2] 3 4)
34+3
35+```
docs/programming/hoon/catalog/wut-test/lus-deft.mdnew file+41
@@ -0,0 +1,41 @@
1+---
2+sort: 13
3+---
4+
5+# `:deft, ?-, "wutlus", {$case p/wing q/seed r/(list (pair moss seed))}`
6+
7+Switch against a union, with a default.
8+
9+## Expands to
10+
11+```
12+:ifno r
13+ q
14+:if :fits(p.i.r p)
15+ q.i.r
16+:moar(r t.r)
17+```
18+
19+## Syntax
20+
21+Regular: *2-fixed*, then *jogging*.
22+
23+## Discussion
24+
25+An extra case will throw `mint-vain`. A lost case defaults.
26+
27+## Examples
28+
29+```
30+~zod:dojo> =cor |= vat/?($a $b)
31+ ?+ vat 240
32+ $a 20
33+ $b 42
34+ ==
35+~zod:dojo> (cor %a)
36+20
37+~zod:dojo> (cor %b)
38+42
39+~zod:dojo> (cor %c)
40+240
41+```
docs/programming/hoon/catalog/wut-test/pam-and.mdnew file+30
@@ -0,0 +1,30 @@
1+---
2+sort: 8
3+---
4+
5+# `:and, ?&, "wutpam", {$and p/(list seed)}`
6+
7+Logical and.
8+
9+## Expands to
10+
11+```
12+:ifno p
13+ &
14+:lest i.p
15+ |
16+:moar(p t.p)
17+```
18+
19+## Syntax
20+
21+Regular: *running*.
22+
23+Irregular: `&(foo bar baz)` is `?&(foo bar baz)`.
24+
25+## Examples
26+
27+```
28+~zod:dojo> &(=(6 6) =(42 42))
29+%.y
30+```
docs/programming/hoon/catalog/wut-test/pat-ifat.mdnew file+31
@@ -0,0 +1,31 @@
1+---
2+sort: 4
3+---
4+
5+# `:ifat, ?@, "wutpat", {$ifat p/wing q/seed r/seed}`
6+
7+Branch on whether a wing of the subject is an atom.
8+
9+## Expands to
10+
11+```
12+:if :fits($~ p)
13+ q
14+r
15+```
16+
17+## Syntax
18+
19+Regular: *3-fixed*.
20+
21+## Examples
22+
23+```
24+~zod:dojo> ?@(0 1 2)
25+! mint-vain
26+! exit
27+~zod:dojo> ?@(`*`0 1 2)
28+1
29+~zod:dojo> ?@(`*`[1 2] 3 4)
30+4
31+```
docs/programming/hoon/catalog/wut-test/sig-ifno.mdnew file+32
@@ -0,0 +1,32 @@
1+---
2+sort: 3
3+---
4+
5+# `ifno`, `?~`, "wutsig" `{$ifno p/wing q/seed r/seed}`
6+
7+Branch on whether a wing of the subject is null.
8+
9+## Expands to
10+
11+```
12+:if :fits($~ p)
13+ q
14+r
15+```
16+
17+## Syntax
18+
19+Regular: *3-fixed*.
20+
21+## Discussion
22+
23+It's bad style to use `:ifno` to test for any zero atom. Use it
24+only for a true null, `~`.
25+
26+## Examples
27+
28+```
29+~zod:dojo> =foo ""
30+~zod:dojo> ?~(foo 1 2)
31+11
32+```
docs/programming/hoon/catalog/wut-test/tis-fits.mdnew file+40
@@ -0,0 +1,40 @@
1+---
2+sort: 6
3+---
4+
5+# `:fits, ?=, "wuttis", {$fits p/moss q/wing}
6+
7+Test whether the noun at wing `q` fits pattern `p`.
8+
9+## Produces
10+
11+`&` (yes) if the noun at `q` is in the icon of `p`;
12+`|` (no) otherwise.
13+
14+## Syntax
15+
16+Regular: *2-fixed*.
17+
18+## Discussion
19+
20+`:fits` is not as powerful as it might seem. For instance, it
21+can't generate a loop -- you cannot (and should not) use it to
22+test whether a `*` is a `(list @)`. Nor can it validate atomic
23+auras.
24+
25+Patterns should be as weak as possible. Unpack one layer of
26+union at a time. Don't confirm things the type system knows.
27+
28+For example, when matching a book containing a page `{$foo p/@
29+q/{@ @}}`, the proper pattern is `{$foo *}`. You have one
30+question, which is whether the head of the noun is `%foo`.
31+
32+A common error is `find.$`, meainng `p` is not a mold.
33+
34+## Examples
35+
36+```
37+~zod:dojo> =bar [%foo %bar %baz]
38+~zod:dojo> ?=({$foo *} bar)
39+%.y
40+```
docs/programming/hoon/catalog/wut-test/zap-not.mdnew file+32
@@ -0,0 +1,32 @@
1+---
2+sort: 7
3+---
4+
5+# `:not, ?!, "wutzap", {$not p/seed}`
6+
7+Logical not.
8+
9+## Expands to
10+
11+```
12+:same(%.n p)
13+```
14+
15+Produces the logical "not" of `p`.
16+
17+## Syntax
18+
19+Regular: *1-fixed*.
20+
21+Irregular: `!(foo)` is `?!(foo)`.
22+
23+## Examples
24+
25+```
26+~zod:dojo> !&
27+%.n
28+~zod:dojo> !|
29+%.y
30+~zod:dojo> !(gth 5 6)
31+%.y
32+```
docs/programming/hoon/catalog/zap-wild.mdnew file+23
@@ -0,0 +1,23 @@
1+---
2+sort: 11
3+---
4+
5+# `! zap` (wild)
6+
7+<list dataPreview="true" className="runes" linkToFragments="true"></list>
8+
9+<kids className="runes"></kids>
10+
11+## Twigs
12+
13+```
14+|%
15+++ twig
16+ $% {$twig p/twig q/twig} :: !,
17+ {$wrap p/twig} :: !>
18+ {$spit p/twig q/twig} :: !;
19+ {$code p/twig} :: !=
20+ {$need p/$@(p/@ {p/@ q/@}) q/twig} :: !?
21+ {$fail $~} :: !!
22+ ==
23+--
docs/programming/hoon/catalog/zap-wild/gar-wrap.mdnew file+27
@@ -0,0 +1,27 @@
1+---
2+sort: 2
3+---
4+
5+# `:wrap !> "zapgar" {$wrap p/twig}`
6+
7+Wrap a noun in its span.
8+
9+## Produces
10+
11+A cell whose tail is `p`, and whose head is the static span of p.
12+
13+## Syntax
14+
15+Regular: *1-fixed*.
16+
17+## Discussion
18+
19+In Hoon, dynamic type is static type compiled at runtime. This
20+span-noun cell is generally called a `vase`.
21+
22+## Examples
23+
24+```
25+~zod:dojo> !>(1)
26+[#t/@ud q=1]
27+```
docs/programming/hoon/catalog/zap-wild/tis-code.mdnew file+26
@@ -0,0 +1,26 @@
1+---
2+sort: 3
3+---
4+
5+# `:code != "zaptis" {$code p/twig}`
6+
7+Make the Nock formula for a twig.
8+
9+## Produces
10+
11+The Nock generated by `p`.
12+
13+## Syntax
14+
15+Regular: *1-fixed*.
16+
17+## Examples
18+
19+```
20+~zod:dojo> !=(20)
21+[1 20]
22+~zod:dojo> !=(~zod)
23+[1 0]
24+~zod:dojo> !=((add 2 2))
25+[8 [9 3.110.356 0 31] 9 2 [0 4] [7 [0 3] 1 2 2] 0 11]
26+```
docs/programming/hoon/catalog/zap-wild/wut-need.mdnew file+27
@@ -0,0 +1,27 @@
1+---
2+sort: 4
3+---
4+
5+# `:need !? "zapwut" {$need p/@ q/twig}`
6+
7+Restrict Hoon version.
8+
9+## Produces
10+
11+`q`, if `p` is greater than or equal to the Hoon kelvin version.
12+(Versions count down; the current version is 150.)
13+
14+## Syntax
15+
16+Regular: *2-fixed*.
17+
18+## Examples
19+
20+```
21+~zod:dojo> !?(264 (add 2 2))
22+4
23+~zod:dojo> !?(164 (add 2 2))
24+4
25+~zod:dojo> !?(64 (add 2 2))
26+! exit
27+```
docs/programming/hoon/catalog/zap-wild/zap-fail.mdnew file+26
@@ -0,0 +1,26 @@
1+---
2+sort: 1
3+---
4+
5+# `:fail, !! "zapzap" {$fail $~}`
6+
7+Crash.
8+
9+## Produces
10+
11+Nothing. Always crashes, with span `%void`.
12+
13+## Syntax
14+
15+`!!`
16+
17+## Discussion
18+
19+`%void` nests in every other span, so you can stub out anything with `!!`.
20+
21+## Examples
22+
23+```
24+~zod:dojo> !!
25+! exit
26+```
docs/programming/hoon/cheat-sheets.mdnew file+9
@@ -0,0 +1,9 @@
1+---
2+sort: 13
3+---
4+
5+# Quick references
6+
7+Some quick-reference sheets to print out or keep on your other monitor.
8+
9+<list></list>
docs/programming/hoon/cheat-sheets/hoon.mdnew file+532
@@ -0,0 +1,532 @@
1+
2+##Quick references
3+
4+###Lexical syntax
5+
6+####Comments
7+
8+`::` all code following '::' on a line is a comment.
9+
10+By convention, comments should begin on either column 39 or
11+column 57.
12+
13+####Runes (Expressions)
14+
15+- Most runes have a predetermined amount of children, and thus do not need to be closed.
16+
17+- Runes that accept an arbitrary number of children are typically closed with
18+ `==`, with the exception being the `|` runes, some of which are closed with
19+ `--`.
20+
21+- In some cases, the second glyph denotes how many 'children' a rune accepts:
22+
23+ `-` two
24+ `+` three
25+ `^` four
26+
27+- Backstep pattern: in order to avoid excess parentheses as well as code that
28+ flows off the page, the last child of a rune should fall directly below it.
29+ The first child should be the furthest to the right, with every subsequent
30+ rune 'backstepping' two spaces towards the last child.
31+
32+ XX
33+
34+The first glyph in a rune defines a rough semantic category of expressions:
35+
36+##### ? : Conditional statements
37+
38+`?&` Logical "and"
39+
40+ - Irregular: `&`
41+
42+`?|` Logical "or"
43+
44+ - Irregular: `|.`
45+
46+`?!` Logical "not"
47+
48+ - Irregular: `!`
49+
50+
51+`?:` - If-then-else
52+
53+`?.` - Inverted if-then-else
54+
55+`?@` - If atom-then-else
56+
57+`?^` - If cell-then-else
58+
59+
60+`?-` - Switch (on type)
61+
62+`?+` - Swith (on type) with default
63+
64+
65+`?>` - Assert `p` is false.
66+
67+`?<` - Assert `p` is true.
68+
69+
70+`?~` - if null-then-else Note: don't forget, changes type
71+`?=` - is `q` of type `p`Note: don't forget, changes the type
72+
73+##### % : Code execution
74+
75+`%-` Call `p` with 1 arg
76+
77+ - Irregular: `(p q)` Note: irregular form can accept n children.
78+
79+`%.` Inverted `%-`: call `q` with arg `p`
80+
81+`%+` Call `p` with 2 args
82+
83+`%^` Call `p` with 3 args
84+
85+
86+`%~` Call one arm `p` within object/core `q` with arg `r`
87+
88+ - Irregular: `~(p q r)`
89+
90+`%*` Same as `%~` except `s` is a list of changes that can be made anywhere in
91+the context, not just to input data.
92+
93+
94+`%=` Evaluate `p` with changes specified in `q`
95+
96+ - Irregular: `a(p q.p, q p.a)`, where `a` is the code to be executed with changes
97+ specified in the `()`
98+
99+`%_` Same as `%=`, except that product is cast back to type of `p`.
100+
101+##### : : Tuple construction
102+
103+`:-` Tuple of two
104+
105+ - Irregular `[p q ..]` Note: the irregular form can make tuples of arbitrary size
106+
107+`:_` Inverted tuple of two
108+
109+`:+` Tuple of three
110+
111+`:^` Tuple of four
112+
113+
114+`:*` Tuple of arbitrary number of elements, closed with `==`
115+
116+`:~` Null terminated tuple of arbitrary number of elements, closed with `==`.
117+
118+
119+`:/` XX
120+
121+##### | : Object aka "core" construction
122+
123+`|%` Generic core, closed with `--`
124+
125+`|_` Core with input data (aka 'sample), closed with `--`
126+
127+
128+`|=` Function with type-checking at compile time (aka 'dry gate'); called automatically
129+
130+`|*` Function with type-checking at run time (aka 'wet gate'); called automatically
131+
132+`|.` Function (like `|=`) with no argument; called automatically
133+
134+`|-` Function with no arguments (like `|.`); not called automatically
135+
136+
137+`|/` Same as `|_`, but with well typed output, closed with `--`
138+
139+`|^` Same as `|-`, but can contain internal arms, closed with `--`
140+
141+`|+` Function with unreadable argument(s) (aka 'sample'), so as to avoid type conflicts
142+
143+`|?` Same as `|_` but both the input and 'context' are hidden to avoid type conflicts
144+
145+##### $ : Type definitions
146+
147+`$|` Union between atom and cell
148+
149+`$_` 'Unbunt'; create type from example
150+
151+ - Irregular: `_p`, but only when in mold syntax
152+
153+`$:` Tuple of types (aka 'molds')
154+
155+ - Irregular: `{i.p i.t.p i.t.t.p}`
156+
157+`$%` Tagged union
158+
159+`$+` Type of function (type signature)
160+
161+`$&` Union of two cells: one w/cellular head and other w/atomic head
162+
163+`$*` 'Bunt'; produce default value of a type
164+
165+ - Irregular: `*([mold])`
166+
167+`$=` Add variable name; technically changes the type as well
168+
169+ - Irregular: `p=q`, but only when in mold syntax
170+
171+`$?` Union of types; non-empty list of types ('molds'). Default value ('bunt') is the value of the first element
172+
173+ - Irregular: `?([list of molds])`, but only when in mold syntax
174+
175+##### = : Subject ("context") modification XX
176+
177+`=>` Resolve code; use the product of `p` as the subject of `q`
178+
179+ - Irregular: `p:q`
180+
181+`=<` Inverted `=>`, used for code readability
182+
183+
184+`=|` Push default value of type ('mold') onto subject
185+
186+`=+` Push variable/value onto subject
187+
188+`=-` Inverted `=+`; push product of `q` onto subject `p`
189+
190+
191+`=.` One change to subject; produce `r` with `p` in the context (in hoon the
192+'subject') set to `q`
193+
194+`=:` Multiple changes to subject; Make a list of changes to the context (in hoon the 'subject')
195+
196+ XX how do we talk about subject and context.
197+
198+
199+`=^` Used to push a new variable `q` with face `p` onto the subject `s`, as
200+well as to change the value of another. `r` is a function that accepts `q` and
201+produces a cell of a new value of `q`, and a new subject. XX
202+
203+`=~` Compose a list of twigs, applying `=>` to the list, using each result as the subject to the subsequent expressions.
204+
205+`=*` Make `p` an alias of `q`
206+
207+##### ^ : Casting
208+
209+`^|` Make core context unreadable so as to avoid type conflicts
210+
211+`^.` Cast `q` to the product type of `p`. Useful when you don't actually want to run a funciton at run time
212+
213+`^-` Traditional Cast `q` to the type of the default value ('bunt') of `p`
214+
215+ - `\`p\`q`
216+
217+`^+` Cast `q` to the type of `p`. Used to cast to types that have previously been made into validator functions with `$,`.
218+
219+`^&` Convert object/core from invariant to covariant
220+
221+`^~` Try to execute `p` statically at compile time. If this fails, `p` remains dynamic
222+
223+`^=` Put on variable name ('face')
224+
225+ - Irregular: `p=q`
226+
227+`^?` Convert core with unreadable context to a core whose input ('sample') and context are unreadable. Used to avoid type conflicts
228+
229+##### . : Nock operations
230+
231+`.^` Nock 11; loads a file from `%clay`
232+
233+`.+` Nock 4; increments an atom
234+
235+ - Irregular: `+(p)`
236+
237+`.*` Compute nock; formula `q` on subject `p`
238+
239+`.=` Nock 5; test `p` and `q` for equality
240+
241+ - Irregular: `=(p q)`
242+
243+`.?` Test if noun is cell or an atom
244+
245+##### # : Pretty printing
246+
247+`#<` Pretty print tape; only used in its irregular form
248+
249+ - Irregular: `<i.p i.t.p i.t.t.p>`
250+
251+`#>` Pretty print `++tank`; used only in it's irregular form
252+
253+ - Irregular: `>i.p i.t.p i.t.t.p<`
254+
255+##### / : Library access
256+
257+`//` Load a file between twigs
258+
259+`/~` Cached computation, similar to a `=+` at the top of the file
260+
261+`/$` Pull in dynamic request data, slam it through a gate
262+
263+`/=` Horn form of `^=`. Puts a face on a cached computation
264+
265+`/^` Horn form of `^-`
266+
267+`/;` Apply gate to result of horn
268+
269+`/,` Appen path to current working beam before computing horn
270+
271+`/:` Replace beam
272+
273+`/%` Reifiy the 'heel' virtual path, letting any requested resource interpret it further
274+
275+`/.` Construct list of specified horns
276+
277+`/*` similar to `/.`, but produces a map instead
278+
279+`/_` descend into each available subdirectory, construct a map from all successfully building versions
280+
281+`/&` Parse directory name as `@da`
282+
283+`/|` Parse directory name as `@dr`
284+
285+##### ~ : Compiler hints
286+
287+`~$` Label computation `q` as `p` for profiling
288+
289+`~|` `p` in stacktrace if `q` crashes
290+
291+`~_` Preformatted stackframe `p` (a trap producing a `++tank`) into stacktrace
292+
293+`~%` i.p i.t.p i.t.t.pRegister jet in core `s`
294+
295+`~/` XX
296+
297+`~<` Hint to product; applies arbitrary hint `p` to the product of `q`, which is computed beforehand
298+
299+`~>` Arbitrary hint `p` to `q`
300+
301+`~+` Memoize computation of `p`
302+
303+`~&` Printf
304+
305+`~=` Hint to avoid duplication
306+
307+`~?` PrintF if `q` is true
308+
309+`~!` Print type on compilation fail
310+
311+##### ! : Special runes
312+
313+`!_` Path and range in stack trace
314+
315+`!>` Produces a cell of both the type and value of `p` (called a `++vase`).
316+Useful for debugging.
317+
318+`!=` Show nock of `p`
319+
320+`!?` Enforce a Hon version restriction
321+
322+`!!` Crash
323+
324+
325+####Data types
326+
327+#####Strings
328+
329+`++tape` - List of chars. Used when you want to manipulate and interpolate text - `"[text]"`
330+ See [list]() section for operations.
331+
332+`@t` - UTF-8 text; aka `++cord` - `'[text]'`
333+ `++trip`: cord to string XX
334+ `++taco`: cord to octet stream (for http requests) XX
335+ `++slav`: parse cord to an atom of input odor XX
336+
337+`@ta` - Valid Hoon ASCII symbols - `~.[text]` + {`a-z`, `0-9`, `~`, `-`, `.`, `_`.}
338+`@tas` - Hoon identifier ASCII subset - `%` + `a-z`, `-` (not first), `1-9` (not first)
339+
340+XX Would love to add half a liine about the difference between cords and tapes.
341+
342+#####Numbers
343+
344+`@` - Generic atom (defaults to unsigned integer) - `42`
345+`@u` - Unsigned integer - `42`
346+`@sd` - Signed decimal - `-42`(-), `--42` see `++si` for operations
347+`@rd` - Single precision floating point - `.-42.75` (-), `.42.75` (+), see `++rd` for operations
348+
349+#####Other Important Atoms
350+`@da` - absolute date - `~~[year].[month].[date]..[hour].[minute].[second]..[fractionals]`
351+ `++year`: `++date` to `@d` XX
352+ `++yore`: `@d` to `++date` XX
353+ note: year month day is mandatory, others are optional
354+`@dr` - relative date (timespan) - `~d[day].h[hour]m[minute].s[second]..[fractionals]`
355+ note: every measurement optional.
356+ `++add`: can add `@dr`s together XX
357+ `++yell`: `@d` to `++tarp` XX
358+`@p` - phonemic base - `~[valid @p]`
359+ `(scot %p [number])` prints a number as a `@p`
360+
361+#####Data structures
362+
363+######Tuples are made with the `:` runes and their irregular `[]` wide forms
364+
365+ To construct, use [`[]`]() (irregular form of [`:` runes]()).
366+
367+`[3 'hello']`
368+
369+Special syntaxes:
370+
371+`~[1 2 3]` > `[1 2 3 ~]`
372+
373+`[1 2 3]~` > `[[1 2 3] ~]`
374+
375+`~[1 2 3]~` > `[[1 2 3 ~] ~]`
376+
377+######Autocons
378+
379+To eliminate need for excess `[]`, tuples automatically group to
380+the right:
381+
382+`[1 [2 [3 ~]]]` == `[1 2 3 ~]`
383+
384+######pair, trel, quad put faces on tuples
385+
386+``=+ a=`(pair term cord)`[%h 'j']`` > `[p=%h q='j']`
387+
388+Faces allow you to access specific axes within your context:
389+
390+`p.a` > `%h` and `p:[p=%h q='j']` > `%h`
391+
392+######Lists are null-terminated and have faces of `i` and `t`
393+
394+- Definition:
395+
396+`++ list |* a=_,* :: null-term list
397+ $|(~ [i=a t=(list a)]) ::
398+`
399+
400+- Constructor: `++limo` makes a list out of a null terminated tuple.
401+
402+`(limo [67 55 201 ~])` > `[i=67 t=[i=55 t=[i=201 t=~]]]`
403+
404+``(list ,@t)`(list ,@)\`~[67 55] > <|C 7|>``
405+
406+- Operations:
407+
408+`++weld`: concatenate
409+`++scag`: slice up to (and including) index number args: (index, list)
410+`++slag`: slice list after index, args: (index, list)
411+`++turn`: map over list, args: (list, function)
412+`++reel`: right fold args: (list, function)
413+`++roll`: left fold args: (list, function)
414+`++sort`: quicksort, args: (list, comparator-function)
415+
416+######Map
417+
418+- Definition:
419+
420+` ++ map |* [a=_,* b=_,*] :: associative tree
421+ $|(~ [n=[p=a q=b] l=(map a b) r=(map a b)]) ::
422+`
423+
424+- Constructor: `++mo` produces a map of key-val pairs from left-right cell pairs of a list
425+
426+`
427+ ~zod/try=> (mo \`(list ,[@t *])\`[[a 1] [b 2] ~])
428+ {[p=a q=1] [p=b q=2]}
429+`
430+
431+- Operations: contained within the `++by` core
432+
433+`++by` accepts a map, then we use `%~` to pull the desired arm, which we then
434+pass the remainder of the arguments
435+
436+`
437+> =m (mo \`(list ,[@t *])\`[['a' 1] ['b' 2] ~])
438+> (~(got by m) 'a')
439+1
440+`
441+
442+`+-all:by`: logical 'AND'
443+`+-any:by`: logical 'OR'
444+`+-del:by`: delete at key
445+`+-dig:by`: axis of key
446+`+-gas:by`: concatenate: insert a list of key-value pairs into map
447+`+-get:by`: pull out value at key as a unit
448+`+-got:by`: assert: pull value at key, crash if key doesn't exist
449+`+-has:by`: check if key exists
450+`+-int:by`: intersection: if keys match, use value from `b`
451+`+-put:by`: add key value pair
452+`+-rep:by`: fold over map
453+`+-run:by`: 'map' over map
454+`+-tap:by`: convert map to list
455+`+-uni:by`: produce union between keys; if both share keys, use value from `a`
456+`+-urn:by`: 'map', with key included with value as input to mapping function
457+`+-wyt:by`: produce depth of tree of map
458+
459+######Set
460+
461+- Definition:
462+
463+`
464+ ++ set |* a=_,* :: set
465+ $|(~ [n=a l=(set a) r=(set a)]) ::
466+`
467+
468+- Constructor: `++sa`
469+
470+`
471+ ~zod/try=> (sa \`(list ,@)\`[1 2 3 4 5 ~])
472+ {5 4 1 3 2}
473+`
474+
475+- Operations: contained within the `++in` core
476+
477+The `++in` core accepts a set, then we use `%~` to pull desired operation out
478+of it, which we then pass the remainder of the arguments.
479+
480+ > =a (~(gas in `(set ,@t)`~) `(list ,@t)`[`a` `b` `c` ~])
481+ > (~(has in a) `a`)
482+ %.y
483+
484+
485+`+-all:in`: logical 'AND'
486+`+-any:in`: logical 'OR'
487+`+-del:in`: delete val at key
488+`+-dif:in`: difference between sets
489+`+-dig:in`: produce axis `b` in set
490+`+-gas:in`: concatenate: insert elements of list `b` into set
491+`+-has:in`: check if element exists in set
492+`+-int:in`: intersection
493+`+-put:in`: add an element to set
494+`+-rep:in`: fold over set
495+`+-tap:in`: convert set to list
496+`+-uni:in`: produces the union between two sets
497+`+-wyt:in`: Produces the number of elements in set
498+
499+#####Addressing within nouns
500+
501+There are several ways you can address an axes of a noun:
502+
503+1. `[face].[variable-name]`
504+
505+2. `-.+.+.a`: 'the head, within the tail of the tail of `a`.'
506+
507+Can also intersperse faces: `+.a.b` reads 'the tail of `a` within `b`.
508+
509+3. `->+.a`: 'tail within the head of the head of `a`.'
510+
511+Must start with either `-` (head) or `+` (tail), and then follow with either `<` (head) or `>` (tail), so
512+as to not repeat two symbols.
513+
514+4. `|[number].[var]` returns the elements that follow the nth element in a list
515+
516+5. `&[number]` returns the nth element in a list. Cannot return the last element.
517+
518+####Error messages
519+
520+ i. hoon-how to generate the list of errors (Henry)
521+
522+ ii. arvo
523+ %a. Curtis
524+ %b. Philip
525+ %c. PHilip
526+ %d. Curtis || Anton
527+ %e. Anton
528+ %f. Curtis || Anton
529+ %g. Curtis || Anton
530+
531+
532+
docs/programming/hoon/cheat-sheets/odors.mdnew file+686
@@ -0,0 +1,686 @@
1+Odors
2+=====
3+
4+Overview
5+--------
6+
7+Since Everything in Hoon is a natural number, the interpreter needs to
8+know both how to render them and subject them to type enforcement.
9+Odors, which are just ASCII spans beginning with a `@`, carry all of the
10+information necessary for the interpreter to do this. For instance, the
11+interpreter knows to render an atom of odor `@t` as UTF-8 text.
12+
13+The span composing the Odor consists of two parts: a lowercase prefix
14+carrying type information, and an upper-case suffix containing
15+information about its size. The prefix is a taxonomy that grows more
16+specific to the right. For example, atoms of the odor `@ta` are URL-safe
17+ASCII text, and Atoms of the odor `@tas` are the more specific subset of
18+ASCII text that is acceptable in hoon.
19+
20+The general principle of type enforcement is that atoms change freely
21+either up or down the taxonomy, but not across. You can treat a `@tas`
22+as a `@t`, as in a strong type system; but you can also treat a `@t` as
23+a `@tas`, or an `@` as anything. However, passing a `@t` to a function
24+that expects an `@ux` is a type error.
25+
26+XXDIAGRAMXX
27+
28+For example, you can cast a `@t` to a `@tas`, or vice-versa:
29+
30+ ~zod/try=> =a `@t`'permitted'
31+ ~zod/try=> a
32+ 'permitted'
33+ ~zod/try=> `@tas`a
34+ %permitted
35+
36+However, you cannot pass a `@ux` to a function that expects a `@t`
37+without casting it to a `@` first:
38+
39+ ~zod/try=> (|=(a=@t [%foo a]) 0x20)
40+ ! type-fail
41+ ! exit
42+ ~zod/try=> =a 0x21
43+ ~zod/try=> (|=(a=@t [%foo a]) `@t`a)
44+ [%foo '!']
45+
46+Note that when explicitly casting a `@ux` to a `@t`, the interpreter
47+automatically casts the `@ux` to a `@` first.
48+
49+Comprehensive list of the Hoon Odors
50+------------------------------------
51+
52+ @c UTF-32 codepoint
53+ @d date
54+ @da absolute date
55+ @dr relative date (ie, timespan)
56+ @f yes or no (inverse boolean)
57+ @n nil
58+ @p phonemic base
59+ @r IEEE floating-point
60+ @rd double precision (64 bits)
61+ @rh half precision (16 bits)
62+ @rq quad precision (128 bits)
63+ @rs single precision (32 bits)
64+ @s signed integer, sign bit low
65+ @sb signed binary
66+ @sd signed decimal
67+ @sv signed base32
68+ @sw signed base64
69+ @sx signed hexadecimal
70+ @t UTF-8 text (cord)
71+ @ta ASCII text (span)
72+ @tas ASCII symbol (term)
73+ @u unsigned integer
74+ @ub unsigned binary
75+ @ud unsigned decimal
76+ @uv unsigned base32
77+ @uw unsigned base64
78+ @ux unsigned hexadecimal
79+
80+Odor Size Suffixes
81+------------------
82+
83+The suffix of an odor, if present, is a single upper-case character A-Z
84+`c`, which indicates the size of an atom. This is possible, because in
85+Hoon, a letter maps to an ASCII code number, thus a number.
86+
87+Size is specified in bits in the form of `1 << (c - 'A')` resp. `2^c`,
88+since most data aligns to the power of 2 or can be composed of such
89+blocks.
90+
91+The size of a block of size `N` can be calculated for example using
92+`(bex (sub 'N' 'A'))` in bits or `(div (bex (sub 'N' 'A')) 8)` in bytes.
93+
94+Thus, `@tD` is one UTF-8 byte (whatever that means) and `@tN` is 1
95+kilobyte or less of UTF-8.
96+
97+For reference:
98+
99+ A 1 bit
100+ B 2 bits
101+ C 4 bits
102+ D 1 byte
103+ E 2 bytes
104+ F 4 bytes
105+ G 8 bytes
106+ H 16 bytes
107+ I 32 bytes
108+ J 64 bytes
109+ K 128 bytes
110+ L 256 bytes
111+ M 512 bytes
112+ N 1K
113+ O 2K
114+ P 4K
115+ Q 8K
116+ R 16K
117+ S 32K
118+ T 64K
119+ U 128K
120+ V 256K
121+ W 512K
122+ X 1MB
123+ Y 2MB
124+ Z 4MB
125+
126+It is possible to construct an atom bigger than 4Mb in size, but the
127+type system would not be able to express an odor size for it.
128+
129+There is also the datatype `++bloq` to hold a to-the-power-of block size
130+(though it is just an alias for `@`).
131+
132+------------------------------------------------------------------------
133+
134+### @c
135+
136+UTF-32 codepoint
137+
138+Atoms of the odor `@c` represent Unicode text, constructed with a UTF-32
139+bytestream, with the lowest-significant bit first. Although we usually
140+use a UTF-8 bytestream, sometimes it's useful to build atoms of one or
141+more UTF-32 words.
142+
143+##### Forms
144+
145+`~-[text]`
146+
147+##### Examples
148+
149+ ~zod/try=> ? ~-foo
150+ ~-foo
151+ @c
152+ ~zod/try=> ~-i~2764.u
153+ ~-i~2764.u
154+ ~zod/try=> (tuft ~-i~2764.u)
155+ 'i❤u'
156+ ~zod/try=> `@ux`~-foo
157+ 0x6f.0000.006f.0000.0066
158+ ~zod/try=> `@ux`~-i~2764.u
159+ 0x75.0000.2764.0000.0069
160+ ~zod/try=> `@ux`(tuft ~-i~2764.u)
161+ 0x75.a49d.e269
162+
163+------------------------------------------------------------------------
164+
165+### @d
166+
167+Date
168+
169+#### @da
170+
171+Absolute date
172+
173+Atoms of the odor `@da` represent absolute Urbit dates. Urbit dates
174+represent 128-bit chronological time, with 2\^64 seconds from the start
175+of the universe. For example, 2\^127 is 3:30:08 PM on December 5, AD
176+226. The time of day and/or second fragment is optional. As the last
177+example shows, BC times are also possible.
178+
179+##### Forms
180+
181+`~~[year].[month].[date]..[hour].[minute].[second]..[millisecond]`
182+
183+Note: the time of day and/or millisecond fragment is optional.
184+
185+##### Examples
186+
187+ ~zod/try=> ~2014.1.1
188+ ~2014.1.1
189+ ~zod/try=> ? ~2014.1.1
190+ ~2014.1.1
191+ @da
192+ ~zod/try=> ~2014.1.1..01.01.01
193+ ~2014.1.1..01.01.01
194+ ~zod/try=> ? ~2014.1.1..01.01.01
195+ ~2014.1.1..01.01.01
196+ @da
197+ ~zod/try=> ~2014.1.1..01.01.01..1234
198+ ~2014.1.1..01.01.01..1234
199+ ~zod/try=> `@da`(bex 127)
200+ ~226.12.5..15.30.08
201+ ~zod/try=> `@da`(dec (bex 127))
202+ ~226.12.5..15.30.07..ffff.ffff.ffff.ffff
203+ ~zod/try=> `@ux`~2013.12.7
204+ 0x8000.000d.2140.7280.0000.0000.0000.0000
205+ ~zod/try=> `@ux`~2013.12.7..15.30.07
206+ 0x8000.000d.2141.4c7f.0000.0000.0000.0000
207+ ~zod/try=> `@ux`~2013.12.7..15.30.07..1234
208+ 0x8000.000d.2141.4c7f.1234.0000.0000.0000
209+ ~zod/try=> `@ux`~2013.12.7..15.30.07..1234
210+ 0x8000.000d.2141.4c7f.1234.0000.0000.0000
211+
212+------------------------------------------------------------------------
213+
214+#### @dr
215+
216+Relative date (ie, timespan)
217+
218+Atoms of the odor `@dr` atoms represent basic time intervals in
219+milliseconds. There are no `@dr` intervals under a second or over a day
220+in length.
221+
222+##### Forms
223+
224+`~d[day].h[hour]m[minute].s[second]..[fractionals]`
225+
226+Note: Every measurement is optional, so long as those that are present
227+are in order. The largest measurement is preceded by a `~`.
228+
229+##### Examples
230+
231+ ~zod/try=> ~d1.h19.m5.s29
232+ ~d1.h19.m5.s29
233+ ~zod/try=> ? ~d1.h19.m5.s29
234+ ~d1.h19.m5.s29
235+ @dr
236+ ~zod/try=> `@dr`(div ~s1 1.000)
237+ ~.s0..0041.8937.4bc6.a7ef
238+ ~zod/try=> ~d1.h19.m5.s29..0041
239+ ~d1.h19.m5.s29..0041
240+ ~zod/try=> `@ux`~s1
241+ 0x1.0000.0000.0000.0000
242+ ~zod/try=> `@ux`~m1
243+ 0x3c.0000.0000.0000.0000
244+ ~zod/try=> `@dr`(div ~d1 5)
245+ ~h4.m48
246+ ~zod/try=> (div ~m1 ~s1)
247+ 60
248+ ~zod/try=> (div ~h1 ~m1)
249+ 60
250+ ~zod/try=> (div ~h1 ~s1)
251+ 3.600
252+ ~zod/try=> (div ~d1 ~h1)
253+ 24
254+ ~zod/try=> `@da`(add ~2013.11.30 ~d1)
255+ ~2013.12.1
256+
257+------------------------------------------------------------------------
258+
259+#### @f
260+
261+Loobean(inverse boolean)
262+
263+Atoms of the odor `@f` represent loobeans, where `0` is yes and `1` is
264+no. Loobeans are often represented in their cubic and runic forms shown
265+below.
266+
267+##### Forms
268+
269+`0`, `1` as numbers. `%.y`, `%.n` as [`%cube`]()s. `&`, `|` as short
270+forms.
271+
272+##### Examples
273+
274+ ~zod/try=> `@ud`.y
275+ 0
276+ ~zod/try=> ? .y
277+ %.y
278+ {%.y %.n}
279+ ~zod/try=> `@ud`.n
280+ 1
281+ ~zod/try=> .y
282+ %.y
283+ ~zod/try=> &
284+ %.y
285+ ~zod/try=> |
286+ %.n
287+
288+------------------------------------------------------------------------
289+
290+### @n
291+
292+Nil
293+
294+Atoms of the odor `@n` indicate an absence of information, as in a list
295+terminator. The only value is `~`, which is just `0`.
296+
297+ ~zod/try=> ? ~
298+ ~
299+ %~
300+ ~zod/try=> `@ud`%~
301+ 0
302+ ~zod/try=> `@ud`~
303+ 0
304+
305+------------------------------------------------------------------------
306+
307+### @p
308+
309+Phonemic base
310+
311+Atoms of `@p` are primarily used to represent ships names, but they can
312+be used to optimize any short number for memorability. For example, it
313+is great for checksums.
314+
315+##### Forms
316+
317+`~[phonemic]`
318+
319+Every syllable is a byte. Pairs of two bytes are separated by `-`, and
320+phrases of four pairs are separated by `--`.
321+
322+ ~zod/try=> ~pasnut
323+ ~pasnut
324+ ~zod/try=> ? ~pasnut
325+ ~pasnut
326+ @p
327+ ~zod/try=> `@p`0x4321
328+ ~pasnut
329+ ~zod/try=> `@p`0x8765.4321
330+ ~famsyr-dirwes
331+ ~zod/try=> `@p`0x8766.4321
332+ ~lidlug-maprec
333+ ~zod/try=> `@p`(shaf %foo %bar)
334+ ~ralnyl-panned-tinmul-winpex--togtux-ralsem-lanrus-pagrup
335+
336+------------------------------------------------------------------------
337+
338+### @r
339+
340+IEEE floating-points
341+
342+Hoon does not yet support floating point, so these syntaxes don't work
343+yet. But the syntax for a single-precision float is the normal English
344+syntax, with a `.` prefix:
345+
346+------------------------------------------------------------------------
347+
348+### @s
349+
350+Signed integer, sign bit low
351+
352+Without finite-sized integers, the sign extension trick obviously does
353+not work. A signed integer in Hoon is a different way to use atoms than
354+an unsigned integer; even for positive numbers, the signed integer
355+cannot equal the unsigned.
356+
357+The prefix for a negative signed integer is a single `-` before the
358+unsigned syntax. The prefix for a positive signed integer is `--`. The
359+least significant represents the sign. The representation is similar to
360+a folded number line.
361+
362+#### @sb
363+
364+Signed binary
365+
366+Atoms of the odor `@sb` represent signed binary numbers.
367+
368+#### Forms
369+
370+`-0b[negative_binary]` `--0b[postive_binary]`
371+
372+#### Examples
373+
374+ ~zod/try=> ? -0b1
375+ -0b1
376+ @sb
377+ ~zod/try=> `@sd`-0b1
378+ -1
379+ ~zod/try=> `@sd`--0b1
380+ --1
381+ ~zod/try=> `@sd`--0b11
382+ --3
383+ ~zod/try=> `@sb`(sum:si -0b10 -0b10)
384+ -0b100
385+
386+------------------------------------------------------------------------
387+
388+#### @sd
389+
390+Signed decimal
391+
392+Atoms of odor `@sd` represent signed decimal numbers.
393+
394+#### Forms
395+
396+`-[negative[decimal]()]` `--[postive_[decimal]()]`
397+
398+#### Examples
399+
400+ ~zod/try=> -234
401+ -234
402+ ~zod/try=> ? -234
403+ -234
404+ @sd
405+ ~zod/try=> ? --234
406+ --234
407+ @sd
408+ ~zod/try=> (sum:si -234 --234)
409+ --0
410+
411+------------------------------------------------------------------------
412+
413+#### @sv
414+
415+Signed base32
416+
417+Atoms of odor `@sv` represent signed base32 numbers.
418+
419+##### Forms
420+
421+`-0v[negative_base32]` The digits are, in order, `0-9`, `a-v`.
422+`--0v[positive_base32]`
423+
424+##### Examples
425+
426+ ~zod/try=> -0vv
427+ -0vv
428+ ~zod/try=> ? -0vv
429+ -0vv
430+ @sv
431+ ~zod/try=> --0vb
432+ --0vb
433+ ~zod/try=> `@sd`-0vv
434+ -31
435+ ~zod/try=> `@sd`--0vb
436+ --11
437+ ~zod/try=> `@sd`(sum:si -0vv --0vb)
438+ -20
439+
440+------------------------------------------------------------------------
441+
442+#### @sw
443+
444+Signed base64
445+
446+Atoms of odor `@sw` represent base64 numbers.
447+
448+##### Forms
449+
450+`-0w[negative_base64]` The digits are, in order, `0-9`, `a-z`,
451+`A-Z`,`-`, and `~`. `--0w[positive_base64]` The digits are, in order,
452+`0-9`
453+
454+##### Examples
455+
456+ ~zod/try=> -0w--
457+ -0w--
458+ ~zod/try=> ? -0w--
459+ -0w--
460+ @sw
461+ ~zod/try=> `@sd`(sum:si -0w-A -0w--)
462+ -8.034
463+
464+#### @sx
465+
466+Signed hexadecimal
467+
468+Atoms of odor `@sx` represent signed hexadecimal numbers.
469+
470+##### Forms
471+
472+`-[negative_hexadecimal]` `--[positive_hexadecimal]`
473+
474+##### Examples
475+
476+ ~~zod/try=> -0x0
477+ --0x0
478+ ~zod/try=> `@sd`--0x17
479+ --23
480+ ~zod/try=> `@ux`(bex 20)
481+ 0x10.0000
482+ ~zod/try=> 0x10. 0000
483+ 0x10.0000
484+ ~zod/try=> `@sd`(sum:si --0x17 -0x0)
485+ --23
486+ ~zod/try=> `@sd`(sum:si --0x17 -0xa)
487+ --13
488+
489+------------------------------------------------------------------------
490+
491+### @t
492+
493+UTF-8 text (cord)
494+
495+Atoms of the odor `@t` represent a
496+[cord](http://en.wikipedia.org/wiki/Rope_data_structure), sequence of
497+UTF-8 bytes, LSB first. It is sometimes called a cord.
498+
499+##### Forms
500+
501+`~~[text]` `'[text]'`
502+
503+##### Examples
504+
505+ ~zod/try=> ~~foo
506+ 'foo'
507+ ~zod/try=> ? 'foo'
508+ 'foo'
509+ @t
510+ ~zod/try=> ? ~~foo
511+ 'foo'
512+ @t
513+
514+------------------------------------------------------------------------
515+
516+#### @ta
517+
518+ASCII text (span)
519+
520+Atoms of the odor `@ta` represent the ASCII text subset used in hoon
521+literals: `a-z`, `0-9`, `~`, `-`, `.`, `_`.
522+
523+##### Forms
524+
525+`~.[text]` There are no escape sequences.
526+
527+##### Examples
528+
529+ ~zod/try=> ~..asdf
530+ ~..asdf
531+ ~zod/try=> ? ~.asdf
532+ ~.asdf
533+ @ta
534+ ~zod/try=> `@t`~.asdf
535+ 'asdf'
536+
537+------------------------------------------------------------------------
538+
539+#### @tas
540+
541+ASCII symbol (term)
542+
543+Atoms of `@tas` represent [`++term`]()s, the most exclusive text odor.
544+The only characters permitted are lowercase ASCII, except as the first
545+or last character, and 0-9, except as the first character.
546+
547+##### Forms
548+
549+`%[text]` This means a term is always [cubical]().
550+
551+##### Examples
552+
553+ ~zod/try=> %dead-fish9
554+ %dead-fish9
555+ ~zod/try=> -:!>(%dead-fish9)
556+ [%cube p=271.101.667.197.767.630.546.276 q=[%atom p=%tas]]
557+
558+------------------------------------------------------------------------
559+
560+### @u
561+
562+Unsigned integer
563+
564+------------------------------------------------------------------------
565+
566+#### @ub
567+
568+Unsigned binary
569+
570+Atoms of the odor `@ub` represent unsigned binary numbers.
571+
572+#### Forms
573+
574+`0b[number]` Numbers are least-significant bit first.
575+
576+##### Examples
577+
578+ ~zod/try=> `@`0b1
579+ 1
580+ ~zod/try=> ? 0b1
581+ 0b1
582+ @ub
583+ ~zod/try=> `@`0b10
584+ 2
585+ ~zod/try=> `@`0b100
586+ 4
587+
588+------------------------------------------------------------------------
589+
590+#### @ud
591+
592+Unsigned decimal
593+
594+Atoms of `@ud` represent unsigned decimal numbers. It is the default
595+print format for both `@u` and and `@u`, namely unsigned numbers with no
596+printing preference, as well as opaque atoms.
597+
598+##### Forms
599+
600+Numbers of more than three digits must be delimited by `.`s. Whitespace
601+and linebreaks can appear between the dot and the next group.
602+
603+ ~zod/try=> 0
604+ 0
605+ ~zod/try=> 19
606+ 19
607+ ~zod/try=> ? 19
608+ 19
609+ @ud
610+ ~zod/try=> 1.024
611+ 1.024
612+ ~zod/try=> 65.536
613+ 65.536
614+ ~zod/try=> (bex 20)
615+ 1.048.576
616+
617+------------------------------------------------------------------------
618+
619+#### @uv
620+
621+Unsigned base32
622+
623+Atoms of the odor `@uv` represent unsigned base64 numbers.
624+
625+##### Forms
626+
627+`0v[number]` The digits are, in order, `0-9`, `a-v`.
628+
629+##### Examples
630+
631+ ~zod/try=> `@ud`0vv
632+ 31
633+ ~zod/try=> ? 0vv
634+ 0vv
635+ @uv
636+ ~zod/try=> `@ud`(add 0vv 0v9)
637+ 40
638+
639+------------------------------------------------------------------------
640+
641+#### @uw
642+
643+Unsigned base64
644+
645+##### Forms
646+
647+`ow[number]` The digits are, in order, `0-9`, `a-z`, `A-Z`,`-`, and `~`.
648+
649+##### Examples
650+
651+ ~zod/try=> 0w~
652+ 0w~
653+ ~zod/try=> ? 0w~
654+ 0w~
655+ @uw
656+ ~zod/try=> `@uv`(add 0w~ 0wZ)
657+ 0v3s
658+ ~zod/try=> `@ud``@uv`(add 0w~ 0wZ)
659+ 124
660+
661+------------------------------------------------------------------------
662+
663+#### @ux
664+
665+Unsigned hexadecimal
666+
667+Atoms of the odor `@ux` represent hexadecimal numbers.
668+
669+##### Forms
670+
671+`0x`number. Numbers with more than four digits must be delimited by
672+`.`s. Hex digits are lowercase only.
673+
674+ ~zod/try=> 0x0
675+ 0x0
676+ ~zod/try=> ? 0x0
677+ 0x0
678+ @ux
679+ ~zod/try=> `@ud`0x17
680+ 23
681+ ~zod/try=> `@ux`(bex 20)
682+ 0x10.0000
683+ ~zod/try=> 0x10. 0000
684+ 0x10.0000
685+
686+------------------------------------------------------------------------
docs/programming/hoon/cheat-sheets/pronunciation.mdnew file+68
@@ -0,0 +1,68 @@
1+Pronunciation
2+=============
3+
4+Overview
5+--------
6+
7+Hoon is a reserved-word-free
8+language - any text in the program is part of the program.
9+
10+We use so many of these ASCII glyphs that we like to be able
11+to read them out loud. A language is meant to be _said_. The
12+squiggles have conventional names, sort of, some of them easy to
13+say, others not so much. So we've renamed them:
14+
15+ ace space
16+ bar |
17+ bas \
18+ buc $
19+ cab _
20+ cen %
21+ col :
22+ com ,
23+ doq "
24+ dot .
25+ fas /
26+ gal <
27+ gar >
28+ hax #
29+ hep -
30+ kel {
31+ ker }
32+ ket ^
33+ lus +
34+ pam &
35+ pat @
36+ pel (
37+ per )
38+ sel [
39+ sem ;
40+ ser ]
41+ sig ~
42+ soq '
43+ tar *
44+ tec `
45+ tis =
46+ wut ?
47+ zap !
48+
49+Memorizing these names seems like a burden, but it actually makes
50+communicating about hoon code a lot faster and easier. `bartis`
51+sounds a lot better than 'bar equals'.
52+
53+To pronounce a rune, concatenate the glyph names, stressing the
54+first syllable and softening the second vowel into a "schwa."
55+Hence, to say `~.`, say "sigdot." To say `|=`, say "bartis."
56+Which has an inevitable tendency to turn into "barts" - a sin
57+to be encouraged.
58+
59+There are a few runes with irregular special pronunciations:
60+
61+ -- hephep phep
62+ +- lushep slep
63+ ++ luslus slus
64+ == tistis stet
65+ -> hepgar lark
66+ -< hepgal lush
67+ +> lusgar dark
68+ +< lusgal dush
docs/programming/hoon/concepts.md+5−19
@@ -16,7 +16,7 @@ ones, which mean almost the same things. But why?
1616
1717## Motivation
1818
19−Hoon has no close relatives. The normal jargon of programming
19+Hoon has no close relatives, and the normal jargon of programming
2020maps poorly onto its semantics. For example, although Hoon is a
2121typed language, the term "type" is not formally defined in Hoon.
2222"Type" is a great word, but Hoon has three quite separate
@@ -64,12 +64,12 @@ scheme which maps an atom to a subtree. The whole noun is slot
6464
6565### `nock` (interpreter)
6666
67−Hoon compiles itself to the [Nock](../nock) VM. Nock is a
67+Hoon compiles itself to the [Nock](nock) VM. Nock is a
6868Turing-complete, non-lambda combinator function. The function
6969takes a cell `{subject formula}`, and produces a noun `product`.
7070
7171To program in Hoon, this is all you need to know about Nock. But
72−it's still fun and useful to [learn more](../nock).
72+it's still fun and useful to [learn more](nock).
7373
7474## Compilation concepts
7575
@@ -81,21 +81,6 @@ expression (AST), and a `nock` is a Nock formula. `mint` accepts
8181a subject type and a source expression; it produces a product type
8282and an executable formula.
8383
84−Calculating the output type from the input type and the source
85−code is called "type inference." If you've used another typed
86−functional language, like Haskell, Hoon's type inference does the
87−same job but with less intelligence.
88−
89−Haskell infers backward and forward; Hoon only infers forward.
90−Hoon can't figure out the type of a noun from how you use it,
91−only from how you make it. Hoon can infer tail recursion, but
92−not head recursion.
93−
94−Low-powered type inference means you need more type annotations,
95−which makes your program more readable anyway. Also, the dumber
96−the compiler, the easier it is for a dumb human to understand
97−what the compiler is thinking.
98−
9984### `twig` (expression)
10085
10186A [`twig`](twig) is a Hoon AST node, the result of parsing a
@@ -202,7 +187,8 @@ arm `foo`. If it finds a face, the product is a *leg*, or
202187subtree of the subject. If it finds a core, it computes the arm
203188formula with that core as the subject.
204189
205−A limb can also be a slot (direct tree address), like `+15`.
190+A limb can also be a slot (tree address), like `+15`, which
191+takes a leg directly.
206192
207193### `wing` (limb path)
208194
docs/programming/hoon/demo.md+2−2
@@ -27,8 +27,8 @@ line is commented with its number:
2727:moar(count (add 1 count)) :: 15
2828```
2929
30−Can you understand this code by just looking at it? Maybe.
31−But let's explain it anyway.
30+Can you understand this code by just looking at it? Hopefully,
31+but let's explain it anyway.
3232
3333Hoon is a functional language. FizzBuzz is usually defined as a
3434side effect, but Hoon has no side effects. This code will
docs/programming/hoon/examples.md+1−2
@@ -1,7 +1,6 @@
11---
2−sort: 9
2+sort: 8
33title: Examples
4−next: true
54---
65
76# Examples
docs/programming/hoon/library.md+4−3
@@ -1,8 +1,9 @@
11---
2−sort: 11
3−title: Library
2+sort: 12
3+title: Standard Library
44---
55
6−# Library
6+Library
7+========
78
89<list dataPreview="true" titlesOnly="true"></list>
docs/programming/hoon/mint.mdnew file+27
@@ -0,0 +1,27 @@
1+---
2+sort: 6
3+next: true
4+Title: Compiler
5+---
6+
7+# Compiler: `mint`
8+
9+`mint` is the Hoon compiler. It maps a cell `{subject/span
10+source/twig}` to a cell `{product/span formula/nock}`, where
11+`span` is a type, `twig` is a compiled expression, and `nock` is
12+a Nock formula.
13+
14+Calculating the output type from the input type and the source
15+code is called "type inference." If you've used another typed
16+functional language, like Haskell, Hoon's type inference does the
17+same job but with less intelligence.
18+
19+Haskell infers backward and forward; Hoon only infers forward.
20+Hoon can't figure out the type of a noun from how you use it,
21+only from how you make it. Hoon can infer tail recursion, but
22+not head recursion.
23+
24+Low-powered type inference means you need more type annotations,
25+which makes your program more readable anyway. (Also, the dumber
26+the compiler, the easier it is for a dumb human to understand
27+what the compiler is thinking.)
docs/programming/hoon/noun.mdnew file+37
@@ -0,0 +1,37 @@
1+---
2+sort: 4
3+next: true
4+title: Data model: noun
5+---
6+
7+# Data model: `noun`
8+
9+A value in Hoon is called a `noun`. A noun is either a unsigned
10+integer of any size (`atom`), or an ordered pair of any two
11+nouns (`cell`). In other words, a noun is a binary tree whose
12+leaves are unsigned integers.
13+
14+Nouns are a Nock concept; there is no Nock syntax; so there is no
15+general noun syntax. But nouns are usually written with square
16+brackets associating right; `[a b c]` means `[a [b c]]`. In Hoon
17+we also see `{a b c}`, a constructor (`mold`) for `[a b c]`.
18+
19+Nouns are almost like Lisp's S-expressions, but S-expressions
20+have dynamic type tags in atoms; the difference between a symbol
21+and an integer, for instance, is dynamic type. Lisp needs this
22+dynamic type because it doesn't expect a static type system.
23+
24+For the same reason, nouns tend to be tuple-centric where Lisp is
25+list-centric. Lisp `(a b c)` as a noun is `[a b c 0]`; Nock `[a
26+b c]` is Lisp `(a . b . c)`.
27+
28+Nouns are immutable and acyclic. A naive implementation uses
29+reference counting and needs no tracing GC. There is no test for
30+pointer equality as in Lisp. But indirect nouns have a lazily
31+computed short hash, so nonduplicates have O(1) comparison cost.
32+
33+All kinds of atomic values can be and are stored as atoms:
34+unsigned integers, signed integers (with sign bit low), dates,
35+floats, UTF-8 strings (LSB first), even whole files. Again,
36+a static type system is essential; an atom is not usable or even
37+printable if we don't know what it means.
docs/programming/hoon/philosophy.md+19−15
@@ -13,10 +13,10 @@ Hoon's design goal is to support higher-order typed functional
1313programming without category theory, formal logic, or other
1414interesting math. The reasoning: (a) a programming language is a
1515user interface for programmers; (b) most programmers are not very
16−good at math.
16+good at math. Hoon is not quite as expressive as Haskell, though
17+fairly close.
1718
18−Hoon is not quite as expressive as Haskell, though fairly close.
19−But good Hoon style isn't good Haskell style. Hoon encourages
19+Good Hoon style varies from good Haskell style. Hoon encourages
2020coders to use higher-order programming as little as possible --
2121again, simply for UI reasons. For example, multiple arguments
2222are curried by default in Haskell and tupled by default in Hoon.
@@ -25,18 +25,22 @@ a functional language." The power of Haskell, or close, is there
2525when we really need it. But we try not to swat flies with it.
2626
2727Hoon is objectively simple: its complexity is bounded by the size
28−of the compiler, about 3000 lines of Hoon. This is split evenly
29−between frontend (parsing and macro expansion) and backend (code
30−generation and type inference).
31−
32−Compared to most languages, Hoon has a heavier front end (more
33−complex syntax) and a lighter back end (less complex semantics).
34−This ratio reflects the belief that our brains are better than
35−everyone thinks at learning languages (symbols and/or grammars),
36−and worse at learning abstractions (proofs and/or algorithms).
37−At first glance, Hoon may look gnarly (though its squiggles are
38−more structured than most ASCII-heavy languages). But there's
39−less than you might expect under the hood.
28+of the compiler, about 3000 lines of Hoon. This is split about
29+halfway half between frontend (parsing and macro expansion) and
30+backend (code generation and type inference).
31+
32+This parser-heavy ratio reflects the belief that our brains are
33+better than everyone thinks at learning languages (symbols and/or
34+grammars), and worse at learning abstractions (proofs and/or
35+algorithms). At first glance, Hoon may look gnarly (though its
36+squiggles are more structured than most ASCII-heavy languages).
37+But there's less than you might expect under the hood.
38+
39+(Hoon has simple principles and a lot of details. To keep the
40+details from getting overwhelming, we start out learning a
41+simplified subset called Core Hoon. Note that some of the
42+internal structures we show are simplified to match the subset.
43+These simplifications are corrected in the Advanced section.)
4044
4145Keeping the Hoon-to-Nock mapping straightforward is a priority.
4246Very roughly, Hoon is to Haskell as C is to Pascal. Pascal tries
docs/programming/hoon/basic.md → docs/programming/hoon/span.mdrenamed+31−23
@@ -1,16 +1,14 @@
11---
2−sort: 5
2+sort: 6
33next: true
4−title: Basic types
4+title: Type: span
55---
66
7−# Basic types
7+# Type: `span`
88
99A `span` is a set of nouns and an interpretation of these nouns.
10−Officially, we don't use the word "type" in Hoon. But if we had
11−to say "type," it would mean `span`.
1210
13−## Span and mold
11+## Span, mold, type: what's in a type system?
1412
1513There is no Hoon syntax for a span. The programmer never defines
1614a span explicitly. It is always produced as the inferred range
@@ -28,8 +26,8 @@ the standard form is useful. The standard form is a constructor
2826function, or *mold*.
2927
3028A mold is an idempotent function (`gate`), accepting any noun.
31−(An idempotent function is one such that *f(f(x))* equals *f(x)*
32−if *f(x)* terminates.) The product range of the function is the
29+(An idempotent function is one such that f(f(x)) equals f(x) if
30+f(x) does not crash.) The product range of the function is the
3331span, or *icon*, of the mold.
3432
3533Usually we use molds purely in the first sense: as an abstract
@@ -37,16 +35,29 @@ definition of a noun. Don't actually call a mold unless you're
3735actually validating untrusted foreign data. As a beginner,
3836hopefully you aren't!
3937
40−## The `span` mold (simplified)
38+(It's also important to remember that any twig can be a mold.
39+Some stems are macros designed for making molds, but a mold is
40+defined by how it's used, not what it's made of. The Hoon type
41+system cannot even check the mold definition, since Hoon lacks
42+dependent type and therefore can't verify idempotence.)
43+
44+To summarize: a Hoon "type declaration" is the definition of a
45+function, the mold. A mold and a span are different things. A
46+mold is a constructor. A span defines a set of nouns, possibly
47+infinite, and annotates them with semantics.
48+
49+Either mold or span could be called a "type," but not both. We
50+often say "type" in Hoon. But we always mean it informally.
51+Ideally, the meaning is obvious from context. ("Type" can also
52+mean a `mark`, Urbit's equivalent of a MIME type.)
53+
54+## The `span` mold
4155
4256Usually in Hoon we define the semantics of a primitive by the
4357state the span of all nouns that implement that primitive. We
4458state this span as the icon of a mold. That mold is produced by
4559a kernel arm `span`:
4660
47−This is a slightly simplified version of `span`. We'll undo and
48−explain the simplifications below.
49−
5061```
5162++ term @tas
5263++ span
@@ -54,7 +65,7 @@ explain the simplifications below.
5465 $void
5566 == $% {$atom p/term q/(unit atom)}
5667 {$cell p/span q/span}
57− {$core p/span q/(map term twig)}
68+ {$core p/span q/(map term span)}
5869 {$face p/term q/span}
5970 {$fork p/(set span)}
6071 {$hold p/span q/twig}
@@ -67,29 +78,26 @@ pseudocode. If a span is an atom, it's either the atomic string
6778`atom`, `cell`, `core`, etc. We'll go through each of these
6879cases below.
6980
70−### `$noun` and `$void`
81+## `$noun` and `$void`
7182
7283`$noun` is the set of all nouns. `$void` is the set of no nouns.
7384
74−### `{$cell p/span q/span}`
85+## `{$cell p/span q/span}`
7586
7687`{$cell p/span q/span}` is the set of all cells with head `p` and
7788tail `q`.
7889
79−### `{$fork p/(set span)}
90+## `{$fork p/(set span)}
8091
8192`{$fork p/(set span)}` is the union of all spans in the set `p`.
8293
83−### `{$hold p/span q/twig}`
94+## `{$hold p/span q/twig}`
8495
8596A `$hold` span, with span `p` and twig `q`, is a lazy reference
8697to the span of `(mint p q)`. In English it means: "the type of
8798the product when we compile `q` against subject `p`.
8899
89−This is "manual laziness." Hoon is a strict language, so we have
90−to express
91−
92−### `{$face p/term q/span}
100+## `{$face p/term q/span}
93101
94102A `{$face p/term q/span}` wraps the label `p` around the span
95103`q`. `p` is a `term` or `@tas`, an atomic ASCII string which
@@ -99,7 +107,7 @@ first character must be lowercase.
99107See the [twig chapter](twig) for how labels are resolved. It's
100108nontrivial.
101109
102−### `{%atom p/term q/(unit atom))}
110+## `{%atom p/term q/(unit atom))}
103111
104112An `$atom` is an atom, with two twists. `q` is a `unit`, Hoon's
105113equivalent of a nullable pointer or a Haskell `Maybe`. If `q`
@@ -123,7 +131,7 @@ statically, by casting through the empty aura `@`. Hoon is not
123131dependently typed and can't statically enforce data constraints
124132(for example, it can't enforce that a `@tas` is really a symbol).
125133
126−### `{$core p/span q/(map term span)}
134+## `{$core p/span q/(map term span)}
127135
128136A `$core` is a code-data cell. The data (or *payload*) is the
129137tail; the code (or *battery*) is the head. `p`, a span, is the
docs/programming/hoon/troubleshooting.md+1−2
@@ -1,7 +1,6 @@
11---
2−sort: 8
2+sort: 9
33title: Troubleshooting
4−next: true
54---
65
76# Troubleshooting
docs/programming/hoon/twig.md+8−12
@@ -1,14 +1,13 @@
11---
2−sort: 6
2+sort: 7
33next: true
4−title: Expressions
4+title: Expressions: twig
55---
66
7−# Expressions
7+# Expression: `twig`
88
9−A Hoon expression is called a `twig`. A `twig` is an AST node:
10−the noun that the Hoon compiler makes when it parses a source
11−expression.
9+A `twig` is an AST node: the noun that the Hoon compiler makes
10+when it parses a source expression.
1211
1312The definition of `twig` is the definition of Hoon. So let's
1413define the syntax and semantics of Hoon, a twig at a time. But
@@ -38,12 +37,9 @@ syntax and semantics; again, the difference is how we use it.
3837
3938Twigs are described as *mossy* (or *moldy*) and *seedy*; an
4039example of X is the seedy form of X, a mold producing X is its
41−mossy form.
42−
43−For instance, `[%foo %bar]` is seedy: a twig producing the noun
44−`[7.303.014 7.496.034]`. `{$foo $bar}` is mossy: a twig
45−producing a function whose product is always `[7.303.014
46−7.496.034]`.
40+mossy form. For instance, `$foo` (mossy) is a mold whose product
41+is always `%foo` (seedy). (Obviously, seed is *yang* and moss is
42+*yin*, so we can also say "yang foo" or "yin foo".)
4743
4844## Twig categories
4945
docs/programming/hoon/twig/atom.md+1−2
@@ -1,6 +1,5 @@
11---
2−sort: 1
3−next: true
2+sort: 2
43---
54
65# Atoms, constants, quasi-constants
docs/programming/hoon/twig/call.mdnew file+121
@@ -0,0 +1,121 @@
1+---
2+sort: 7
3+---
4+
5+# Full make (`%` runes)
6+
7+We've already covered the irregular-only twigs `$wing` and
8+`$limb`. These are simple forms of the *invocation* family of
9+twigs, `%`, whose general form is `$make`, `%=`.
10+
11+## Regular forms
12+
13+The rune prefix is `%`. Suffixes: `=` for `:make`, `~` for
14+`:open`, `-` for `:call`, `+` for `:calt`, `^` for `:calq`, `*`
15+for `:calp`.
16+
17+### `:make`, `%=`, "centis", `{$make p/wing q/(list (pair wing twig))}`
18+
19+Syntax: *1-fixed*, then *jogging*.
20+
21+The product: `p`, modified by the change list `q`.
22+
23+If `p` resolves to a leg, `q` is a list of changes to that leg.
24+If `p` resolves to an arm, `q` is a list of changes to the core
25+containing that arm. We compute the arm on the modified core.
26+
27+### `:open`, `%~`, "censig", `{$open p/wing q/twig r/twig}`
28+
29+Syntax: *3-fixed*.
30+
31+Expands to:
32+
33+```
34+ :pin q
35+ :make(p.+2 +6 :per(+3 r))
36+```
37+
38+We pin `q`, making our subject `[q subject]`. We make arm `p` on
39+`q`, changing leg `6` to `r` (per the original subject).
40+
41+Wut? Why? `$open` is a general case of `$call`; see below.
42+
43+### `:call`, `%-`, "cenhep", `{$call p/twig q/twig}`/
44+
45+Syntax: *2-fixed*.
46+
47+Expands to: `:open($ p q)`.
48+
49+`$call` is a function call; `p` is the function (`gate`), `q` the
50+argument. `$call` is a special case of `$open`, and a gate is a
51+special case of a `door` (see the [core](../core) twigs).
52+
53+In a gate, the modified core has only one anonymous arm; in a
54+door it gets a full battery. Intuitively, a gate defines one
55+algorithm it can compute upon its sample, `+6`. A door defines
56+many such algorithms.
57+
58+In classical languages, doors correspond to groups of functions
59+with the same argument list, or at least sharing a prefix. In
60+Hoon, this shared sample is likely to be pulled into a door.
61+
62+### `:calt`, `%+`, "cenlus", `{$calt p/twig q/twig r/twig}`
63+
64+Syntax: *3-fixed*.
65+
66+Expands to: `:(call p [q r])`.
67+
68+### `:calq`, `%^`, "cenket", `{$cnkt p/twig q/twig r/twig s/twig}`
69+
70+Syntax: *4-fixed*.
71+
72+Expands to: `:(call p [q r s])`.
73+
74+### `:calp`, `%*`, "centar", `{$cntr p/twig q/(list twig)}`
75+
76+Syntax: *4-fixed*.
77+
78+Expands to: `:(call p [q])`.
79+
80+## Irregular forms
81+
82+### Classic call, `(p q r s)`
83+
84+Translation:
85+
86+```
87+(p) :per(p $)
88+(p q) :call(p q)
89+(p q r s) :call(p [q r s])
90+```
91+
92+### Modified wing, `p.q(r s, t u, v w)`
93+
94+Translation:
95+
96+```
97+p.q(r s, t u, v w) :make(p.q r s, t u, v w)
98+```
99+
100+### Anonymous recursion, `:moar*`.
101+
102+Translation:
103+
104+```
105+:moar $
106+:moar(a b, c d, e f) $(a b, c d, e f)
107+:moarr ^$
108+:moarrrr ^^^$
109+```
110+
111+`:moar` has tall and wide form like a regular stem, though it has
112+no rune and is not a regular stem.
113+
114+`$` is a label like any other. But loops, gates, and traps all
115+hardcode this label. `$` thus implies recursing back to the
116+nearest `:loop` (`|-)`, `:gate` (`|=`), or `:trap` (`|.`). (Or
117+`^$` for the second nearest, `^^$` for the third, etc.
118+
119+`$` *seems* like a language primitive (eg, Clojure's `recur`), so
120+we made it look like one. Keyword enthusiasts and cats who love
121+cheeseburgers will appreciate `:moar`. Others can use `$`.
docs/programming/hoon/twig/cast.mdnew file+53
@@ -0,0 +1,53 @@
1+---
2+sort: 10
3+---
4+
5+# Type manipulation (`^` runes).
6+
7+`$cast`, `$like`, and `$name` let us adjust spans without
8+violating type constraints.
9+
10+The `nest` algorithm which tests span subtyping is conservative;
11+it never allows invalid nests, it sometimes rejects valid nests.
12+
13+## Regular forms
14+
15+### `:like`, `^+`, "ketlus", `{$like p/twig q/twig}`
16+
17+Syntax: *2-fixed*.
18+
19+The product is the formula of `q` with the span of `p`, provided
20+nouns within the span of `q` can be shown to nest within the span
21+of `p`.
22+
23+### `:cast`, `^-`, "ketlus", `{$like p/moss q/twig}`
24+
25+Syntax: *2-fixed*.
26+
27+Expands to: `:like($.p q)`.
28+
29+`$like` is a typecheck by example; `$cast` is a typecheck by
30+mold.
31+
32+### `:name`, `^=`, "kettis", `{$name p/@tas q/twig}
33+
34+Syntax: *2-fixed*.
35+
36+The product: the formula of `q`, with the span of `q` labeled by
37+symbol `p`.
38+
39+### Irregular forms
40+
41+### Backtick cast: `\`foo\`bar`
42+
43+Translation:
44+```
45+`foo`bar ^-(foo bar)
46+```
47+
48+### Infix name: `foo=bar`
49+
50+Translation:
51+```
52+foo=bar ^=(foo bar)
53+```
docs/programming/hoon/twig/cell.mdnew file+83
@@ -0,0 +1,83 @@
1+---
2+sort: 4
3+---
4+
5+# Cell construction (`:` runes)
6+
7+The cell twigs, `$cons` and friends, are simple and regular.
8+All `:` twigs expand to `$cons`.
9+
10+## Twigs
11+
12+```
13+|%
14+++ twig
15+ {$scon p/twig q/twig}
16+ {$conq p/twig q/twig r/twig s/twig}
17+ {$cons p/twig q/twig}
18+ {$cont p/twig q/twig r/twig}
19+ {$conl p/(list twig)}
20+ {$conp p/(list twig)}
21+--
22+```
23+
24+All construction stems expand to one natural stem, `$cons`, the
25+pair constructor, named for the Lisp special form.
26+
27+Synthetic stems change the last letter to indicate the bulb type:
28+`$cont` for triple, `$conq` for quad, `$conp` for tuple, `$conl`
29+for list. `$scon` is the reverse.
30+
31+## Regular forms
32+
33+The rune prefix is `:`. Suffixes: `-` for pair, `+` for triple,
34+`^` for quad, `*` for tuple, `~` for list, `_` for reverse.
35+
36+### `:cons`, `:-`, "colhep", `{$cons p/twig q/twig}`,
37+
38+*Construct a cell (2-tuple*).
39+
40+Syntax: *2-fixed*.
41+
42+The product: the cell of `p` and `q`, each compiled against
43+the subject.
44+
45+### `:cont`, `:+`, "collus", `{$cont p/twig q/twig r/twig}`,
46+
47+Syntax: *3-fixed*.
48+
49+Expands to: `:cons(p :cons(q r))`.
50+
51+### `:conq`, `:^`, "colket", `{$cont p/twig q/twig r/twig s/twig}`,
52+
53+Syntax: *4-fixed*.
54+
55+Expands to: `:cons(p :cont(q r s))`.
56+
57+### `:conp`, `:*`, "coltar", `{$conp p/(list twig)}`,
58+
59+Syntax: *running*.
60+
61+Expands by: `|-(?~(p ~ ?~(t.p i.p [%cons i.p $(p t.p)])))`.
62+
63+### `:conl`, `:~`, "colsig", `{$conl p/(list twig)}`, "construct list"
64+
65+Syntax: *running*.
66+
67+Expands by: `|-(?~(p [%rock %n ~] [%cons i.p $(p t.p)]))`.
68+
69+### `:scon`, `:_`, "colcab", `{$scon p/twig q/twig}`, "construct backward"
70+
71+Syntax: *running*.
72+
73+Expands to: `[%cons q p]`.
74+
75+## Irregular forms
76+
77+### Bracket tuple, `[p q r s]`
78+
79+Translation:
80+
81+```
82+[p q r s] :conp(p q r s)
83+```
docs/programming/hoon/twig/core.mdnew file+90
@@ -0,0 +1,90 @@
1+---
2+sort: 6
3+---
4+
5+# Cores (`|` runes)
6+
7+Core twigs are flow twigs. The compiler essentially pins a Nock
8+formula, or battery of formulas, to the subject.
9+
10+All `|` twigs are macros around `$core`. (See the `$core`
11+section in [`span`](../span) above.) `$core` uses the subject as
12+the payload of a battery, whose arms are compiled with the core
13+itself as the subject.
14+
15+## Regular forms
16+
17+The rune prefix is `|`. Suffixes: `%` for `:core`, `=` for
18+`:gate`, `-` for `:loop`, `.` for `:trap`, `_` for `:door`.
19+
20+### `:core`, `|%`, "barcen", `{$core p/(map term twig)}`
21+
22+Syntax: *battery*
23+
24+The product: a core with battery `p`. Payload is the subject.
25+
26+### `:gate`, `|=`, "bartis", `{$gate p/moss q/twig}
27+
28+Syntax: *2-fixed*.
29+
30+Expands to:
31+
32+```
33+:new p
34+:core
35+++ $
36+ q
37+--
38+```
39+
40+A `$gate` produces a function from `p` to `q`. `p` is the
41+*sample*, or argument. The core has one formula, named `$` (the
42+empty name). The payload is of the form `{sample context}`,
43+where `context` is the subject of the gate.
44+
45+### `:loop`, `|-`, "barhep", `{$loop p/twig}`
46+
47+Syntax: *1-fixed*.
48+
49+Expands to:
50+
51+```
52+ :rap $
53+ :core
54+ ++ $
55+ p
56+ --
57+```
58+
59+A `$loop` makes a core with one anonymous arm `p`, then takes
60+that arm.
61+
62+### `:trap`, `|.`, "bardot", `{$trap p/twig}`
63+
64+Syntax: *1-fixed*.
65+
66+Expands to:
67+
68+```
69+ :core
70+ ++ $ p
71+ --
72+```
73+
74+A `$trap` is a deferred value.
75+
76+### `:door`, `|_`, "barcab", `{$door p/moss q/(map term twig)}`
77+
78+Syntax: *1-fixed*, then *battery*.
79+
80+Expands to:
81+
82+```
83+ :new p
84+ :core
85+ q
86+ ==
87+```
88+
89+A `gate` is a function; a `door` is the general case of a
90+function. Wut? We'll look at this again from the caller's side.
docs/programming/hoon/twig/flow.mdnew file+143
@@ -0,0 +1,143 @@
1+---
2+sort: 5
3+---
4+
5+# Subject flow (`=` runes)
6+
7+Flow twigs change the subject. (Or more precisely, a flow twig
8+compiles at least one of its subtwigs with a different subject.)
9+All non-flow twigs (except cores) pass the subject down unchanged.
10+
11+## Overview
12+
13+The simplest way to change the subject is to compose two twigs,
14+`p` and `q`. Let `x` be `(mint subject p)`, with product span
15+`p.x` and nock formula `q.x`. Let `y` be `(mint p.x q)`. Then
16+their composition is `[p.y [7 q.x q.y]]`.
17+
18+This composition is the `$per` twig. A close relative is `$pin`,
19+which is `$per` over `[p .]`. The new subject is a cell of `p`
20+and the old subject. `$pin` is the simplest Hoon equivalent of
21+"declaring a variable" (introducing new data into the subject).
22+
23+Another way to change the subject is to mutate it. With the
24+`$set` twig, given a wing that resolves to a leg, we can write
25+instead of reading, *installing* a new value at that leg. Of
26+course, we are creating a copy, not modifying the original.
27+
28+## Structures
29+
30+### `taco`: name with optional filling
31+
32+A `taco` is either a symbol or a symbol-mold cell. The mold is a
33+typecheck and cast. For instance, when "initializing a variable"
34+with `:var`, we can cast the inferred type of the initial value
35+to match an explicit `taco` mold, or just state the symbol and
36+use the inferred type.
37+
38+The `taco` syntax is `foo` for the symbol foo, or `foo/bar` for
39+symbol `foo` and mold `bar`.
40+
41+## Definitions
42+
43+The rune prefix is `=`. Suffixes: `>` for `:per`, `<` for
44+`:rap`, `+` for `:pin`, `-` for `:nip`, `|` for `:new`, `/` for
45+`:var`, `;` for `:rev`, `.` for `:set`, and `^` for `:sip`.
46+
47+### `:per`, `=>`, "tisgar", `{$per p/twig q/twig}`, "compose"
48+
49+The product: `q`, compiled against the product of `p`.
50+
51+Intuitively: uses `p` as the subject of `q`.
52+
53+### `:rap`, `=<`, "tisgal", `{$rap p/twig q/twig}`, "reverse compose"
54+
55+Expands to: `:per(q p)`
56+
57+Intuitively: reverse of `:per`.
58+
59+### `:pin`, `=+`, "tislus", `{$pin p/twig q/twig}`, "work with"
60+
61+Expands to: `:per(:cons(p .) q)`
62+
63+Intuitively: uses `[p subject]` as the subject of `q`.
64+
65+### `:nip`, `=-`, "tishep", `{$nip p/twig q/twig}`, "work over"
66+
67+Expands to: `:pin(q p)`
68+
69+Intuitively: reverse of `:pin`.
70+
71+### `:var`, `=/`, "tisfas", `{$var p/taco q/twig r/twig}, "with variable"
72+
73+Expands to: `?@(p :pin(:name(p q) r) :pin(:cast(:(coat p) q) r)`
74+
75+Intuitively: uses `[p=q subject]` as the subject of `r`. If `p`
76+contains a mold, cast `q` to that mold.
77+
78+### `:rev`, `=;`, "tissem", `{$var p/taco q/twig r/twig}, "over variable"
79+
80+Expands to: `:var(p r q)`
81+
82+Intuitively: reverse of `:var`.
83+
84+### `:new`, `=|`, "tisbar", `{$new p/moss q/twig}`, "with blank"
85+
86+Expands to: `:pin(:per($ p) q)`
87+
88+Intuitively: pin the default value of `p`.
89+
90+### `:set`, `=.`, "tisdot", `{$set p/wing q/twig r/twig}`, "mutate"
91+
92+The product: `r`, compiled against a version of the subject
93+with wing `p` modified to the product of `q`.
94+
95+Intuitively: `r` with `p` set to `q`. Almost an assignment.
96+
97+### `:sip`, `=^`, "tisket", `{$sip p/taco q/wing r/twig s/twig}`, "advance"
98+
99+The product is `s`, compiled against a version of the subject
100+in which the head of `r` is bound to variable `p`, and the tail
101+of `r` is assigned into the wing `q`.
102+
103+Intuitively: `r` produces a cell; we pin the head and install the
104+tail.
105+
106+Whyuppose we have a state machine with a function that
107+produces a cell, whose head is a result and whose tail is a new
108+state. We want to use the head as a new variable, and stuff the
109+tail back into wherever we stored the old state. This may also
110+remind you of Haskell's State monad.
111+
112+## Irregular forms
113+
114+### Infix colon, p:q
115+
116+Not to be confused with the wing `p.q`. Translation:
117+```
118+p:q:r :rap(p :rap(q r))
119+```
120+
121+## Structures
122+
123+Using a mold syntax we haven't learned yet:
124+
125+```
126+|%
127+++ taco
128+ ?@(term {term moss})
129+::
130+++ twig
131+ {$per p/twig q/twig}
132+ {$rap p/twig q/twig}
133+
134+ {$pin p/twig q/twig}
135+ {$nip p/twig q/twig}
136+
137+ {$new p/moss q/twig}
138+ {$var p/taco q/twig r/twig}
139+ {$rev p/taco q/twig r/twig}
140+ {$set p/wing q/twig r/twig}
141+ {$sip p/taco q/wing r/twig s/twig}
142+--
143+```
docs/programming/hoon/twig/limb.md+1−2
@@ -1,6 +1,5 @@
11---
2−sort: 2
3−next: true
2+sort: 3
43---
54
65# Limbs and wings
docs/programming/hoon/twig/mold.mdnew file+136
@@ -0,0 +1,136 @@
1+---
2+sort: 8
3+---
4+
5+# Molds (`$` runes).
6+
7+A *mold* is a `gate` (function) that helps us build simple and
8+rigorous data structures. (In fact, since "mold" sounds nasty,
9+molds are often called "structures.")
10+
11+## Overview
12+
13+While Hoon can't check this property statically, a proper mold
14+is a *normalizer*: an idempotent function across all nouns. If
15+the sample of a gate has span `%noun`, and its body obeys the
16+constraint that for any x, `=((mold x) (mold (mold x)))`, it's a
17+rectifier and can be used as a mold.
18+
19+Twigs in the `$` family are macros designed for making molds.
20+But any Hoon twig may produce a mold. (This is why `moss` is a
21+synonym for `twig`).
22+
23+Many macros *bunt* a mold, producing `:per(mold $)`. This value,
24+simply the result of executing the gate on the default sample,
25+is a constant by definition and normally can be compiled as such.
26+The range of a mold (the span of its bunt) is called its *icon*.
27+
28+Molds have two uses: defining simple and rigorous structures, and
29+validating untrusted input data. Validation, though very
30+important, is a rare use case. Except for direct raw input,
31+it's generally a faux pas to rectify nouns at runtime -- or even
32+in userspace.
33+
34+As a structure definition, a mold has three common uses. One,
35+its bunt is a default value (such as the sample in a gate.) Two,
36+the product of some computation is cast to its icon, both
37+checking the type and regularizing it. Three, it's used as a
38+building block in other molds.
39+
40+## Regular forms
41+
42+The rune prefix is `$`. Suffixes:
43+
44+### `:bank`, `$:`, "buccol", `{$bank p/(list moss)}`
45+
46+Syntax: *running*.
47+
48+The product: a rectifier gate producing the tuple `p`.
49+
50+Where `a`, `b` and `c` produce molds, `:bank(a b c)` produces a
51+mold whose icon is the span `[$.a $.b $.c]`.
52+
53+### `:coat`, `$=`, "buctis", `{$coat p/@tas q/moss}`
54+
55+Syntax: *2-fixed*.
56+
57+The product: a rectifier gate producing mold `q` under label `p`.
58+
59+Where `q` produces a mold, `:coat(p q)` produces a mold whose
60+icon matches the span of `:name(p $.q)`.
61+
62+### `:pick`, `$?`, "bucwut", `{$pick p/(list moss)}`
63+
64+Syntax: *running*.
65+
66+The product: a rectifier gate producing the union of the molds in
67+`p`.
68+
69+Where `a`, `b`, and `c` produce molds, `:pick(a b c)` produces a
70+mold whose icon matches the span of `?:(& $.a ?:(& $.b $.c))`.
71+
72+The default mold is the first item in `p`. To avoid an infinite
73+loop, it has to be a termination case (such as a constant).
74+
75+### `:book`, `$%`, "buccen", `{$book p/(list moss)}`
76+
77+Syntax: *running*.
78+
79+The product: a rectifier gate producing the tagged union of the
80+molds in `p`, all of which must be of the form `:bank(stem
81+bulb)`, where `stem` is an atomic mold.
82+
83+`$book` has the same icon as `$pick`, but rectifies better.
84+
85+The default mold is the first item in `p`. To avoid an infinite
86+loop, it has to be a termination case (such as a constant).
87+
88+### `:shoe`, `$_`, "buccab", "{$shoe p/twig}"
89+
90+Syntax: *1-fixed*.
91+
92+Expands to: `:gate(* p)`.
93+
94+A `$shoe` is not useful for rectification; it ignores its input.
95+It is only useful for defaults and typechecks. Sometimes we have
96+no choice but to describe by example.
97+
98+### `:lamb`, `$-`, `"buchep"`, `{$lamb p/moss q/moss}`
99+
100+Syntax: *1-fixed*.
101+
102+Expands to: `:shoe(:gate(p $.q))`.
103+
104+`$lamb` is a lambda. We shoe a trivial function from `p` to `q`.
105+Like any `$shoe`, a `$lamb` is not useful for rectification (eg,
106+you can't use it to typecheck cores sent over the network).
107+
108+## Irregular forms
109+
110+### Primitives
111+
112+`*` means any noun; `@` with an aura means an atom, such as `@ud`
113+for unsigned decimal, or just `@` for a generic noun; `?` for
114+boolean; `^` for a cell (of `*`).
115+
116+### Constants
117+
118+For a mold producing a cold atom, replace the `%` of the constant
119+syntax with `$`. `%42` is the constant number `42`; `$42` is a
120+function that, passed 42 or any other argument, produces `%42`.
121+
122+Similarly, `%foo` is the number `7.303.014` or `0x6f.6f66`;
123+`$foo` is a function that produces `%foo`.
124+
125+`$~` produces `~`.
126+
127+### Miscellaneous
128+
129+Translation:
130+
131+```
132+{a b c} :bank(a b c)
133+a/b :coat(a b)
134+?(a b c) :pick(a b c)
135+_a :shoe(a)
136+```
docs/programming/hoon/twig/nock.mdnew file+36
@@ -0,0 +1,36 @@
1+---
2+sort: 11
3+---
4+
5+# Intrinsics (`.` runes)
6+
7+Anything Nock can do, Hoon can do.
8+
9+## Regular forms
10+
11+### `:bump`, `.+`, "dotlus", `{$bump p/twig}`
12+
13+Syntax: *1-fixed*
14+
15+The product: the product of `p`, which must be an atom, plus 1.
16+
17+### `:same`, `.=`, "dottis", `{$same p/twig q/twig}`
18+
19+Syntax: *2-fixed*.
20+
21+The product: yes iff `p` and `q` produce the same value. The span
22+of `p` must nest within the span of `q`, or vice versa.
23+
24+### `:nock`, `.*`, "dottar", `{$nock p/twig q/twig}`
25+
26+The product: Nock of the formula produced by `q`, with the
27+subject produced by `p`. Typeless.
28+
29+### `:wish`, `.^`, "dotket", `{$wish p/moss q/twig}`
30+
31+The product: the noun `q` dereferenced in the Urbit global
32+namespace. The product must nest within the icon of `p`.
33+
34+Only available in user-level code. Not blocking except in
35+dojo-level code (blocks for a generator, fails if it would block
36+for an app).
docs/programming/hoon/twig/test.mdnew file+143
@@ -0,0 +1,143 @@
1+---
2+sort: 9
3+---
4+
5+# Tests (`?` runes)
6+
7+Hoon has the usual branches and logical tests. For pattern
8+matching, it also has a `$fits` twig that tests whether a value
9+matches the icon of a mold. And it has branch inference,
10+learning from `$fits` tests in the condition of `:if` twigs.
11+
12+## Overview
13+
14+All `?` runes expand to `$if` (`?:`) and/or `$fits` (`?=`).
15+
16+If the condition of an `$if` is a `$fits`, *and* the `$fits` is
17+testing a leg of the subject, the compile specializes the subject
18+span for the branches of the `$if`. Branch inference also works
19+for twigs which expand to `$if`.
20+
21+The test does not have to be a single `$fits`; the compiler can
22+analyze arbitrary boolean logic (`$and`, `$or`, `$not`) with full
23+short-circuiting. Equality tests (`=`) are *not* analyzed.
24+
25+If the compiler detects that the branch is degenerate (only one
26+side is taken), it fails with an error.
27+
28+## Regular forms
29+
30+The rune prefix is `?`. Suffixes: `=` for `:fits`, `:` for
31+`:if`, `.` for `:lest`, `-` for `:case`, `+` for `:deft`, `|` for
32+`:or`, `&` for `:and`, `!` for `:not`, `>` for `$sure`, `<` for
33+`$deny`, `^` for `:ifcl`, `@` for `:ifat`, `~` for `:ifno`.
34+
35+### `:fits`, `?=`, "wuttis", `{$fits p/moss q/twig}`
36+
37+Syntax: *2-fixed*.
38+
39+The product: `&` if the product of `q` is in the icon of `p`,
40+`|` otherwise.
41+
42+The icon of `p` must be finite / nonrecursive. In general,
43+always match one layer of a data structure at a time.
44+
45+### `:if`, `?:`, "wutcol", `{$if p/twig q/twig r/twig}`
46+
47+Syntax: *3-fixed*.
48+
49+The product: `q` if `p` has the value `&` (0), `r` for `|` (1).
50+`p` must be statically boolean.
51+
52+### `:lest`, `?.`, "wutdot", `{$lest p/twig q/twig r/twig}`
53+
54+Syntax: *3-fixed*.
55+
56+Expands to: `:if(p r q)`.
57+
58+### `:case`, `?-`, "wuthep", `{$case p/twig q/(list (pair moss twig))}`
59+
60+Syntax: *1-fixed*, then *jogging*.
61+
62+Expands by:
63+
64+```
65+|-(?~(q [%lost p] [%if [%fits p.i.q p] q.i.q $(q t.q)]))
66+```
67+
68+A pattern-matching switch. Fails to compile if the pattern is
69+incomplete or irrelevant.
70+
71+### `:deft`, `?+`, "wutlus", `{$case p/twig q/twig r/(list (pair moss twig))}`
72+
73+Syntax: *1-fixed*, then *jogging*.
74+
75+Expands by: `[%case p (weld r [[%base %noun] q])]`
76+
77+A pattern-matching switch, with default.
78+
79+### `:or`, `?|`, "wutbar", `{$or p/(list twig)}`
80+
81+Syntax: *running*.
82+
83+Expands by: `|-(?~(p [%rock %f |] [%if i.p [%rock %f &]] $(p t.p)))`
84+
85+Logical or (`&` (`0`) is yes, `|` (`1`) is no).
86+
87+### `:and`, `?&`, "wutpam", `{$and p/(list twig)}`
88+
89+Syntax: *running*.
90+
91+Expands by: `|-(?~(p [%rock %f &] [%if i.p $(p t.p) [%rock %f |]]))`
92+
93+Logical and (`&` (`0`) is yes, `|` (`1`) is no).
94+
95+### `:not`, `?!`, "wutzap", `{$not p/twig}`
96+
97+Syntax: *1-fixed*.
98+
99+Expands to: `:if(p %| %&)`.
100+
101+Logical not (`&` (`0`) is yes, `|` (`1`) is no).
102+
103+### `:sure`, `?>`, "wutgar", `{$sure p/twig q/twig}`
104+
105+Expands to: `:if(p q !!)`.
106+
107+An assertion.
108+
109+### `:deny`, `?<`, "wutgal", `{$deny p/twig q/twig}`
110+
111+Expands to: `:if(p !! q)`.
112+
113+A negative assertion.
114+
115+### `:ifno`, `?~`, "wutsig", `{$ifno p/twig q/twig r/twig}`
116+
117+Expands to: `:if(:fits($~ p) q r)`.
118+
119+Branches on whether `p` is null.
120+
121+### `:ifat`, `?@`, "wutpat", `{$ifat p/twig q/twig r/twig}`
122+
123+Expands to: `:if(:fits(@ p) q r)`.
124+
125+Branches on whether `p` is atomic.
126+
127+### `:ifcl`, `?^`, "wutket", `{$ifat p/twig q/twig r/twig}`
128+
129+Expands to: `:if(:fits(^ p) q r)`.
130+
131+Branches on whether `p` is cellular.
132+
133+## Irregular forms
134+
135+### Light logic
136+
137+Translations:
138+
139+```
140+&(a b c) ?&(a b c)
141+|(a b c) ?|(a b c)
142+!a ?!(a)
143+```