Эх сурвалжийг харах

upd help; fix converges; fix stencil; fix rank

txlyre 5 сар өмнө
parent
commit
131b3a51b8
1 өөрчлөгдсөн 139 нэмэгдсэн , 119 устгасан
  1. 139 119
      jk.c

+ 139 - 119
jk.c

@@ -1,18 +1,18 @@
 /* jk intepreter, by @txlyre,www:txlyre.website, in the public domain */
-#include <ctype.h>
-#include <limits.h>
-#include <math.h>
-#include <setjmp.h>
-#include <stdbool.h>
-#include <stdint.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <time.h>
-#include <unistd.h>
-#include <sys/wait.h>
-#include <errno.h>
-#include <gc.h>
+#include<ctype.h>
+#include<limits.h>
+#include<math.h>
+#include<setjmp.h>
+#include<stdbool.h>
+#include<stdint.h>
+#include<stdio.h>
+#include<stdlib.h>
+#include<string.h>
+#include<time.h>
+#include<unistd.h>
+#include<sys/wait.h>
+#include<errno.h>
+#include<gc.h>
 #define R return
 #define BR break
 #define CN continue
@@ -125,7 +125,7 @@ Lst*lI(Lst**list,SZ index,P value){Lst*head=*list;
     Lst*temp=ln();
     temp->value=value;
     temp->next=head;
-   *list=temp;R temp;}
+    *list=temp;R temp;}
   Lst*temp0=*list;
   for(Z i=0;i<((Z)index)-1;i++)temp0=temp0->next;
   Lst*temp=temp0->next;
@@ -139,7 +139,8 @@ Lst*ld(Lst**list,SZ index){Lst*head=*list;
   if(index<0||index>=length)R N;
   if(index==0){head->value=N;
     if(!head->next)R head;
-   *list=head->next;R*list;}
+    *list=head->next;
+    return*list;}
   Lst*temp0=*list;
   for(Z i=0;i<((Z)index)-1;i++)temp0=temp0->next;
   Lst*temp=temp0->next;
@@ -234,7 +235,7 @@ V Llex(Lt*lexer,S s){lexer->source=s;
       LpT(lexer,T_QUOTE,Bread(buf));}elif(ispunct(c)){C buf[3];
       buf[0]=Leat(lexer);
       buf[1]=0;
-      if(Llook(lexer,0)=='.' ||Llook(lexer,0)==':'){buf[1]=Leat(lexer);
+      if(Llook(lexer,0)=='.'||Llook(lexer,0)==':'){buf[1]=Leat(lexer);
         buf[2]=0;}
       if(strcmp(buf,"-")==0&&isdigit(Llook(lexer,0))){Llnum(lexer,T);CN;}
       LpT(lexer,T_PUNCT,sdup(buf));}else Lerror(lexer,"lex");}}
