1 /* v/reck.c
2 **
3 **  This file is in the public domain.
4 */
5 #include <stdio.h>
6 #include <stdlib.h>
7 #include <fcntl.h>
8 #include <sys/ioctl.h>
9 #include <sys/stat.h>
10 #include <unistd.h>
11 #include <setjmp.h>
12 #include <gmp.h>
13 #include <dirent.h>
14 #include <stdint.h>
15 #include <uv.h>
16 #include <curses.h>
17 #include <termios.h>
18 #include <term.h>
19 
20 #include "all.h"
21 #include "vere/vere.h"
22 
23 /* _reck_mole(): parse simple atomic mole.
24 */
25 static u3_noun
_reck_mole(u3_noun fot,u3_noun san,c3_d * ato_d)26 _reck_mole(u3_noun  fot,
27            u3_noun  san,
28            c3_d*    ato_d)
29 {
30   u3_noun uco = u3do("slay", san);
31   u3_noun p_uco, q_uco, r_uco, s_uco;
32 
33   if ( (c3n == u3r_qual(uco, &p_uco, &q_uco, &r_uco, &s_uco)) ||
34        (0 != p_uco) ||
35        (0 != q_uco) ||
36        (c3n == u3r_sing(fot, r_uco)) )
37   {
38     uL(fprintf(uH, "strange mole %s\n", u3r_string(san)));
39 
40     u3z(fot); u3z(uco); return c3n;
41   }
42   else {
43     *ato_d = u3r_chub(0, s_uco);
44 
45     u3z(fot); u3z(uco); return c3y;
46   }
47 }
48 
49 /* _reck_lily(): parse little atom.
50 */
51 static u3_noun
_reck_lily(u3_noun fot,u3_noun txt,c3_l * tid_l)52 _reck_lily(u3_noun fot, u3_noun txt, c3_l* tid_l)
53 {
54   c3_d ato_d;
55 
56   if ( c3n == _reck_mole(fot, txt, &ato_d) ) {
57     return c3n;
58   } else {
59     if ( ato_d >= 0x80000000ULL ) {
60       return c3n;
61     } else {
62       *tid_l = (c3_l) ato_d;
63 
64       return c3y;
65     }
66   }
67 }
68 
69 /* _reck_kick_term(): apply terminal outputs.
70 */
71 static u3_noun
_reck_kick_term(u3_noun pox,c3_l tid_l,u3_noun fav)72 _reck_kick_term(u3_noun pox, c3_l tid_l, u3_noun fav)
73 {
74   u3_noun p_fav;
75 
76   if ( c3n == u3du(fav) ) {
77     u3z(pox); u3z(fav); return c3n;
78   }
79   else switch ( u3h(fav) ) {
80     default: u3z(pox); u3z(fav); return c3n;
81     case c3__bbye:
82     {
83       u3z(pox); u3z(fav); return c3y;
84     } break;
85 
86     case c3__blit: p_fav = u3t(fav);
87     {
88       u3_term_ef_blit(tid_l, u3k(p_fav));
89 
90       u3z(pox); u3z(fav); return c3y;
91     } break;
92 
93     case c3__logo:
94     {
95       u3_Host.liv = c3n;
96       u3_Host.xit_i = u3t(fav);
97 
98       u3z(pox); u3z(fav); return c3y;
99     } break;
100 
101     case c3__init: p_fav = u3t(fav);
102     {
103       u3A->own = u3nc(u3k(p_fav), u3A->own);
104 
105       u3_noun hox =  u3dc("scot", 'p', u3k(p_fav));
106       c3_c* nam_c = u3r_string(hox);
107 
108       // uL(fprintf(uH, "kick: init: %s\n", nam_c));
109       free(nam_c); u3z(pox); u3z(hox); u3z(fav); return c3y;
110     } break;
111 
112     case c3__mass: p_fav = u3t(fav);
113     {
114       u3A->sac = u3k(p_fav);
115 
116       u3z(pox); u3z(fav); return c3y;
117     } break;
118   }
119   c3_assert(!"not reached"); return 0;
120 }
121 
122 /* _reck_kick_http(): apply http effects.
123 */
124 static u3_noun
_reck_kick_http(u3_noun pox,c3_l sev_l,c3_l coq_l,c3_l seq_l,u3_noun fav)125 _reck_kick_http(u3_noun  pox,
126                 c3_l     sev_l,
127                 c3_l     coq_l,
128                 c3_l     seq_l,
129                 u3_noun  fav)
130 {
131   u3_noun p_fav, q_fav;
132 
133   if ( c3n == u3du(fav) ) {
134     u3z(pox); u3z(fav); return c3n;
135   }
136   else switch ( u3h(fav) ) {
137     default: u3z(pox); u3z(fav); return c3n;
138 
139     case c3__thus: p_fav = u3h(u3t(fav)); q_fav = u3t(u3t(fav));
140     {
141       u3_cttp_ef_thus(u3r_word(0, p_fav), u3k(q_fav));
142 
143       u3z(pox); u3z(fav);
144       return c3y;
145     }
146     case c3__thou: p_fav = u3t(fav);
147     {
148       u3_http_ef_thou(sev_l, coq_l, seq_l, u3k(p_fav));
149 
150       u3z(pox); u3z(fav);
151       return c3y;
152     } break;
153   }
154   c3_assert(!"not reached"); return c3n;
155 }
156 
157 /* _reck_kick_sync(): apply sync outputs.
158 */
159 static u3_noun
_reck_kick_sync(u3_noun pox,u3_noun fav)160 _reck_kick_sync(u3_noun pox, u3_noun fav)
161 {
162   switch ( u3h(fav) ) {
163     default: break;
164     case c3__ergo: {
165       u3_noun mon = u3k(u3h(u3t(fav)));
166       u3_noun can = u3k(u3t(u3t(fav)));
167 
168       u3_unix_ef_ergo(mon, can);
169       u3z(pox); u3z(fav); return c3y;
170     } break;
171     case c3__ogre: {
172       u3_unix_ef_ogre(u3k(u3t(fav)));
173       u3z(pox); u3z(fav); return c3y;
174     }
175     case c3__hill: {
176       u3_unix_ef_hill(u3k(u3t(fav)));
177       u3z(pox); u3z(fav); return c3y;
178     }
179   }
180 
181   //  XX obviously not right!
182   //  ? looks fine to me
183   u3z(pox); u3z(fav); return c3n;
184 }
185 
186 static u3_noun
_reck_kick_newt(u3_noun pox,u3_noun fav)187 _reck_kick_newt(u3_noun pox, u3_noun fav)
188 {
189   switch ( u3h(fav) ) {
190     default: break;
191     case c3__send: {
192       u3_noun lan = u3k(u3h(u3t(fav)));
193       u3_noun pac = u3k(u3t(u3t(fav)));
194 
195       u3_ames_ef_send(lan, pac);
196       u3z(pox); u3z(fav); return c3y;
197     } break;
198   }
199   u3z(pox); u3z(fav); return c3n;
200 }
201 
202 /* _reck_kick_ames(): apply packet network outputs.
203 */
204 static u3_noun
_reck_kick_ames(u3_noun pox,u3_noun fav)205 _reck_kick_ames(u3_noun pox, u3_noun fav)
206 {
207   u3_noun p_fav;
208 
209   switch ( u3h(fav) ) {
210     default: break;
211     case c3__init: p_fav = u3t(fav);
212     {
213       u3A->own = u3nc(u3k(p_fav), u3A->own);
214 
215       // uL(fprintf(uH, "kick: init: %d\n", p_fav));
216       u3z(pox); u3z(fav); return c3y;
217     } break;
218   }
219   u3z(pox); u3z(fav); return c3n;
220 }
221 
222 /* _reck_kick_spec(): apply an effect, by path.
223 */
224 static u3_noun
_reck_kick_spec(u3_noun pox,u3_noun fav)225 _reck_kick_spec(u3_noun pox, u3_noun fav)
226 {
227   u3_noun i_pox, t_pox;
228   u3_noun p_fav;
229 
230   if ( (c3n == u3r_cell(pox, &i_pox, &t_pox)) ||
231        ((i_pox != u3_blip) &&
232         (i_pox != c3__gold) &&
233         (i_pox != c3__iron) &&
234         (i_pox != c3__lead)) )
235   {
236     u3z(pox); u3z(fav); return c3n;
237   } else {
238     u3_noun it_pox, tt_pox;
239 
240     if ( (c3n == u3r_cell(t_pox, &it_pox, &tt_pox)) ) {
241       u3z(pox); u3z(fav); return c3n;
242     }
243     else switch ( it_pox ) {
244       default: u3z(pox); u3z(fav); return c3n;
245 
246       case c3__http: {
247         u3_noun pud = tt_pox;
248         u3_noun p_pud, t_pud, tt_pud, q_pud, r_pud, s_pud;
249         c3_l    sev_l, coq_l, seq_l;
250 
251         if ( (c3n == u3r_cell(pud, &p_pud, &t_pud)) ||
252              (c3n == _reck_lily(c3__uv, u3k(p_pud), &sev_l)) )
253         {
254           u3z(pox); u3z(fav); return c3n;
255         }
256 
257         if ( u3_nul == t_pud ) {
258           coq_l = seq_l = 0;
259         }
260         else {
261           if ( (c3n == u3r_cell(t_pud, &q_pud, &tt_pud)) ||
262                (c3n == _reck_lily(c3__ud, u3k(q_pud), &coq_l)) )
263           {
264             u3z(pox); u3z(fav); return c3n;
265           }
266 
267           if ( u3_nul == tt_pud ) {
268             seq_l = 0;
269           } else {
270             if ( (c3n == u3r_cell(tt_pud, &r_pud, &s_pud)) ||
271                  (u3_nul != s_pud) ||
272                  (c3n == _reck_lily(c3__ud, u3k(r_pud), &seq_l)) )
273             {
274               u3z(pox); u3z(fav); return c3n;
275             }
276           }
277         }
278         return _reck_kick_http(pox, sev_l, coq_l, seq_l, fav);
279       } break;
280 
281       case c3__clay:
282       case c3__boat:
283       case c3__sync: {
284         return _reck_kick_sync(pox, fav);
285       } break;
286 
287       case c3__newt: {
288         return _reck_kick_newt(pox, fav);
289       } break;
290 
291       case c3__ames: {
292         if ( (u3_nul != tt_pox) ) {
293           u3z(pox); u3z(fav); return c3n;
294         }
295         else {
296           return _reck_kick_ames(pox, fav);
297         }
298       } break;
299 
300       case c3__init: p_fav = u3t(fav);
301       {
302         u3A->own = u3nc(u3k(p_fav), u3A->own);
303 
304         // uL(fprintf(uH, "kick: init: %d\n", p_fav));
305         u3z(pox); u3z(fav); return c3y;
306       } break;
307 
308       case c3__term: {
309         u3_noun pud = tt_pox;
310         u3_noun p_pud, q_pud;
311         c3_l    tid_l;
312 
313         if ( (c3n == u3r_cell(pud, &p_pud, &q_pud)) ||
314              (u3_nul != q_pud) ||
315              (c3n == _reck_lily(c3__ud, u3k(p_pud), &tid_l)) )
316         {
317           uL(fprintf(uH, "term: bad tire\n"));
318           u3z(pox); u3z(fav); return c3n;
319         } else {
320           return _reck_kick_term(pox, tid_l, fav);
321         }
322       } break;
323     }
324   }
325   c3_assert(!"not reached");
326   return c3n;
327 }
328 
329 /* _reck_kick_norm(): non path-specific effect handling.
330 */
331 static u3_noun
_reck_kick_norm(u3_noun pox,u3_noun fav)332 _reck_kick_norm(u3_noun pox, u3_noun fav)
333 {
334   if ( c3n == u3du(fav) ) {
335     u3z(pox); u3z(fav); return c3n;
336   }
337   else switch ( u3h(fav) ) {
338     default: u3z(pox); u3z(fav); return c3n;
339 
340     case c3__vega:
341     {
342       uL(fprintf(uH, "<<<reset>>>\n"));
343       u3z(pox); u3z(fav);
344 
345       //  u3_ds_wipe(u3_Wire);  //  doesn't work
346 
347       return c3y;
348     }
349     case c3__exit:
350     {
351       uL(fprintf(uH, "<<<goodbye>>>\n"));
352       u3_lo_bail();
353 
354       u3z(pox); u3z(fav); return c3y;
355     } break;
356   }
357   c3_assert(!"not reached"); return c3n;
358   u3z(pox); u3z(fav); return c3n;
359 }
360 
361 /* u3_reck_kick(): handle effect.
362 */
363 void
u3_reck_kick(u3_noun ovo)364 u3_reck_kick(u3_noun ovo)
365 {
366   if ( (c3n == _reck_kick_spec(u3k(u3h(ovo)), u3k(u3t(ovo)))) &&
367        (c3n == _reck_kick_norm(u3k(u3h(ovo)), u3k(u3t(ovo)))) )
368   {
369 #if 0
370     if ( (c3__warn != u3h(u3t(ovo))) &&
371          (c3__text != u3h(u3t(ovo))) &&
372          (c3__note != u3h(u3t(ovo))) )
373 #endif
374 #if 1
375     if ( (c3__crud == u3h(u3t(ovo))) )
376 #if 0
377          (c3__talk == u3h(u3t(ovo))) ||
378          (c3__helo == u3h(u3t(ovo))) ||
379          (c3__init == u3h(u3t(ovo))) )
380 #endif
381     {
382       u3v_plan(u3nt(u3_blip, c3__term, u3_nul),
383                  u3nc(c3__flog, u3k(u3t(ovo))));
384     }
385     else {
386       u3_noun tox = u3do("spat", u3k(u3h(ovo)));
387       uL(fprintf(uH, "kick: lost %%%s on %s\n",
388                      u3r_string(u3h(u3t(ovo))),
389                      u3r_string(tox)));
390       u3z(tox);
391 #if 0
392       if ( c3__hear == u3h(u3t(ovo)) ) {
393         c3_assert(0);
394       }
395 #endif
396     }
397 #endif
398   }
399   u3z(ovo);
400 }
401