shrub/pkg/arvo/sys/vane/khan.hoon

221 lines
7.0 KiB
Plaintext
Raw Normal View History

2022-01-21 21:48:05 +03:00
:: %khan, thread runner
2022-02-08 19:42:22 +03:00
::
:: this vane presents a command/response interface for running
:: threads. two modes are supported: %fard for intra-arvo
:: requests (i.e. within the same kernel space) and %fyrd for
:: external requests (e.g. from the unix control plane.)
::
:: both modes take a thread start request consisting of a
:: namespace, thread name, and input data; they respond over the
:: same duct with either success or failure. %fard takes its
2022-03-02 22:23:06 +03:00
:: input arguments as a cage and produces %arow, which contains
:: a cage on success (or tang on failure). %fyrd takes an output
2022-03-03 03:02:20 +03:00
:: mark and input page; it produces %avow, which contains a page
:: on success.
2022-02-08 19:42:22 +03:00
::
2022-03-02 22:23:06 +03:00
:: threads currently expect input and produce output as vase,
:: not cage. %fard/%arow use cage instead since this is the
:: eventual desired thread API; however, the input mark is
:: currently ignored, and the output mark is always %noun. (for
:: forward compatibility, it is safe to specify %noun as the
:: input mark.)
::
:: %fyrd does mark conversion on both ends, and additionally
:: lifts its input into a $unit. this second step is done
:: because threads conventionally take their input as a unit,
:: with ~ for the case of "no arguments".
2022-02-08 19:42:22 +03:00
::
:: n.b. the current convention for threads is to use !< to
2022-03-02 22:23:06 +03:00
:: unpack their input vase. !< imposes the requirement that the
:: input type nests within the specified type. this limits %fyrd
:: to threads with inputs for which a named mark exists; it is
:: impossible to use %noun in general since it does not nest.
:: threads written against the current vase-based API could use
:: ;; instead of !< to unpack their input, thus allowing the
:: use of %fyrd with %noun. however the eventual solution is
:: probably to make threads consume and produce cages, and do
:: mark conversion where appropriate.
2022-01-21 21:48:05 +03:00
!:
!? 164
::
2022-02-12 09:13:31 +03:00
=, khan
2022-01-21 21:48:05 +03:00
|= our=ship
=> |% :: %khan types
2022-02-12 09:13:31 +03:00
+$ move [p=duct q=(wite note gift)] ::
+$ note :: out request $->
$~ [%g %deal *sock *term *deal:gall] ::
$% $: %g :: to %gall
2022-01-22 04:46:59 +03:00
$>(%deal task:gall) :: full transmission
== ::
$: %k :: to self
2022-02-12 09:13:31 +03:00
$>(%fard task) :: internal thread
2022-01-22 04:46:59 +03:00
== == ::
+$ sign :: in response $<-
$% $: %gall :: from %gall
$>(%unto gift:gall) :: update
== ::
$: %khan :: from self
$>(?(%arow %avow) gift) :: thread result
== == ::
+$ khan-state ::
$: %0 :: state v0
hey=duct :: unix duct
tic=@ud :: tid counter
== ::
-- ::
2022-01-22 04:46:59 +03:00
=>
|%
++ get-beak
2022-02-12 09:13:31 +03:00
|= [=bear now=@da]
?@(bear [our bear %da now] bear)
2022-03-03 00:09:01 +03:00
::
2022-01-27 04:41:01 +03:00
++ get-dais
|= [=beak =mark rof=roof]
^- dais:clay
?~ ret=(rof ~ %cb beak /[mark])
~|(mark-unknown+mark !!)
2022-01-27 04:41:01 +03:00
?~ u.ret
~|(mark-invalid+mark !!)
2022-01-27 04:41:01 +03:00
?> =(%dais p.u.u.ret)
!<(dais:clay q.u.u.ret)
2022-03-03 00:09:01 +03:00
::
++ get-tube
|= [=beak =mark =out=mark rof=roof]
^- tube:clay
?~ ret=(rof ~ %cc beak /[mark]/[out-mark])
~|(tube-unknown+[mark out-mark] !!)
?~ u.ret
~|(tube-invalid+[mark out-mark] !!)
?> =(%tube p.u.u.ret)
!<(tube:clay q.u.u.ret)
2022-03-03 00:09:01 +03:00
::
++ make-wire
|= [=beak =mark]
^- wire
[%fyrd (en-beam beak mark ~)]
2022-03-03 00:09:01 +03:00
::
++ read-wire
|= =wire
^- (pair beak mark)
~| khan-read-wire+wire
?> ?=([%fyrd ^] wire)
=/ =beam (need (de-beam t.wire))
?>(?=([@ ~] s.beam) beam(s i.s.beam))
2022-03-03 00:09:01 +03:00
::
khan: support inline threads This allows you to pass a thread directly into khan, instead of passing a filename. This has several implications: - The friction for using threads from an app is significantly lower. Consider: =/ shed =/ m (strand ,vase) ;< ~ bind:m (poke:strandio [our %hood] %helm-hi !>('hi')) ;< ~ bind:m (poke:strandio [our %hood] %helm-hi !>('there')) (pure:m !>('product')) [%pass /wire %arvo %k %lard %base shed] - These threads close over their subject, so you don't need to parse arguments out from a vase -- you can just refer to them. The produced value must still be a vase. ++ hi-ship |= [=ship msg1=@t msg2=@t] =/ shed =/ m (strand ,vase) ;< ~ bind:m (poke:strandio [ship %hood] %helm-hi !>(msg1)) ;< ~ bind:m (poke:strandio [ship %hood] %helm-hi !>(msg2)) (pure:m !>('product')) [%pass /wire %arvo %k %lard %base shed] - Inline threads can be added to the dojo, though this PR does not add any sugar for this. =strandio -build-file %/lib/strandio/hoon =sh |= message=@t =/ m (strand:rand ,vase) ;< ~ bind:m (poke:strandio [our %hood] %helm-hi !>('hi')) ;< ~ bind:m (poke:strandio [our %hood] %helm-hi !>(message)) (pure:m !>('product')) |pass [%k %lard %base (sh 'the message')] Implementation notes: - Review the commits separately: the first is small and implements the real feature. The second moves the strand types into lull so khan can refer to them. - In lull, I wanted to put +rand inside +khan, but this fails to that issue that puts the compiler in a loop. +rand depends on +gall, which depends on +sign-arvo, which depends on +khan. If +rand is in +khan, this spins the compiler. The usual solution is to either move everything into the same battery (very ugly here) or break the recursion (which we do here).
2022-08-30 07:35:14 +03:00
++ poke-spider
2022-10-27 08:09:53 +03:00
|= [hen=duct =cage]
^- move
[hen %pass //g %g %deal [our our] %spider %poke cage]
2022-03-03 00:09:01 +03:00
::
2022-01-22 04:46:59 +03:00
++ watch-spider
2022-10-27 08:09:53 +03:00
|= [hen=duct =path]
^- move
[hen %pass //g %g %deal [our our] %spider %watch path]
2022-01-22 04:46:59 +03:00
--
2022-01-21 21:48:05 +03:00
=| khan-state
=* state -
|= [now=@da eny=@uvJ rof=roof]
=* khan-gate .
^?
|%
2022-02-12 09:13:31 +03:00
:: +call: handle a +task request
2022-01-21 21:48:05 +03:00
::
++ call
|= $: hen=duct
dud=(unit goof)
2022-02-12 09:13:31 +03:00
wrapped-task=(hobo task)
2022-01-21 21:48:05 +03:00
==
^- [(list move) _khan-gate]
::
2022-02-12 09:13:31 +03:00
=/ =task ((harden task) wrapped-task)
2022-02-13 18:33:03 +03:00
?^ dud
~|(%khan-call-dud (mean tang.u.dud))
2022-01-26 08:28:45 +03:00
?+ -.task [~ khan-gate]
2022-01-22 01:09:01 +03:00
%born
2022-03-03 05:15:21 +03:00
[~ khan-gate(hey hen, tic 0)]
::
2022-10-27 08:09:53 +03:00
%fard (bard hen 'khan-fyrd--' bear.p.task %| [name args]:p.task)
%lard (bard hen 'khan-lard--' bear.task %& shed.task)
%fyrd
2022-03-26 16:54:13 +03:00
=* fyd p.task
=/ =beak (get-beak bear.fyd now)
=/ =wire (make-wire beak p.args.fyd)
=/ =dais:clay (get-dais beak p.q.args.fyd rof)
=/ =vase
(slap (vale.dais q.q.args.fyd) !,(*hoon [~ u=.]))
=- [[hen %pass wire -]~ khan-gate]
[%k %fard bear.fyd name.fyd p.q.args.fyd vase]
2022-01-22 01:09:01 +03:00
==
2022-10-27 08:09:53 +03:00
::
++ bard
|= [hen=duct prefix=@ta =bear payload=(each shed [name=term args=cage])]
^- [(list move) _khan-gate]
=/ =tid:rand (cat 3 prefix (scot %uv (sham (mix tic eny))))
=/ =beak (get-beak bear now)
=/ =cage
?- -.payload
%& [%spider-inline !>([~ `tid beak p.payload])]
%| [%spider-start !>([~ `tid beak [name q.args]:p.payload])]
==
=. tic +(tic)
:_ khan-gate
:~ (watch-spider hen /thread-result/[tid])
(poke-spider hen cage)
==
::
2022-01-21 21:48:05 +03:00
:: +load: migrate an old state to a new khan version
::
++ load
2022-03-02 08:38:55 +03:00
|= old=khan-state
2022-01-21 21:48:05 +03:00
^+ khan-gate
2022-03-02 08:38:55 +03:00
khan-gate(state old)
2022-01-26 08:28:45 +03:00
:: +scry: nothing to see as yet
2022-01-21 21:48:05 +03:00
::
++ scry
^- roon
|= [lyc=gang car=term bem=beam]
^- (unit (unit cage))
~
++ stay state
2022-01-26 08:28:45 +03:00
:: +take: handle responses.
::
2022-01-21 21:48:05 +03:00
++ take
|= [tea=wire hen=duct dud=(unit goof) hin=sign]
^- [(list move) _khan-gate]
?^ dud
~|(%khan-take-dud (mean tang.u.dud))
:_ khan-gate
?- -.hin
%gall
?+ -.p.hin ~
?(%poke-ack %watch-ack)
?~ p.p.hin ~
%- (slog 'khan-ack' u.p.p.hin)
[hen %give %arow %| -.p.hin u.p.p.hin]~
::
%fact
=* cag cage.p.hin
?+ p.cag ~&(bad-fact+p.cag !!)
%thread-fail
=/ =tang !<(tang q.cag)
2022-10-18 07:16:54 +03:00
:: %- (slog 'khan-fact' tang)
[hen %give %arow %| p.cag tang]~
::
%thread-done
[hen %give %arow %& %noun q.cag]~
==
==
::
%khan
2022-03-26 16:54:13 +03:00
?. ?=(%arow +<.hin) ~
?. ?=([%fyrd *] tea) ~
=* row p.hin
?. ?=(%& -.row)
[hen %give %avow row]~
2022-03-26 16:54:13 +03:00
=/ [=beak =mark] (read-wire tea)
=/ =tube:clay (get-tube beak p.p.row mark rof)
=/ =vase (tube q.p.row)
[hen %give %avow %& mark q.vase]~
==
2022-01-21 21:48:05 +03:00
--