@@ -262,35 +263,35 @@ static U64 MM86128(P key,const I len,U32 seed){const uint8_t*data=(const uint8_t
   U32 c2=0xab0e9789;
   U32 c3=0x38b34ae5;
   U32 c4=0xa1e38b93;
-  const U32*blocks=(const U32*)(data+nblocks*16);
+  const uint32_t*blocks=(const uint32_t*)(data+nblocks*16);
   for(I i=-nblocks;i;i++){U32 k1=blocks[i*4+0];
     U32 k2=blocks[i*4+1];
     U32 k3=blocks[i*4+2];
     U32 k4=blocks[i*4+3];
-    k1*= c1;
+    k1*=c1;
     k1=ROTL32(k1,15);
-    k1*= c2;
+    k1*=c2;
     h1^=k1;
     h1=ROTL32(h1,19);
     h1+=h2;
     h1=h1*5+0x561ccd1b;
-    k2*= c2;
+    k2*=c2;
     k2=ROTL32(k2,16);
-    k2*= c3;
+    k2*=c3;
     h2^=k2;
     h2=ROTL32(h2,17);
     h2+=h3;
     h2=h2*5+0x0bcaa747;
-    k3*= c3;
+    k3*=c3;
     k3=ROTL32(k3,17);
-    k3*= c4;
+    k3*=c4;
     h3^=k3;
     h3=ROTL32(h3,15);
     h3+=h4;
     h3=h3*5+0x96cd1c35;
-    k4*= c4;
+    k4*=c4;
     k4=ROTL32(k4,18);
-    k4*= c1;
+    k4*=c1;
     h4^=k4;
     h4=ROTL32(h4,13);
     h4+=h1;
@@ -300,36 +301,36 @@ static U64 MM86128(P key,const I len,U32 seed){const uint8_t*data=(const uint8_t
   U32 k2=0;
   U32 k3=0;
   U32 k4=0;
-  SW(len & 15){CS 15:k4^=tail[14] << 16;
-  CS 14:k4^=tail[13] << 8;
-  CS 13:k4^=tail[12] << 0;
-    k4*= c4;
+  SW(len & 15){CS 15:k4^=tail[14]<<16;
+  CS 14:k4^=tail[13]<<8;
+  CS 13:k4^=tail[12]<<0;
+    k4*=c4;
     k4=ROTL32(k4,18);
-    k4*= c1;
+    k4*=c1;
     h4^=k4;
-  CS 12:k3^=tail[11] << 24;
-  CS 11:k3^=tail[10] << 16;
-  CS 10:k3^=tail[9] << 8;
-  CS 9:k3^=tail[8] << 0;
-    k3*= c3;
+  CS 12:k3^=tail[11]<<24;
+  CS 11:k3^=tail[10]<<16;
+  CS 10:k3^=tail[9]<<8;
+  CS 9:k3^=tail[8]<<0;
+    k3*=c3;
     k3=ROTL32(k3,17);
-    k3*= c4;
+    k3*=c4;
     h3^=k3;
-  CS 8:k2^=tail[7] << 24;
-  CS 7:k2^=tail[6] << 16;
-  CS 6:k2^=tail[5] << 8;
-  CS 5:k2^=tail[4] << 0;
-    k2*= c2;
+  CS 8:k2^=tail[7]<<24;
+  CS 7:k2^=tail[6]<<16;
+  CS 6:k2^=tail[5]<<8;
+  CS 5:k2^=tail[4]<<0;
+    k2*=c2;
     k2=ROTL32(k2,16);
-    k2*= c3;
+    k2*=c3;
     h2^=k2;
-  CS 4:k1^=tail[3] << 24;
-  CS 3:k1^=tail[2] << 16;
-  CS 2:k1^=tail[1] << 8;
-  CS 1:k1^=tail[0] << 0;
-    k1*= c1;
+  CS 4:k1^=tail[3]<<24;
+  CS 3:k1^=tail[2]<<16;
+  CS 2:k1^=tail[1]<<8;
+  CS 1:k1^=tail[0]<<0;
+    k1*=c1;
     k1=ROTL32(k1,15);
-    k1*= c2;
+    k1*=c2;
     h1^=k1;}
   h1^=len;
   h2^=len;
@@ -350,13 +351,13 @@ static U64 MM86128(P key,const I len,U32 seed){const uint8_t*data=(const uint8_t
   h1+=h4;
   h2+=h1;
   h3+=h1;
-  h4+=h1;R(((U64)h2)<< 32)| h1;}
+  h4+=h1;R(((U64)h2)<<32)| h1;}
 static U32 HASH_SEED=0;
 P Tget(Tt*table,S key){if(Tempty(table))R N;
   U64 hash=MM86128(key,strlen(key),HASH_SEED);
   Z index=hash%table->capacity;
   Z i=index;
-  WH(table->entries[i].key){if(!table->entries[i].is_deleted &&strcmp(table->entries[i].key,key)==0)R table->entries[i].value;
+  WH(table->entries[i].key){if(!table->entries[i].is_deleted&&strcmp(table->entries[i].key,key)==0)R table->entries[i].value;
     i++;
     if(i>=table->capacity)i=0;
     if(i==index)BR;}
@@ -365,7 +366,7 @@ B Thas(Tt*table,S key){if(Tempty(table))R F;
   U64 hash=MM86128(key,strlen(key),HASH_SEED);
   Z index=hash%table->capacity;
   Z i=index;
-  WH(table->entries[i].key){if(!table->entries[i].is_deleted &&strcmp(table->entries[i].key,key)==0)R T;
+  WH(table->entries[i].key){if(!table->entries[i].is_deleted&&strcmp(table->entries[i].key,key)==0)R T;
     i++;
     if(i>=table->capacity)i=0;
     if(i==index)BR;}
@@ -448,7 +449,7 @@ Vt*Vnn(D number){if(isnan(number))R _NAN;
   elif(number==INFINITY)R INF;
   elif(number==-INFINITY)R NINF;
   elif(number>=0&&number<256&&number==(D)((Z)number))R NUMS[(Z)number];
-  elif(number<0&&number>=-8 &&fabs(number)==(D)((Z)fabs(number)))R NNUMS[((Z)fabs(number))-1];
+  elif(number<0&&number>=-8&&fabs(number)==(D)((Z)fabs(number)))R NNUMS[((Z)fabs(number))-1];
   Vt*val=Vnew(NUM);
   val->val.number=number;R val;}
 Vt*Vnc(UC _char){R CHARS[_char];}
@@ -613,9 +614,9 @@ Vt*_over_d(St*st,vt*self,Vt*x,Vt*y){Vt*f=li(self->bonds,0);
   vt*g=li(self->bonds,1);
   vt*h=li(self->bonds,2);
   Vt*l=tgth(st,h,x,y,0,0,h->rank[1],h->rank[2]);R tgth(st,g,f,l,0,0,g->rank[1],g->rank[2]);}
-B nca(Nt*node,UI*argc){if(!node)R F;
-  if(node->tag==N_LITERAL&&node->v->tag==SYM &&strcmp(node->v->val.symbol,"y")==0){*argc=2;R T;}elif(node->tag==N_LITERAL&&node->v->tag==SYM &&strcmp(node->v->val.symbol,"x")==0){if(*argc<2)*argc=1;}elif(node->tag==N_MONAD||node->tag==N_CONJ ||node->tag==N_HOOK||node->tag==N_BOND ||node->tag==N_INDEX1){if(nca(node->a,argc))R T;
-    if(nca(node->b,argc))R T;}elif(node->tag==N_DYAD||node->tag==N_FORK ||node->tag==N_OVER||node->tag==N_INDEX2){if(nca(node->a,argc))R T;
+B nca(Nt*node,unsigned int*argc){if(!node)R F;
+  if(node->tag==N_LITERAL&&node->v->tag==SYM&&strcmp(node->v->val.symbol,"y")==0){*argc=2;R T;}elif(node->tag==N_LITERAL&&node->v->tag==SYM&&strcmp(node->v->val.symbol,"x")==0){if(*argc<2)*argc=1;}elif(node->tag==N_MONAD||node->tag==N_CONJ||node->tag==N_HOOK||node->tag==N_BOND||node->tag==N_INDEX1){if(nca(node->a,argc))R T;
+    if(nca(node->b,argc))R T;}elif(node->tag==N_DYAD||node->tag==N_FORK||node->tag==N_OVER||node->tag==N_INDEX2){if(nca(node->a,argc))R T;
     if(nca(node->b,argc))R T;
     if(nca(node->c,argc))R T;}elif(node->tag==N_ADV){if(nca(node->a,argc))R T;}elif(node->tag==N_STRAND){Lst*t=node->l;
     WH(t){if(nca(t->value,argc))R T;
@@ -833,7 +834,7 @@ Vt*vflip(St*st,vt*self,Vt*x){if(xt!=ARRAY||le(xa))R st->udf;
   R Vna(r);}
 Vt*vplus(St*st,vt*self,Vt*x,Vt*y){if((xt==NUM||xt==CHAR)&&(yt==NUM||yt==CHAR)){if(xt==CHAR||yt==CHAR)R Vnc(Vnum(x)+Vnum(y));R Vnn(Vnum(x)+Vnum(y));}
   R _NAN;}
-Vt*vsign(St*st,vt*self,Vt*x){if(xt==NUM)R xn<0? NNUMS[0]: xn>0? NUMS[1]: NUMS[0];R _NAN;}
+Vt*vsign(St*st,vt*self,Vt*x){if(xt==NUM)R xn<0?NNUMS[0]:xn>0?NUMS[1]:NUMS[0];R _NAN;}
 D gcd(D a,D b){if(b!=0)R gcd(b,fmod(a,b));
   else R fabs(a);}
 Vt*vgcd(St*st,vt*self,Vt*x,Vt*y){if(xt==NUM&&yt==NUM)R Vnn(gcd(xn,yn));R _NAN;}
@@ -850,7 +851,7 @@ Vt*vtimes(St*st,vt*self,Vt*x,Vt*y){if((xt==NUM||xt==CHAR)&&(yt==NUM||yt==CHAR)){
   R _NAN;}
 D lcm(D a,D b){R(a*b)/gcd(a,b);}
 U64 factorial(U64 n){U64 r=1;
-  WH(n>0)r*= n--;R r;}
+  WH(n>0)r*=n--;R r;}
 Vt*vfactorial(St*st,vt*self,Vt*x){if(xt==NUM)R Vnn(factorial((U64)fabs(xn)));R _NAN;}
 Vt*vlcm(St*st,vt*self,Vt*x,Vt*y){if(xt==NUM&&yt==NUM)R Vnn(lcm(xn,yn));R _NAN;}
 Vt*vdouble(St*st,vt*self,Vt*x){if(xt==NUM)R Vnn(xn*2);R _NAN;}
@@ -888,25 +889,25 @@ Vt*vmod(St*st,vt*self,Vt*x,Vt*y){if(xt==NUM&&yt==NUM){D ny=yn;
   R _NAN;}
 Vt*vtake(St*st,vt*self,Vt*x,Vt*y);
 Vt*vdrop(St*st,vt*self,Vt*x,Vt*y);
-B is_bad_num(D v){R isnan(v)||v==INFINITY||v==-INFINITY;}
+B spnp(D v){R isnan(v)||v==INFINITY||v==-INFINITY;}
 Vt*vodometer(St*st,vt*self,Vt*x){if(xt!=ARRAY)x=venlist(st,N,x);
   elif(le(xa)||!xa->next)R st->udf;
   Z p=1;
   Z xl=0;
   Lst*t=xa;
   WH(t){Vt*it=t->value;
-    if(it->tag!=NUM||is_bad_num(it->val.number))R st->udf;
+    if(it->tag!=NUM||spnp(it->val.number))R st->udf;
     p*=(Z)(it->val.number);
     t=t->next;xl++;}
   if(p<1)R st->unit;
   t=xa;
-  U64*lims=maa(SO(U64)*xl);
+  uint64_t*lims=maa(SO(U64)*xl);
   for(Z i=0;i<xl;i++){lims[i]=(Z)(((Vt*)t->value)->val.number);
     t=t->next;}
-  U64**z=ma(SO(U64*)*p);
+  uint64_t**z=ma(SO(uint64_t*)*p);
   for(Z i=0;i<p;i++)z[i]=maa(SO(U64)*xl);
-  for(Z i=0;i<p-1;i++){U64*r=z[i];
-    U64*s=z[i+1];
+  for(Z i=0;i<p-1;i++){uint64_t*r=z[i];
+    uint64_t*s=z[i+1];
     B carry=T;
     for(Z j=0;j<xl;j++){U64 a=xl-1-j;
       s[a]=r[a];
@@ -931,13 +932,13 @@ Vt*vpower(St*st,vt*self,Vt*x,Vt*y){if(xt==NUM&&yt==NUM)R Vnn(pow(xn,yn));R _NAN;
 Vt*vnlog(St*st,vt*self,Vt*x){if(xt==NUM)R Vnn(log(xn));R _NAN;}
 Vt*vlog(St*st,vt*self,Vt*x,Vt*y){if(xt==NUM&&yt==NUM)R Vnn(log(yn)/log(xn));R _NAN;}
 I bits_needed(U32 value){I bits=0;
-  for(I bit_test=16;bit_test>0;bit_test >>= 1){if(value >> bit_test!=0){bits+=bit_test;
-      value >>= bit_test;}}
+  for(I bit_test=16;bit_test>0;bit_test>>=1){if(value>>bit_test!=0){bits+=bit_test;
+      value>>=bit_test;}}
   R bits+value;}
 Vt*vbits(St*st,vt*self,Vt*x){if(xt==NUM){I n=xn;
     I bk=bits_needed(n);
     Lst*r=ln();
-    for(I i=0;i<bk;i++)if((n &(1 << i))>> i)lp(r,NUMS[1]);
+    for(I i=0;i<bk;i++)if((n &(1<<i))>>i)lp(r,NUMS[1]);
       else lp(r,NUMS[0]);R Vna(r);}
   R st->udf;}
 Vt*vbase(St*st,vt*self,Vt*x,Vt*y){if(xt==NUM&&yt==NUM){Z v=fabs(yn);
@@ -948,12 +949,12 @@ Vt*vbase(St*st,vt*self,Vt*x,Vt*y){if(xt==NUM&&yt==NUM){Z v=fabs(yn);
       v/=b;}
     R Vna(r);}
   R st->udf;}
-SZ indexOf(Lst*l,Vt*x){if(le(l))R -1;
+SZ indexOf(Lst*l,Vt*x){if(le(l))return-1;
   Z i=0;
   WH(l){if(Veq(l->value,x))R i;
     l=l->next;
     i++;}
-  R -1;}
+  return-1;}
 Vt*vgroup(St*st,vt*self,Vt*x){if(xt!=ARRAY)x=venlist(st,N,x);
   elif(le(xa))R x;
   Lst*r=ln();
@@ -1003,7 +1004,7 @@ Vt*vbuckets(St*st,vt*self,Vt*x,Vt*y){if(xt!=ARRAY)x=venlist(st,N,x);
   R Vna(r);}
 Vt*vequals(St*st,vt*self,Vt*x,Vt*y){R Veq(x,y)?NUMS[1]:NUMS[0];}
 Vt*vpermute(St*st,vt*self,Vt*x){if(xt!=ARRAY||le(xa)||!xa->next)R x;
-  Lst* permutation=lc(xa);
+  Lst*permutation=lc(xa);
   Z length=ll(permutation);
   Lst*result=ln();
   lp(result,lc(permutation));
@@ -1019,7 +1020,7 @@ Vt*vpermute(St*st,vt*self,Vt*x){if(xt!=ARRAY||le(xa)||!xa->next)R x;
       p=li(permutation,i);
       ls(permutation,i,li(permutation,k));
       ls(permutation,k,p);
-     *n=(*n)+1;
+      *n=(*n)+1;
       i=1;
       lp(result,lc(permutation));}else{*n=0;
       i++;}}
@@ -1044,7 +1045,7 @@ Vt*voccurences(St*st,vt*self,Vt*x){if(xt!=ARRAY)x=venlist(st,N,x);
     Lst*tt=table;
     if(!le(tt))WH(tt){Lst*p=tt->value;
         if(Veq(p->value,it)){Z*n=p->next->value;
-         *n=(*n)+1;
+          *n=(*n)+1;
           lp(r,Vnn(*n));
           f=T;BR;}
         tt=tt->next;}
@@ -1093,7 +1094,7 @@ Vt*vclassify(St*st,vt*self,Vt*x){if(xt!=ARRAY)x=venlist(st,N,x);
     if(!f){Lst*p=ln();
       lp(p,it);
       Z*n=maa(SO(Z));
-     *n=i++;
+      *n=i++;
       lp(p,n);
       lp(table,p);
       lp(r,Vnn(*n));}
@@ -1111,8 +1112,8 @@ Vt*vunbits(St*st,vt*self,Vt*x){if(xt!=ARRAY)x=venlist(st,N,x);
   I n=0;
   I i=0;
   Lst*t=xa;
-  WH(t){if(VTp(t->value))n|=(int)1 << i;
-    else n &= ~((int)1 << i);
+  WH(t){if(VTp(t->value))n|=(int)1<<i;
+    else n &=~((int)1<<i);
     t=t->next;
     i++;}
   R Vnn(n);}
@@ -1388,7 +1389,7 @@ Vt*vbin(St*st,vt*self,Vt*x,Vt*y){if(xt!=ARRAY)x=venlist(st,self,x);
     if(vs->tag==NUM)s=vs->val.number;
     elif(vs->tag==CHAR)s=vs->val._char;
     else R st->udf;
-    Vt*ve=i==xl-1? Vnn(s+1): li(xa,i+1);
+    Vt*ve=i==xl-1?Vnn(s+1):li(xa,i+1);
     if(ve->tag==NUM)e=fabs(ve->val.number);
     elif(ve->tag==CHAR)e=ve->val._char;
     else R st->udf;
@@ -1396,9 +1397,9 @@ Vt*vbin(St*st,vt*self,Vt*x,Vt*y){if(xt!=ARRAY)x=venlist(st,self,x);
       D*pe=pp->value;
       if(s<=(*pe))R st->udf;}
     D*sn=ma(SO(D));
-   *sn=s;
+    *sn=s;
     D*en=ma(SO(D));
-   *en=e;
+    *en=e;
     Lst*p=ln();
     lp(p,sn);
     lp(p,en);
@@ -1564,8 +1565,8 @@ U64 fibonacci(U64 n){U64 a=0;
 Vt*vfibonacci(St*st,vt*self,Vt*x){if(xt==NUM)R Vnn(fibonacci((U64)fabs(xn)));R _NAN;}
 Vt*viota(St*st,vt*self,Vt*x){if(Veq(x,NUMS[1]))R venlist(st,N,NUMS[1]);
   elif(Veq(x,NUMS[0]))R st->unit;R vrange(st,self,NUMS[1],x);}
-Vt*vrange(St*st,vt*self,Vt*x,Vt*y){if((xt==NUM||xt==CHAR)&&(yt==NUM||yt==CHAR)){if(xt==NUM&&is_bad_num(xn))R st->udf;
-    if(yt==NUM&&is_bad_num(yn))R st->udf;
+Vt*vrange(St*st,vt*self,Vt*x,Vt*y){if((xt==NUM||xt==CHAR)&&(yt==NUM||yt==CHAR)){if(xt==NUM&&spnp(xn))R st->udf;
+    if(yt==NUM&&spnp(yn))R st->udf;
     SZ s=Vnum(x);
     SZ e=Vnum(y);
     if(s==e)R venlist(st,N,x);
@@ -1631,7 +1632,7 @@ Vt*vread(St*st,vt*self,Vt*x){if(x==NUMS[0]){Bt*buf=Bnew();
   fseek(fd,0,SEEK_SET);
   UC*buf=ma(size+1);
   if(!buf)R st->udf;
-  size=fread(buf,SO(unsigned char),size,fd);
+  size=fread(buf,SO(UC),size,fd);
   fclose(fd);
   FR(path);
   Lst*r=ln();
@@ -1685,15 +1686,17 @@ struct files_chain_t{files_t files;
   struct files_chain_t*next;};
 typedef struct files_chain_t files_chain_t;
 static files_chain_t*files_chain;
-V _cleanup_pipe(I*pipe){close(pipe[0]);
+V _cleanup_pipe(int*pipe){close(pipe[0]);
   close(pipe[1]);}
 static I _do_popen2(files_chain_t*link,const S command){I child_in[2];
   I child_out[2];
-  if(0!=pipe(child_in))R -1;
-  if(0!=pipe(child_out)){_cleanup_pipe(child_in);R -1;}
+  if(0!=pipe(child_in))return-1;
+  if(0!=pipe(child_out)){_cleanup_pipe(child_in);
+    return-1;}
   pid_t cpid=link->pid=fork();
   if(0>cpid){_cleanup_pipe(child_in);
-    _cleanup_pipe(child_out);R -1;}
+    _cleanup_pipe(child_out);
+    return-1;}
   if(0==cpid){if(0>dup2(child_in[0],0)||0>dup2(child_out[1],1))_Exit(127);
     _cleanup_pipe(child_in);
     _cleanup_pipe(child_out);
@@ -1701,7 +1704,7 @@ static I _do_popen2(files_chain_t*link,const S command){I child_in[2];
       if(fd_in!=0)close(fd_in);
       I fd_out=fileno(p->files.out);
       if(fd_out!=1)close(fd_out);}
-    execl("/bin/sh","sh","-c",command,(S)N);
+    execl("/bin/sh","sh","-c",command,(S )N);
     _Exit(127);}
   close(child_in[0]);
   close(child_out[1]);
@@ -1717,13 +1720,14 @@ I pclose2(files_t*fp){files_chain_t**p=&files_chain;
   WH(*p){if(*p==(files_chain_t*)fp){*p=(*p)->next;
       found=1;BR;}
     p=&(*p)->next;}
-  if(!found)R -1;
-  if(0>fclose(fp->out)){free((files_chain_t*)fp);R -1;}
+  if(!found)return-1;
+  if(0>fclose(fp->out)){free((files_chain_t*)fp);
+    return-1;}
   I status=-1;
   pid_t wait_pid;
   do{wait_pid=waitpid(((files_chain_t*)fp)->pid,&status,0);}WH(-1==wait_pid&&EINTR==errno);
   free((files_chain_t*)fp);
-  if(wait_pid==-1)R -1;R status;}
+  if(wait_pid==-1)return-1;R status;}
 Vt*vsystem2(St*st,vt*self,Vt*x,Vt*y){S cmd=Vshow(y);
   files_t*pd;
   pd=popen2(cmd);
@@ -1770,8 +1774,8 @@ Lst*prime_factors(D n){Lst*factors=ln();
   WH(n>=2){if(fmod(n,divisor)==0){lp(factors,Vnn(divisor));
       n/=divisor;}else divisor++;}
   R factors;}
-Vt*vfactors(St*st,vt*self,Vt*x){if(xt==NUM&&!is_bad_num(xn))R Vna(prime_factors(xn));R st->udf;}
-Vt*vcombine(St*st,vt*self,Vt*x,Vt*y){if(xt==NUM&&yt==NUM&&!is_bad_num(xn)&&!is_bad_num(yn)){Vt*n=venpair(st,N,x,y);R vunbase(st,N,NUMS[10],n);}
+Vt*vfactors(St*st,vt*self,Vt*x){if(xt==NUM&&!spnp(xn))R Vna(prime_factors(xn));R st->udf;}
+Vt*vcombine(St*st,vt*self,Vt*x,Vt*y){if(xt==NUM&&yt==NUM&&!spnp(xn)&&!spnp(yn)){Vt*n=venpair(st,N,x,y);R vunbase(st,N,NUMS[10],n);}
   R _NAN;}
 Vt*Srun(St*st,S program);
 Vt*veval(St*st,vt*self,Vt*x){S s=Vshow(x);
@@ -1789,10 +1793,10 @@ Vt*vimport(St*st,vt*self,Vt*x){S path=Vshow(x);
   fseek(fd,0,SEEK_SET);
   UC*buf=ma(size+1);
   if(!buf)R st->udf;
-  size=fread(buf,SO(unsigned char),size,fd);
+  size=fread(buf,SO(UC),size,fd);
   fclose(fd);
   FR(path);
-  Vt*v=Srun(st,(S)buf);
+  Vt*v=Srun(st,(S )buf);
   FR(buf);R v;}
 Vt*vudf1(St*st,vt*self,Vt*x){R st->udf;}
 Vt*vudf2(St*st,vt*self,Vt*x,Vt*y){R st->udf;}
@@ -1880,12 +1884,11 @@ Vt*_advconverge_d(St*st,vt*self,Vt*x,Vt*y){Vt*_v=self->bonds->value;
   v=cnjbond(st,Vnv(v),x);R eR(st,v,y,0,1);}
 Vt*_advconverges_m(St*st,vt*self,Vt*x){Vt*_v=self->bonds->value;
   if(_v->tag!=VERB)R st->udf;
-  vt*v=_v->val.verb;
   Lst*r=ln();
   Vt*t;
   lp(r,x);
   LOOP{t=x;
-    x=eR(st,v,x,0,v->rank[0]);
+    x=apM(st,_v,x);
     if(Veq(x,t))BR;
     lp(r,x);}
   R Vna(r);}
@@ -1962,7 +1965,10 @@ Vt*_advspan_m(St*st,vt*self,Vt*x){Vt*v=self->bonds->value;
       p=ln();}else lp(p,t->value);
     t=t->next;}
   lp(r,Vna(p));R Vna(r);}
-Vt*_advspan_d(St*st,vt*self,Vt*x,Vt*y){R _adveach_m(st,self,vwindows(st,N,x,y));}
+Vt*_advspan_d(St*st,vt*self,Vt*x,Vt*y){Vt*_v=self->bonds->value;
+  if(_v->tag!=VERB)R st->udf;
+  vt*v=_v->val.verb;
+  Vt*r=vwindows(st,N,x,y);R eR(st,v,r,0,1);}
 Vt*_advinverse_m(St*st,vt*self,Vt*x){Vt*_v=self->bonds->value;
   if(_v->tag!=VERB)R st->udf;
   vt*v=_v->val.verb;
@@ -2057,12 +2063,12 @@ Vt*_cnjwhile_d(St*st,vt*self,Vt*x,Vt*y){Vt*v1=self->bonds->value;
 Vt*_cnjrank_m(St*st,vt*self,Vt*x){Vt*v1=self->bonds->value;
   Vt*v2=self->bonds->next->value;
   if(v1->tag!=VERB||v2->tag!=NUM)R st->udf;
-  UI rank =
+  UI rank=
       v2->val.number==INFINITY?UINT_MAX:fabs(v2->val.number);R eR(st,v1->val.verb,x,0,rank);}
 Vt*_cnjrank_d(St*st,vt*self,Vt*x,Vt*y){Vt*v1=self->bonds->value;
   Vt*v2=self->bonds->next->value;
   if(v1->tag!=VERB||v2->tag!=NUM)R st->udf;
-  UI rank =
+  UI rank=
       v2->val.number==INFINITY?UINT_MAX:fabs(v2->val.number);R tgth(st,v1->val.verb,x,y,0,0,rank,rank);}
 Vt*_cnjmonaddyad_m(St*st,vt*self,Vt*x){Vt*v=self->bonds->value;
   if(v->tag!=VERB)R st->udf;R eR(st,v->val.verb,x,0,v->val.verb->rank[0]);}
@@ -2229,27 +2235,27 @@ Nt*PPa(Pt*parser,Nt*a,enum Tkt tag){Tkt*tok;
   R N;}
 Nt*_PPnoun(Pt*parser){Nt*n;
   Nt*a=PPatom(parser);
-  if(a->tag==N_LITERAL&&a->v->tag==NUM &&(n=PPa(parser,a,T_NUM)))R n;
-  elif(a->tag==N_LITERAL&&a->v->tag==SYM &&(n=PPa(parser,a,T_NAME)))R n;
-  elif(a->tag==N_LITERAL&&a->v->tag==ARRAY &&Cap(a->v->val.array)&&(n=PPa(parser,a,T_QUOTE)))R n;R a;}
+  if(a->tag==N_LITERAL&&a->v->tag==NUM&&(n=PPa(parser,a,T_NUM)))R n;
+  elif(a->tag==N_LITERAL&&a->v->tag==SYM&&(n=PPa(parser,a,T_NAME)))R n;
+  elif(a->tag==N_LITERAL&&a->v->tag==ARRAY&&Cap(a->v->val.array)&&(n=PPa(parser,a,T_QUOTE)))R n;R a;}
 Nt*PPnoun(Pt*parser,B flat){Nt*a=flat?PPatom(parser):_PPnoun(parser);
   Tkt*tok;
-  if((tok=Plook(parser,0))&&tok->tag==T_PUNCT &&strcmp(tok->text,",:")==0){Peat(parser);
+  if((tok=Plook(parser,0))&&tok->tag==T_PUNCT&&strcmp(tok->text,",:")==0){Peat(parser);
     Lst*l=ln();
     lp(l,a);
     LOOP{a=flat?PPatom(parser):_PPnoun(parser);
       lp(l,a);
-      if(!((tok=Plook(parser,0))&&tok->tag==T_PUNCT &&strcmp(tok->text,",:")==0))BR;
+      if(!((tok=Plook(parser,0))&&tok->tag==T_PUNCT&&strcmp(tok->text,",:")==0))BR;
       Peat(parser);}
     R Nns(l);}
   R a;}
 B Nisv(Pt*parser,Nt*n){Vt*v;
   if(n->tag==N_FUN)R T;
   elif(n->tag==N_ADV||n->tag==N_CONJ||n->tag==N_PARTIAL_CONJ)R T;
-  elif(n->tag==N_FORK||n->tag==N_HOOK||n->tag==N_BOND ||n->tag==N_OVER)R T;
+  elif(n->tag==N_FORK||n->tag==N_HOOK||n->tag==N_BOND||n->tag==N_OVER)R T;
   elif(n->tag==N_LITERAL&&n->v->tag==VERB)R T;
-  elif(n->tag==N_LITERAL&&n->v->tag==SYM &&(v=Tget(parser->st->env,n->v->val.symbol))&&v->tag==VERB)R T;R F;}
-Nt*PPadv(Pt*parser,Nt*v,B*flag){Tkt*tok;
+  elif(n->tag==N_LITERAL&&n->v->tag==SYM&&(v=Tget(parser->st->env,n->v->val.symbol))&&v->tag==VERB)R T;R F;}
+Nt*PPadv(Pt*parser,Nt*v,bool*flag){Tkt*tok;
   advt*adv;
   Nt*t;
   LOOP{tok=Plook(parser,0);
@@ -2261,7 +2267,7 @@ Nt*PPadv(Pt*parser,Nt*v,B*flag){Tkt*tok;
       t->a=v;
       v=t;}else BR;}
   R v;}
-Nt*PPcnj(Pt*parser,Nt*v,B*flag){Tkt*tok;
+Nt*PPcnj(Pt*parser,Nt*v,bool*flag){Tkt*tok;
   advt*adv;
   Nt*t;
   LOOP{tok=Plook(parser,0);
@@ -2276,13 +2282,13 @@ Nt*PPcnj(Pt*parser,Nt*v,B*flag){Tkt*tok;
         t->b=PPnoun(parser,T);}
       v=t;}else BR;}
   R v;}
-B is_apply(Nt*n){R n->tag==N_LITERAL&&n->v->tag==VERB &&(strcmp(n->v->val.verb->name,"`.")==0 ||strcmp(n->v->val.verb->name,"`:")==0);}
+B is_apply(Nt*n){R n->tag==N_LITERAL&&n->v->tag==VERB&&(strcmp(n->v->val.verb->name,"`.")==0||strcmp(n->v->val.verb->name,"`:")==0);}
 B is_obverse(Nt*n){R n->tag==N_LITERAL&&n->v->tag==VERB&&strcmp(n->v->val.verb->name,"::")==0;}
 Nt*PPexpr(Pt*parser){Tkt*tmp;
   Lst*ns=ln();
-  WH(!Pstop(parser)){if(le(ns)&&(tmp=Plook(parser,0))&&tmp->tag==T_PUNCT&&strcmp(tmp->text,":")==0 &&(Plook(parser,1))){Peat(parser);R Nn1(N_FUN,PPexpr(parser));}
+  WH(!Pstop(parser)){if(le(ns)&&(tmp=Plook(parser,0))&&tmp->tag==T_PUNCT&&strcmp(tmp->text,":")==0&&(Plook(parser,1))){Peat(parser);R Nn1(N_FUN,PPexpr(parser));}
     Nt*n=PPnoun(parser,F);
-    if(le(ns)&&n->tag==N_LITERAL&&n->v->tag==SYM &&(tmp=Plook(parser,0))&&tmp->tag==T_PUNCT &&strcmp(tmp->text,":")==0){Peat(parser);R Nn2(N_BIND,n,PPexpr(parser));}
+    if(le(ns)&&n->tag==N_LITERAL&&n->v->tag==SYM&&(tmp=Plook(parser,0))&&tmp->tag==T_PUNCT&&strcmp(tmp->text,":")==0){Peat(parser);R Nn2(N_BIND,n,PPexpr(parser));}
     LOOP{B flag=F;
       n=PPadv(parser,n,&flag);
       n=PPcnj(parser,n,&flag);
@@ -2383,6 +2389,7 @@ cS VHELP =\
 ">: monadic gradeup       indices of array sorted ascending" "\n"\
 ",  monadic enlist        put x into 1-elt array" "\n"\
 ",  dyadic  join          concat x and y" "\n"\
+",. monadic enfile        ame as , enlist but with infinite rank, ,.1 2 3 is (,1),:(,2),:(,3)" "\n"\
 "#  monadic count         yield count of elts of x" "\n"\
 "#  dyadic  take          take x first elts of y (or last if x < 0)" "\n"\
 "#. monadic where         #.0 0 1 0 1 0 is 2 4" "\n"\
@@ -2405,6 +2412,7 @@ cS VHELP =\
 "{  monadic head          all elts of x except last, same as -1_" "\n"\
 "{  dyadic  bin           bin search, e.g. 1 3 5 7 9{8 9 0 yields 3 4 -1" "\n"\
 "}  monadic behead        all elts of x except first, same as 1_" "\n"\
+"[  monadic factors       compute prime factors of x" "\n"\
 "[  dyadic  left          yield x" "\n"
 "]  monadic same          yield x (i.e. identity)" "\n"
 "]  dyadic  right         yield y (i.e. right argument)" "\n"
@@ -2426,20 +2434,32 @@ cS V2HELP =\
 cS AHELP =\
 "f\"       each          >\"1 2 3 yields 2 3 4" "\n"\
 "xf\"      merge         1 2 3,\"a b c yields (1,.a),:(2,.b),:(3,.c)" "\n"\
-"\n"\
 "f\".      eachprior     -\".1 2 2 3 5 6 yields 1 0 1 2 1" "\n"\
 "xf\".     eachpriorwith 0-\".1 2 2 3 5 6 yields 1 1 0 1 2 1" "\n"\
-"\n"\
 "f/       fold          +/1 2 3 yields 6" "\n"\
 "xf/      foldwith      1+/1 2 3 yields 7" "\n"\
-"\n"\
 "f\\       scan          +/1 2 3 yields 1 3 6" "\n"\
 "xf\\      scanwith      1+\\1 2 3 yields 1 2 4 7" "\n"\
-"\n"\
-"f/.      converge      _;1/.1 2 3 yields ()" "\n"\
+"f/.      converge      1;_/.1 2 3 yields ()" "\n"\
+"f\\.      converges     1;_\\.1 2 3 yields 1 2 3,:2 3,:(,3),:()" "\n"\
+"xf/.     eachright     1-/.1 2 3 yields 0 1 2" "\n"\
+"xf\\.     eachleft      1-\\.1 2 3 yields 0 -1 -2" "\n"\
+"f\":      rank          #\":1 2 3$1 yields 3 3, #\":inf 2 3$1 yields 1 1 1,:1 1 1" "\n"\
+"xf\":     rank          1 2 3 *:\":1 1 2 3 yields (,1),:2 2,:3 3 3" "\n"\
+"f@:      laminate      1 2 3,:1 2 3@@:0 1 yields 2" "\n"\
+"n`       amend         'gw'0 3`'cross' yields 'grows'" "\n"\
+"f&.      filter        >;0&.-2!.2 yields 1 2, basically shortcut for ]#.f" "\n"\
+"f/:      span          =;' '/:'x y z' yields (,'x'),:(,'y'),:(,'z')" "\n"\
+"xf/:     stencil       3+//:!10 yields 3 6 9 12 15 18 21 24, shortcut for f\"x|:" "\n"\
+"f;.      reflex        *;.5 yields 25, 5%;.2 yields 0.4" "\n"\
 "";
 cS CHELP =\
-"f;g      bond     */;!.5 yields 120, +;1 5 yields 6, 5;- 1 yields 4" "\n"\
+"f;g      bond      */;!.5 yields 120, +;1 5 yields 6, 5;- 1 yields 4" "\n"\
+"f?.x     pick      >;5?.((2*),:<)\"3 6 yields 6 5" "\n"\
+"f?:F     while     <;5?:>0 yields 5" "\n"\
+"n?:f     repeat    5?:*;2 1 yields 32" "\n"\
+"f&:F     if        1+&:+2 yields 2" "\n"\
+"f;:F     monaddyad -;:+5 yields -5, 1-;:+5 yields 6" "\n"\
 "";
 cS IHELP =\
 "inverse of a function f is a function ~f that undoes the effect of f" "\n"\
@@ -2559,7 +2579,7 @@ I main(I argc,S*argv){GC_INIT();
     WH(*s)lp(arg,CHARS[*s++]);
     lp(args,Vna(arg));}
   Tset(st->env,"args",Vna(args));
-  if(Iin)printf("jk\t\\ to exit  \\\\ for help\n");
+  if(Iin)printf("jk\t\\\\ to exit  \\ for help\n");
   S s=N;
   if(Iin)setjmp(Icp);
   if(s){FR(s);s=N;}
@@ -2568,8 +2588,8 @@ I main(I argc,S*argv){GC_INIT();
     buffer=Bnew();
     if(Iin)putc('\t',stdout);
     if(!fgets(line,SO(line),stdin))BR;
-    if(Iin){if(strcmp(line,"\\\n")==0)BR;
-      elif(strcmp(line,"\\\\\n")==0){printf("%s",HELP);CN;}
+    if(Iin){if(strcmp(line,"\\\\\n")==0)BR;
+      elif(strcmp(line,"\\\n")==0){printf("%s",HELP);CN;}
       elif(strcmp(line,"\\0\n")==0){printf("%s",SHELP);CN;}
       elif(strcmp(line,"\\+\n")==0){printf("%s",VHELP);CN;}
       elif(strcmp(line,"\\a\n")==0){printf("%s",V2HELP);CN;}