diff --git a/include/vere/vere.h b/include/vere/vere.h index c1f6935e95..9d81e4e830 100644 --- a/include/vere/vere.h +++ b/include/vere/vere.h @@ -1197,3 +1197,14 @@ */ void u3_cttp_io_exit(void); + + + /* u3_dawn_come(): mine a comet under star (unit) + */ + u3_noun + u3_dawn_come(u3_noun star); + + /* u3_dawn_vent(): validatated boot event + */ + u3_noun + u3_dawn_vent(u3_noun seed); diff --git a/meson.build b/meson.build index 405bd0d506..a4925d434f 100644 --- a/meson.build +++ b/meson.build @@ -213,6 +213,7 @@ vere_sans_main = [ 'vere/ames.c', 'vere/behn.c', 'vere/cttp.c', + 'vere/dawn.c', 'vere/http.c', 'vere/loop.c', 'vere/raft.c', diff --git a/vere/dawn.c b/vere/dawn.c new file mode 100644 index 0000000000..45252861b9 --- /dev/null +++ b/vere/dawn.c @@ -0,0 +1,444 @@ +/* vere/dawn.c +** +** ethereum-integrated pre-boot validation +*/ +#include +#include +#include +#include "all.h" +#include "vere/vere.h" + +/* _dawn_curl_alloc(): allocate a response buffer for curl +*/ +static size_t +_dawn_curl_alloc(void* dat_v, size_t uni_t, size_t mem_t, uv_buf_t* buf_u) +{ + size_t siz_t = uni_t * mem_t; + buf_u->base = realloc(buf_u->base, 1 + siz_t + buf_u->len); + + if ( 0 == buf_u->base ) { + fprintf(stderr, "out of memory\n"); + u3_lo_bail(); + } + + memcpy(buf_u->base + buf_u->len, dat_v, siz_t); + buf_u->len += siz_t; + buf_u->base[buf_u->len] = 0; + + return siz_t; +} + +/* _dawn_post_json(): POST JSON to url_c +*/ +static uv_buf_t +_dawn_post_json(c3_c* url_c, uv_buf_t lod_u) +{ + CURL *curl; + CURLcode result; + long cod_l; + struct curl_slist* hed_u = 0; + + uv_buf_t buf_u = uv_buf_init(c3_malloc(1), 0); + + if ( !(curl = curl_easy_init()) ) { + fprintf(stderr, "failed to initialize libcurl\n"); + u3_lo_bail(); + } + + hed_u = curl_slist_append(hed_u, "Accept: application/json"); + hed_u = curl_slist_append(hed_u, "Content-Type: application/json"); + hed_u = curl_slist_append(hed_u, "charsets: utf-8"); + + // XX require TLS, pin default cert? + + curl_easy_setopt(curl, CURLOPT_URL, url_c); + curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, _dawn_curl_alloc); + curl_easy_setopt(curl, CURLOPT_WRITEDATA, (void*)&buf_u); + curl_easy_setopt(curl, CURLOPT_HTTPHEADER, hed_u); + + // note: must be terminated! + curl_easy_setopt(curl, CURLOPT_POSTFIELDS, lod_u.base); + + result = curl_easy_perform(curl); + curl_easy_getinfo(curl, CURLINFO_RESPONSE_CODE, &cod_l); + + // XX retry? + if ( CURLE_OK != result ) { + fprintf(stderr, "failed to fetch %s: %s\n", + url_c, curl_easy_strerror(result)); + u3_lo_bail(); + } + if ( 300 <= cod_l ) { + fprintf(stderr, "error fetching %s: HTTP %ld\n", url_c, cod_l); + u3_lo_bail(); + } + + curl_easy_cleanup(curl); + curl_slist_free_all(hed_u); + + return buf_u; +} + +/* _dawn_oct_to_buf(): +octs to uv_buf_t +*/ +static uv_buf_t +_dawn_oct_to_buf(u3_noun oct) +{ + if ( c3n == u3a_is_cat(u3h(oct)) ) { + u3_lo_bail(); + } + + c3_w len_w = u3h(oct); + c3_y* buf_y = c3_malloc(1 + len_w); + buf_y[len_w] = 0; + + u3r_bytes(0, len_w, buf_y, u3t(oct)); + + u3z(oct); + return uv_buf_init((void*)buf_y, len_w); +} + +/* _dawn_buf_to_oct(): uv_buf_t to +octs +*/ +static u3_noun +_dawn_buf_to_oct(uv_buf_t buf_u) +{ + u3_noun len = u3i_words(1, (c3_w*)&buf_u.len); + + if ( c3n == u3a_is_cat(len) ) { + u3_lo_bail(); + } + + return u3nc(len, u3i_bytes(buf_u.len, (const c3_y*)buf_u.base)); +} + +/* _dawn_eth_rpc(): ethereum JSON RPC with request/response as +octs +*/ +static u3_noun +_dawn_eth_rpc(c3_c* url_c, u3_noun oct) +{ + return _dawn_buf_to_oct(_dawn_post_json(url_c, _dawn_oct_to_buf(oct))); +} + +/* _dawn_fail(): pre-boot validation failed +*/ +static void +_dawn_fail(u3_noun who, u3_noun rac, u3_noun sas) +{ + u3_noun how = u3dc("scot", 'p', u3k(who)); + c3_c* how_c = u3r_string(u3k(how)); + + c3_c* rac_c; + + switch (rac) { + default: c3_assert(0); + case c3__czar: { + rac_c = "galaxy"; + break; + } + case c3__king: { + rac_c = "star"; + break; + } + case c3__duke: { + rac_c = "planet"; + break; + } + case c3__earl: { + rac_c = "moon"; + break; + } + case c3__pawn: { + rac_c = "comet"; + break; + } + } + + fprintf(stderr, "dawn: invalid keys for %s '%s'\r\n", rac_c, how_c); + + // XX deconstruct sas, print helpful error messages + u3m_p("pre-boot error", u3t(sas)); + + u3z(how); + free(how_c); + u3_lo_bail(); +} + +/* _dawn_purl(): ethereum gateway url as (unit purl) +*/ +static u3_noun +_dawn_purl(u3_noun rac) +{ + u3_noun url; + + if ( 0 == u3_Host.ops_u.eth_c ) { + if ( c3__czar == rac ) { + fprintf(stderr, "boot: galaxy requires ethereum gateway via -e\r\n"); + u3_lo_bail(); + } + + url = u3_nul; + } + else { + // XX call de-purl directly + // + u3_noun par = u3v_wish("auru:de-purl:html"); + u3_noun lur = u3i_string(u3_Host.ops_u.eth_c); + u3_noun rul = u3dc("rush", u3k(lur), u3k(par)); + + if ( u3_nul == rul ) { + if ( c3__czar == rac ) { + fprintf(stderr, "boot: galaxy requires ethereum gateway via -e\r\n"); + u3_lo_bail(); + } + + url = u3_nul; + } + else { + // XX revise for de-purl + // auru:de-purl:html parses to (pair user purl) + // we need (unit purl) + // + url = u3nc(u3_nul, u3k(u3t(u3t(rul)))); + } + + u3z(par); u3z(lur); u3z(rul); + } + + return url; +} + +/* _dawn_turf(): override contract domains with -H +*/ +static u3_noun +_dawn_turf(c3_c* dns_c) +{ + u3_noun tuf; + + u3_noun par = u3v_wish("thos:de-purl:html"); + u3_noun dns = u3i_string(dns_c); + u3_noun rul = u3dc("rush", u3k(dns), u3k(par)); + + if ( (u3_nul == rul) || (c3n == u3h(u3t(rul))) ) { + fprintf(stderr, "boot: invalid domain specified with -H %s\r\n", dns_c); + // bails, won't return + u3_lo_bail(); + return u3_none; + } + else { + fprintf(stderr, "boot: overriding network domains with %s\r\n", dns_c); + u3_noun dom = u3t(u3t(rul)); + tuf = u3nc(u3k(dom), u3_nul); + } + + u3z(par); u3z(dns); u3z(rul); + + return tuf; +} + +/* u3_dawn_vent(): validatated boot event +*/ +u3_noun +u3_dawn_vent(u3_noun seed) +{ + u3_noun url, bok, pon, zar, tuf, sap; + + u3_noun ship = u3h(seed); + u3_noun rank = u3do("clan:title", u3k(ship)); + + // load snapshot if exists + // + if ( 0 != u3_Host.ops_u.ets_c ) { + fprintf(stderr, "boot: loading ethereum snapshot\r\n"); + u3_noun raw_snap = u3ke_cue(u3m_file(u3_Host.ops_u.ets_c)); + sap = u3nc(u3_nul, raw_snap); + } + else { + sap = u3_nul; + } + + url = _dawn_purl(rank); + + // XX require https? + // + c3_c* url_c = ( 0 != u3_Host.ops_u.eth_c ) ? + u3_Host.ops_u.eth_c : + "https://ropsten.infura.io/v3/196a7f37c7d54211b4a07904ec73ad87"; + + // pin block number + // + if ( c3y == u3_Host.ops_u.etn ) { + fprintf(stderr, "boot: extracting block from snapshot\r\n"); + bok = u3do("bloq:snap:dawn", u3k(u3t(sap))); + } + else { + fprintf(stderr, "boot: retrieving latest block\r\n"); + + u3_noun oct = u3v_wish("bloq:give:dawn"); + u3_noun kob = _dawn_eth_rpc(url_c, u3k(oct)); + bok = u3do("bloq:take:dawn", u3k(kob)); + + u3z(oct); u3z(kob); + } + + { + // +hull:constitution:ethe: on-chain state + // + u3_noun hul; + + if ( c3y == u3_Host.ops_u.etn ) { + hul = u3dc("hull:snap:dawn", u3k(ship), u3k(u3t(sap))); + } + else if ( c3__pawn == rank ) { + // irrelevant, just bunt +hull + // + hul = u3v_wish("*hull:constitution:ethe"); + } + else { + u3_noun oct; + + if ( c3__earl == rank ) { + u3_noun seg = u3do("^sein:title", u3k(ship)); + u3_noun ges = u3dc("scot", 'p', u3k(seg)); + c3_c* seg_c = u3r_string(ges); + + fprintf(stderr, "boot: retrieving %s's public keys (for %s)\r\n", + seg_c, u3_Host.ops_u.who_c); + oct = u3dc("hull:give:dawn", u3k(bok), u3k(seg)); + + free(seg_c); + u3z(seg); u3z(ges); + } + else { + fprintf(stderr, "boot: retrieving %s's public keys\r\n", + u3_Host.ops_u.who_c); + oct = u3dc("hull:give:dawn", u3k(bok), u3k(ship)); + } + + u3_noun luh = _dawn_eth_rpc(url_c, u3k(oct)); + hul = u3dc("hull:take:dawn", u3k(ship), u3k(luh)); + + u3z(oct); u3z(luh); + } + + // +live:dawn: network state + // XX actually make request + // + u3_noun liv = u3_nul; + // u3_noun liv = _dawn_get_json(parent, /some/url) + + fprintf(stderr, "boot: verifying keys\r\n"); + + // (each sponsor=(unit ship) error=@tas) + // + u3_noun sas = u3dt("veri:dawn", u3k(seed), u3k(hul), u3k(liv)); + + if ( c3n == u3h(sas) ) { + // bails, won't return + _dawn_fail(ship, rank, sas); + return u3_none; + } + + // (unit ship): sponsor + // produced by +veri:dawn to avoid coupling to +hull structure + // XX reconsider + // + pon = u3k(u3t(sas)); + + u3z(hul); u3z(liv); u3z(sas); + } + + // (map ship [=life =pass]): galaxy table + // + if ( c3y == u3_Host.ops_u.etn ) { + zar = u3do("czar:snap:dawn", u3k(u3t(sap))); + } + else { + fprintf(stderr, "boot: retrieving galaxy table\r\n"); + + u3_noun oct = u3do("czar:give:dawn", u3k(bok)); + u3_noun raz = _dawn_eth_rpc(url_c, u3k(oct)); + zar = u3do("czar:take:dawn", u3k(raz)); + + u3z(oct); u3z(raz); + } + + // (list turf): ames domains + // + if ( 0 != u3_Host.ops_u.dns_c ) { + tuf = _dawn_turf(u3_Host.ops_u.dns_c); + } + else if ( c3y == u3_Host.ops_u.etn ) { + tuf = u3do("turf:snap:dawn", u3k(u3t(sap))); + } + else { + fprintf(stderr, "boot: retrieving network domains\r\n"); + + u3_noun oct = u3do("turf:give:dawn", u3k(bok)); + u3_noun fut = _dawn_eth_rpc(url_c, u3k(oct)); + tuf = u3do("turf:take:dawn", u3k(fut)); + + u3z(oct); u3z(fut); + } + + u3z(rank); + + // [%dawn seed sponsor galaxies domains block eth-url snap] + // + return u3nc(c3__dawn, u3nq(seed, pon, zar, u3nq(tuf, bok, url, sap))); +} + +/* u3_dawn_come(): mine a comet under star (unit) +*/ +u3_noun +u3_dawn_come(u3_noun star) +{ + u3_noun seed; + + if ( u3_nul == star ) { + // XX ~marzod hardcoded + // choose from list, at random, &c + // + star = 256; + } + else { + // XX parse and validate + // + u3_noun tar = u3k(u3t(star)); + u3z(star); + star = tar; + } + + { + u3_noun sar = u3dc("scot", 'p', u3k(star)); + c3_c* tar_c = u3r_string(sar); + + fprintf(stderr, "boot: mining a comet under %s\r\n", tar_c); + free(tar_c); + u3z(sar); + } + + { + c3_w eny_w[16]; + u3_noun eny; + + c3_rand(eny_w); + eny = u3i_words(16, eny_w); + + seed = u3dc("come:dawn", u3k(star), u3k(eny)); + u3z(eny); + } + + { + u3_noun who = u3dc("scot", 'p', u3k(u3h(seed))); + c3_c* who_c = u3r_string(who); + + fprintf(stderr, "boot: found comet %s\r\n", who_c); + free(who_c); + u3z(who); + } + + u3z(star); + + return seed; +} diff --git a/vere/sist.c b/vere/sist.c index 620ead285f..ec6f77fd98 100644 --- a/vere/sist.c +++ b/vere/sist.c @@ -7,7 +7,6 @@ #include #include #include -#include #include #include "all.h" @@ -21,7 +20,6 @@ #define DEVRANDOM "/dev/random" #endif - /* u3_sist_pack(): write a blob to disk, transferring. */ c3_d @@ -1136,423 +1134,6 @@ _sist_rest() } } -/* _sist_curl_alloc(): allocate a response buffer for curl -*/ -static size_t -_sist_curl_alloc(void* dat_v, size_t uni_t, size_t mem_t, uv_buf_t* buf_u) -{ - size_t siz_t = uni_t * mem_t; - buf_u->base = realloc(buf_u->base, 1 + siz_t + buf_u->len); - - if ( 0 == buf_u->base ) { - fprintf(stderr, "out of memory\n"); - u3_lo_bail(); - } - - memcpy(buf_u->base + buf_u->len, dat_v, siz_t); - buf_u->len += siz_t; - buf_u->base[buf_u->len] = 0; - - return siz_t; -} - -/* _sist_post_json(): POST JSON to url_c -*/ -static uv_buf_t -_sist_post_json(c3_c* url_c, uv_buf_t lod_u) -{ - CURL *curl; - CURLcode result; - long cod_l; - struct curl_slist* hed_u = 0; - - uv_buf_t buf_u = uv_buf_init(c3_malloc(1), 0); - - if ( !(curl = curl_easy_init()) ) { - fprintf(stderr, "failed to initialize libcurl\n"); - u3_lo_bail(); - } - - hed_u = curl_slist_append(hed_u, "Accept: application/json"); - hed_u = curl_slist_append(hed_u, "Content-Type: application/json"); - hed_u = curl_slist_append(hed_u, "charsets: utf-8"); - - // XX require TLS, pin default cert? - - curl_easy_setopt(curl, CURLOPT_URL, url_c); - curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, _sist_curl_alloc); - curl_easy_setopt(curl, CURLOPT_WRITEDATA, (void*)&buf_u); - curl_easy_setopt(curl, CURLOPT_HTTPHEADER, hed_u); - - // note: must be terminated! - curl_easy_setopt(curl, CURLOPT_POSTFIELDS, lod_u.base); - - result = curl_easy_perform(curl); - curl_easy_getinfo(curl, CURLINFO_RESPONSE_CODE, &cod_l); - - // XX retry? - if ( CURLE_OK != result ) { - fprintf(stderr, "failed to fetch %s: %s\n", - url_c, curl_easy_strerror(result)); - u3_lo_bail(); - } - if ( 300 <= cod_l ) { - fprintf(stderr, "error fetching %s: HTTP %ld\n", url_c, cod_l); - u3_lo_bail(); - } - - curl_easy_cleanup(curl); - curl_slist_free_all(hed_u); - - return buf_u; -} - -/* _sist_oct_to_buf(): +octs to uv_buf_t -*/ -static uv_buf_t -_sist_oct_to_buf(u3_noun oct) -{ - if ( c3n == u3a_is_cat(u3h(oct)) ) { - u3_lo_bail(); - } - - c3_w len_w = u3h(oct); - c3_y* buf_y = c3_malloc(1 + len_w); - buf_y[len_w] = 0; - - u3r_bytes(0, len_w, buf_y, u3t(oct)); - - u3z(oct); - return uv_buf_init((void*)buf_y, len_w); -} - -/* _sist_buf_to_oct(): uv_buf_t to +octs -*/ -static u3_noun -_sist_buf_to_oct(uv_buf_t buf_u) -{ - u3_noun len = u3i_words(1, (c3_w*)&buf_u.len); - - if ( c3n == u3a_is_cat(len) ) { - u3_lo_bail(); - } - - return u3nc(len, u3i_bytes(buf_u.len, (const c3_y*)buf_u.base)); -} - -/* _sist_eth_rpc(): ethereum JSON RPC with request/response as +octs -*/ -static u3_noun -_sist_eth_rpc(c3_c* url_c, u3_noun oct) -{ - return _sist_buf_to_oct(_sist_post_json(url_c, _sist_oct_to_buf(oct))); -} - -/* _sist_dawn_fail(): pre-boot validation failed -*/ -static void -_sist_dawn_fail(u3_noun who, u3_noun rac, u3_noun sas) -{ - u3_noun how = u3dc("scot", 'p', u3k(who)); - c3_c* how_c = u3r_string(u3k(how)); - - c3_c* rac_c; - - switch (rac) { - default: c3_assert(0); - case c3__czar: { - rac_c = "galaxy"; - break; - } - case c3__king: { - rac_c = "star"; - break; - } - case c3__duke: { - rac_c = "planet"; - break; - } - case c3__earl: { - rac_c = "moon"; - break; - } - case c3__pawn: { - rac_c = "comet"; - break; - } - } - - fprintf(stderr, "dawn: invalid keys for %s '%s'\r\n", rac_c, how_c); - - // XX deconstruct sas, print helpful error messages - u3m_p("pre-boot error", u3t(sas)); - - u3z(how); - free(how_c); - u3_lo_bail(); -} - -/* _sist_dawn_turf(): override contract domains with -H -*/ -static u3_noun -_sist_dawn_turf(c3_c* dns_c) -{ - u3_noun tuf; - - u3_noun par = u3v_wish("thos:de-purl:html"); - u3_noun dns = u3i_string(dns_c); - u3_noun rul = u3dc("rush", u3k(dns), u3k(par)); - - if ( (u3_nul == rul) || (c3n == u3h(u3t(rul))) ) { - fprintf(stderr, "boot: invalid domain specified with -H %s\r\n", dns_c); - // bails, won't return - u3_lo_bail(); - return u3_none; - } - else { - fprintf(stderr, "boot: overriding network domains with %s\r\n", dns_c); - u3_noun dom = u3t(u3t(rul)); - tuf = u3nc(u3k(dom), u3_nul); - } - - u3z(par); u3z(dns); u3z(rul); - - return tuf; -} - -/* _sist_dawn(): produce %dawn boot card - validate keys and query contract -*/ -static u3_noun -_sist_dawn(u3_noun sed) -{ - u3_noun url, bok, pon, zar, tuf, sap; - - u3_noun who = u3h(sed); - u3_noun rac = u3do("clan:title", u3k(who)); - - // load snapshot if exists - if ( 0 != u3_Host.ops_u.ets_c ) { - fprintf(stderr, "boot: loading ethereum snapshot\r\n"); - u3_noun raw_snap = u3ke_cue(u3m_file(u3_Host.ops_u.ets_c)); - sap = u3nc(u3_nul, raw_snap); - } - else { - sap = u3_nul; - } - - // ethereum gateway as (unit purl) - if ( 0 == u3_Host.ops_u.eth_c ) { - if ( c3__czar == rac ) { - fprintf(stderr, "boot: galaxy requires ethereum gateway via -e\r\n"); - // bails, won't return - u3_lo_bail(); - return u3_none; - } - - url = u3_nul; - } - else { - u3_noun par = u3v_wish("auru:de-purl:html"); - u3_noun lur = u3i_string(u3_Host.ops_u.eth_c); - u3_noun rul = u3dc("rush", u3k(lur), u3k(par)); - - if ( u3_nul == rul ) { - if ( c3__czar == rac ) { - fprintf(stderr, "boot: galaxy requires ethereum gateway via -e\r\n"); - // bails, won't return - u3_lo_bail(); - return u3_none; - } - - url = u3_nul; - } - else { - // auru:de-purl:html parses to (pair user purl) - // we need (unit purl) - // (we're using it to avoid the +hoke weirdness) - // XX revisit upon merging with release-candidate - url = u3nc(u3_nul, u3k(u3t(u3t(rul)))); - } - - u3z(par); u3z(lur); u3z(rul); - } - - // XX require https? - c3_c* url_c = ( 0 != u3_Host.ops_u.eth_c ) ? - u3_Host.ops_u.eth_c : - "https://ropsten.infura.io/v3/196a7f37c7d54211b4a07904ec73ad87"; - - { - fprintf(stderr, "boot: retrieving latest block\r\n"); - - if ( c3y == u3_Host.ops_u.etn ) { - bok = u3do("bloq:snap:dawn", u3k(u3t(sap))); - } - else { - // @ud: block number - u3_noun oct = u3v_wish("bloq:give:dawn"); - u3_noun kob = _sist_eth_rpc(url_c, u3k(oct)); - bok = u3do("bloq:take:dawn", u3k(kob)); - - u3z(oct); u3z(kob); - } - } - - { - // +hull:constitution:ethe: on-chain state - u3_noun hul; - - if ( c3y == u3_Host.ops_u.etn ) { - hul = u3dc("hull:snap:dawn", u3k(who), u3k(u3t(sap))); - } - else { - if ( c3__pawn == rac ) { - // irrelevant, just bunt +hull - hul = u3v_wish("*hull:constitution:ethe"); - } - else { - u3_noun oct; - - if ( c3__earl == rac ) { - u3_noun seg = u3do("^sein:title", u3k(who)); - u3_noun ges = u3dc("scot", 'p', u3k(seg)); - c3_c* seg_c = u3r_string(ges); - - fprintf(stderr, "boot: retrieving %s's public keys (for %s)\r\n", - seg_c, u3_Host.ops_u.who_c); - oct = u3dc("hull:give:dawn", u3k(bok), u3k(seg)); - - free(seg_c); - u3z(seg); u3z(ges); - } - else { - fprintf(stderr, "boot: retrieving %s's public keys\r\n", - u3_Host.ops_u.who_c); - oct = u3dc("hull:give:dawn", u3k(bok), u3k(who)); - } - - u3_noun luh = _sist_eth_rpc(url_c, u3k(oct)); - hul = u3dc("hull:take:dawn", u3k(who), u3k(luh)); - - u3z(oct); u3z(luh); - } - } - - // +live:dawn: network state - // XX actually make request - // u3_noun liv = _sist_get_json(parent, /some/url) - u3_noun liv = u3_nul; - - fprintf(stderr, "boot: verifying keys\r\n"); - - // (each sponsor=(unit ship) error=@tas) - u3_noun sas = u3dt("veri:dawn", u3k(sed), u3k(hul), u3k(liv)); - - if ( c3n == u3h(sas) ) { - // bails, won't return - _sist_dawn_fail(who, rac, sas); - return u3_none; - } - - // (unit ship): sponsor - // produced by +veri:dawn to avoid coupling to +hull structure - pon = u3k(u3t(sas)); - - u3z(hul); u3z(liv); u3z(sas); - } - - { - if ( c3y == u3_Host.ops_u.etn ) { - zar = u3do("czar:snap:dawn", u3k(u3t(sap))); - - if ( 0 != u3_Host.ops_u.dns_c ) { - tuf = _sist_dawn_turf(u3_Host.ops_u.dns_c); - } - else { - tuf = u3do("turf:snap:dawn", u3k(u3t(sap))); - } - } - else { - { - fprintf(stderr, "boot: retrieving galaxy table\r\n"); - - // (map ship [=life =pass]): galaxy table - u3_noun oct = u3do("czar:give:dawn", u3k(bok)); - u3_noun raz = _sist_eth_rpc(url_c, u3k(oct)); - zar = u3do("czar:take:dawn", u3k(raz)); - - u3z(oct); u3z(raz); - } - - if ( 0 != u3_Host.ops_u.dns_c ) { - tuf = _sist_dawn_turf(u3_Host.ops_u.dns_c); - } - else { - fprintf(stderr, "boot: retrieving network domains\r\n"); - - // (list turf): ames domains - u3_noun oct = u3do("turf:give:dawn", u3k(bok)); - u3_noun fut = _sist_eth_rpc(url_c, u3k(oct)); - tuf = u3do("turf:take:dawn", u3k(fut)); - - u3z(oct); u3z(fut); - } - } - } - - u3z(rac); - - // [%dawn seed sponsor galaxies domains block eth-url snap] - return u3nc(c3__dawn, u3nq(sed, pon, zar, u3nq(tuf, bok, url, sap))); -} - -/* _sist_zen(): get OS entropy. -*/ -static u3_noun -_sist_zen(void) -{ - c3_w rad_w[16]; - - c3_rand(rad_w); - return u3i_words(16, rad_w); -} - -/* _sist_come(): mine a comet. -*/ -static u3_noun -_sist_come(void) -{ - u3_noun tar, eny, sed; - - // XX choose from list, at random, &c - tar = u3dc("slav", 'p', u3i_string("~marzod")); - eny = _sist_zen(); - - { - u3_noun sar = u3dc("scot", 'p', u3k(tar)); - c3_c* tar_c = u3r_string(sar); - - fprintf(stderr, "boot: mining a comet under %s\r\n", tar_c); - free(tar_c); - u3z(sar); - } - - sed = u3dc("come:dawn", u3k(tar), u3k(eny)); - - { - u3_noun who = u3dc("scot", 'p', u3k(u3h(sed))); - c3_c* who_c = u3r_string(who); - - fprintf(stderr, "boot: found comet %s\r\n", who_c); - free(who_c); - u3z(who); - } - - u3z(tar); u3z(eny); - - return sed; -} - /* sist_key(): parse a private key-file. */ static u3_noun @@ -1669,11 +1250,11 @@ u3_sist_boot(void) sed = sist_key(des); } else { - sed = _sist_come(); + sed = u3_dawn_come(u3_nul); } u3A->fak = c3n; - pig = _sist_dawn(u3k(sed)); + pig = u3_dawn_vent(u3k(sed)); who = u3k(u3h(u3h(u3t(pig)))); u3z(sed);