/* _http_heds_to_list(): C headers to list. */ static u3_noun _http_heds_to_list(u3_hhed* hed_u) { if ( 0 == hed_u ) { return u3_nul; } else { return u3nc(u3nc(u3i_string(hed_u->nam_c), hed_u->val_c ? u3i_string(hed_u->val_c) : u3_nul), _http_heds_to_list(hed_u->nex_u)); } }
/* _sist_text(): ask for a name string. */ static u3_noun _sist_text(c3_c* pom_c) { c3_c paw_c[60]; u3_noun say; uH; while ( 1 ) { printf("%s: ", pom_c); paw_c[0] = 0; fpurge(stdin); fgets(paw_c, 59, stdin); if ( '\n' == paw_c[0] ) { continue; } else { c3_w len_w = strlen(paw_c); if ( paw_c[len_w - 1] == '\n' ) { paw_c[len_w-1] = 0; } say = u3i_string(paw_c); break; } } uL(0); return say; }
/* u3_sist_boot(): restore or create. */ void u3_sist_boot(void) { // uL(fprintf(uH, "sist: booting\n")); if ( c3y == u3_Host.ops_u.nuu ) { u3_noun pig = u3_none; if ( 0 == u3_Host.ops_u.imp_c ) { c3_c get_c[2049]; snprintf(get_c, 2048, "%s/.urb/get", u3_Host.dir_c); if ( 0 == access(get_c, 0) ) { uL(fprintf(uH, "pier: already built\n")); u3_lo_bail(); } u3_noun ten = _sist_zen(); uL(fprintf(uH, "generating 2048-bit RSA pair...\n")); pig = u3nq(c3__make, u3_nul, 11, u3nc(ten, u3_Host.ops_u.fak)); } else { u3_noun imp = u3i_string(u3_Host.ops_u.imp_c); u3_noun whu = u3dc("slaw", 'p', u3k(imp)); if ( (u3_nul == whu) ) { fprintf(stderr, "czar: incorrect format\r\n"); u3_lo_bail(); } else { u3_noun gen = u3_nul; u3_noun gun = u3_nul; if (c3n == u3_Host.ops_u.fak) { gen = _sist_text("generator"); gun = u3dc("slaw", c3__uw, gen); if ( u3_nul == gun ) { fprintf(stderr, "czar: incorrect format\r\n"); u3_lo_bail(); } } else { gun = u3nc(u3_nul, u3_nul); } pig = u3nq(c3__sith, u3k(u3t(whu)), u3k(u3t(gun)), u3_Host.ops_u.fak); u3z(whu); u3z(gun); } u3z(imp); } _sist_make(pig); } else { _sist_rest(); } }
/* _unix_string_to_path(): convert c string to u3_noun path * * c string must begin with the pier path plus mountpoint */ static u3_noun _unix_string_to_path_helper(c3_c* pax_c) { c3_assert(pax_c[-1] == '/'); c3_c* end_w = strchr(pax_c, '/'); if ( !end_w ) { end_w = strrchr(pax_c, '.'); if ( !end_w ) { return u3nc(u3i_string(pax_c), u3_nul); } else { return u3nt(u3i_bytes(end_w - pax_c, (c3_y*) pax_c), u3i_string(end_w + 1), u3_nul); } } else { return u3nc(u3i_bytes(end_w - pax_c, (c3_y*) pax_c), _unix_string_to_path_helper(end_w + 1)); } }
/* _unix_initial_update_file(): read file, but don't watch */ static u3_noun _unix_initial_update_file(c3_c* pax_c) { struct stat buf_u; c3_i fid_i = open(pax_c, O_RDONLY, 0644); c3_ws len_ws, red_ws; c3_y* dat_y; if ( fid_i < 0 || fstat(fid_i, &buf_u) < 0 ) { if ( ENOENT == errno ) { return u3_nul; } else { uL(fprintf(uH, "error opening initial file %s: %s\r\n", pax_c, strerror(errno))); return u3_nul; } } len_ws = buf_u.st_size; dat_y = c3_malloc(len_ws); red_ws = read(fid_i, dat_y, len_ws); if ( close(fid_i) < 0 ) { uL(fprintf(uH, "error closing initial file %s: %s\r\n", pax_c, strerror(errno))); } if ( len_ws != red_ws ) { if ( red_ws < 0 ) { uL(fprintf(uH, "error reading initial file %s: %s\r\n", pax_c, strerror(errno))); } else { uL(fprintf(uH, "wrong # of bytes read in initial file %s: %d %d\r\n", pax_c, len_ws, red_ws)); } free(dat_y); return u3_nul; } else { u3_noun pax = _unix_string_to_path_helper(pax_c + strlen(U3_LIB) + 6); /* XX VERY BAD */ u3_noun mim = u3nt(c3__text, u3i_string("plain"), u3_nul); u3_noun dat = u3nt(mim, len_ws, u3i_bytes(len_ws, dat_y)); free(dat_y); return u3nc(u3nt(pax, u3_nul, dat), u3_nul); } }
/* _unix_update_mount(): update mount point */ static void _unix_update_mount(u3_umon* mon_u, u3_noun all) { if ( c3n == mon_u->dir_u.dry ) { u3_noun can = u3_nul; u3_unod* nod_u; for ( nod_u = mon_u->dir_u.kid_u; nod_u; nod_u = nod_u->nex_u ) { can = u3kb_weld(_unix_update_node(nod_u), can); } u3v_plan(u3nq(u3_blip, c3__sync, u3k(u3A->sen), u3_nul), u3nq(c3__into, u3i_string(mon_u->nam_c), all, can)); } }
/* u3_term_ef_ticket(): initial effects for new ticket. */ void u3_term_ef_ticket(c3_c* who_c, c3_c* tic_c) { u3_noun pax = u3nq(u3_blip, c3__term, '1', u3_nul); u3_noun who, tic; u3_noun whu, tuc; whu = u3dc("slaw", 'p', u3i_string(who_c)); if ( u3_nul == whu ) { fprintf(stderr, "ticket: invalid planet '%s'\r\n", who_c); exit(1); } else { who = u3k(u3t(whu)); u3z(whu); } tuc = u3dc("slaw", 'p', u3i_string(tic_c)); if ( u3_nul == tuc ) { fprintf(stderr, "ticket: invalid secret '%s'\r\n", tic_c); exit(1); } else { tic = u3k(u3t(tuc)); u3z(tuc); } u3v_plan(pax, u3nt(c3__tick, who, tic)); }
/* _unix_sync_ergo(): sync list of changes to unix */ static void _unix_sync_ergo(u3_umon* mon_u, u3_noun can) { u3_noun nac = can; u3_noun nam = u3i_string(mon_u->nam_c); while ( u3_nul != nac) { _unix_sync_change(&mon_u->dir_u, u3nc(u3k(nam), u3k(u3h(u3h(nac)))), u3k(u3t(u3h(nac)))); nac = u3t(nac); } u3z(nam); u3z(can); }
/* _sist_cask(): ask for a passcode. */ static u3_noun _sist_cask(c3_c* dir_c, u3_noun nun) { c3_c paw_c[60]; u3_noun key; uH; while ( 1 ) { printf("passcode for %s%s? ~", dir_c, (c3y == nun) ? " [none]" : ""); paw_c[0] = 0; c3_fpurge(stdin); fgets(paw_c, 59, stdin); if ( '\n' == paw_c[0] ) { if ( c3y == nun ) { key = 0; break; } else { continue; } } else { c3_c* say_c = c3_malloc(strlen(paw_c) + 2); u3_noun say; say_c[0] = '~'; say_c[1] = 0; strncat(say_c, paw_c, strlen(paw_c) - 1); say = u3do("slay", u3i_string(say_c)); if ( (u3_nul == say) || (u3_blip != u3h(u3t(say))) || ('p' != u3h(u3t(u3t(say)))) ) { printf("invalid passcode\n"); continue; } key = u3k(u3t(u3t(u3t(say)))); u3z(say); break; } } uL(0); return key; }
static u3_noun _unix_string_to_path(c3_c* pax_c) { pax_c += strlen(u3_Host.dir_c) + 1; c3_c* pox_c = strchr(pax_c, '/'); if ( !pox_c ) { pox_c = strchr(pax_c, '.'); if ( !pox_c ) { return u3_nul; } else { return u3nc(u3i_string(pox_c + 1), u3_nul); } } else { return _unix_string_to_path_helper(pox_c + 1); } }
static u3_noun _play_loc_term(u3_noun van, u3_noun loc) { u3_noun fop = u3kb_flop(u3k(u3h(loc))); u3_noun nam = ((0 == fop) ? c3__none : u3k(u3h(fop))); u3_noun lys = u3nt(u3k(u3h(u3t(loc))), u3k(u3t(u3t(loc))), u3_nul); u3_noun rup = u3nc(nam, lys); c3_c* pre_c = u3m_pretty(rup); u3_noun pro = u3i_string(pre_c); u3z(fop); u3z(rup); free(pre_c); return pro; }
/* _http_request_to_noun(): translate http request into noun, or u3_none. */ static u3_noun _http_request_to_noun(u3_hreq* req_u) { u3_noun med, url, hed, bod; switch ( req_u->met_e ) { default: fprintf(stderr, "strange request\r\n"); return u3_none; case u3_hmet_put: { med = c3__put; break; } case u3_hmet_get: { med = c3__get; break; } case u3_hmet_head: { med = c3__head; break; } case u3_hmet_post: { med = c3__post; break; } } url = u3i_string(req_u->url_c); hed = _http_heds_to_list(req_u->hed_u); bod = req_u->bod_u ? u3nc(u3_nul, _http_bods_to_octs(req_u->bod_u)) : u3_nul; return u3nq(med, url, hed, bod); }
/* _unix_update_file(): update file, producing list of changes * * when scanning through files, if dry, do nothing. otherwise, mark as * dry, then check if file exists. if not, remove self from node list * and add path plus sig to %into event. otherwise, read the file and * get a mug checksum. if same as mug_w, move on. otherwise, overwrite * mug_w with new mug and add path plus data to %into event. */ static u3_noun _unix_update_file(u3_ufil* fil_u) { c3_assert( c3n == fil_u->dir ); if ( c3y == fil_u->dry ) { return u3_nul; } fil_u->dry = c3y; struct stat buf_u; c3_i fid_i = open(fil_u->pax_c, O_RDONLY, 0644); c3_ws len_ws, red_ws; c3_y* dat_y; if ( fid_i < 0 || fstat(fid_i, &buf_u) < 0 ) { if ( ENOENT == errno ) { return u3nc(u3nc(_unix_string_to_path(fil_u->pax_c), u3_nul), u3_nul); } else { uL(fprintf(uH, "error opening file %s: %s\r\n", fil_u->pax_c, strerror(errno))); return u3_nul; } } // So, if file gets deleted and then quickly re-added, like vim and // other editors do, we lose the notification. This is a bad thing, // so we always stop and restart the notification. uv_fs_event_stop(&fil_u->was_u); c3_w ret_w = uv_fs_event_start(&fil_u->was_u, _unix_fs_event_cb, fil_u->pax_c, 0); if ( 0 != ret_w ) { uL(fprintf(uH, "update file event start: %s\n", uv_strerror(ret_w))); c3_assert(0); } len_ws = buf_u.st_size; dat_y = c3_malloc(len_ws); red_ws = read(fid_i, dat_y, len_ws); if ( close(fid_i) < 0 ) { uL(fprintf(uH, "error closing file %s: %s\r\n", fil_u->pax_c, strerror(errno))); } if ( len_ws != red_ws ) { if ( red_ws < 0 ) { uL(fprintf(uH, "error reading file %s: %s\r\n", fil_u->pax_c, strerror(errno))); } else { uL(fprintf(uH, "wrong # of bytes read in file %s: %d %d\r\n", fil_u->pax_c, len_ws, red_ws)); } free(dat_y); return u3_nul; } else { c3_w mug_w = u3r_mug_bytes(dat_y, len_ws); if ( mug_w == fil_u->mug_w ) { free(dat_y); return u3_nul; } else if ( mug_w == fil_u->gum_w ) { fil_u->mug_w = mug_w; free(dat_y); return u3_nul; } else { fil_u->mug_w = mug_w; u3_noun pax = _unix_string_to_path(fil_u->pax_c); u3_noun mim = u3nt(c3__text, u3i_string("plain"), u3_nul); u3_noun dat = u3nt(mim, len_ws, u3i_bytes(len_ws, dat_y)); free(dat_y); return u3nc(u3nt(pax, u3_nul, dat), u3_nul); } } }