%include "inc:util.imp"

%externalroutine openstreams(%string(255)which,defaults)
%string(255)%array d(2:7)
%integer i
  %onevent 3,4,9 %start
    selectoutput(0); printstring(event_message); newline
    %stop
  %finish
  d(i) = "" %for i = 2,1,7
  %for i = 1,1,2 %cycle
    defineparam("in1",d(2),0)
    defineparam("in2",d(4),0)
    defineparam("in3",d(6),0)
    defineparam("out1",d(3),pamnewgroup)
    defineparam("out2",d(5),0)
    defineparam("out3",d(7),0)
    processparameters(defaults) %if i=1
    processparameters(which)    %if i=2
  %repeat
  openinput(i,d(2*i)) %for i = 1,1,3
  selectinput(1)
  openoutput(i,d(2*i+1)) %for i = 1,1,3
  selectoutput(1)
%end

%include "inc:fs.imp"

%externalroutine delete(%string(255)file)
%integer x
  x = fcomm('D'<<8,file)
%end

%externalroutine rename(%string(255)old,new)
%string(255)s
%integer x
  s = old.",".new
  x = fcomm('B'<<8,s)
%end

%externalroutine copy(%string(255)from,to)
%string(255)s
%integer x
  s = from.",".to
  x = fcomm('O'<<8,s)
%end

%externalroutine permit(%string(255)file,perms)
%string(255)s
%integer x
  s = file.",".perms
  x = fcomm('E'<<8,s)
%end

%externalintegerfn filesize(%string(255)s)
%integer xno,blocks,pad,pos=1
  %integerfn h
  %integer n=0,k
    %cycle
      %result = n %if pos>length(s); pos = pos+1; k = charno(s,pos-1)-'0'
      %result = n %if k<0; n = n<<4+k
    %repeat
  %end
  s = "S".tostring(userno+'0').s.snl
  etherwrite(fsport,charno(s,1),length(s))
  length(s) = etherread(fsport,charno(s,1),255)
  %result = -1 %if charno(s,1)='-'
  xno = h; blocks = h; pad = h
  pos = fcomm('K0'+xno,"")
  %result = blocks<<9-pad
%end

%externalpredicate exists(%string(255)s)
  %falseif filesize(s)<0
  %true
%end

%externalstring(255)%fn finfo(%string(255)directory,%integer number)
%ownstring(255)s
  s = directory.","
  number = number&1023
  s = s.tostring(number>>4+'0')
  s = s.tostring(number&15+'0')
  length(s) = fcommr('F'<<8,s,charno(s,1),255)
  %result = s
%end

%externalstring(255)%fn ninfo(%string(255)file)
%string(255)s
  length(s) = fcommr('N'<<8,file,charno(s,1),255)
  %result = s
%end

%recordformat finfof(%string(23)name,%string(5)perms,%string(9)date,time,
                     %integer blocks,extents)

%externalroutine upf %alias"unpackfinfo" (%string(255)s,%record(finfof)%name r)
%integer pos=1
  %routine scan
    pos = pos+1 %while pos<=length(s) %and charno(s,pos)=' '
  %end
  %integerfn d
  %integer n=0,k
    scan
    %cycle
      %result = n %if pos>length(s); pos = pos+1; k = charno(s,pos-1)-'0'
      %result = n %if k<0 %or k>9; n = n*10+k
    %repeat
  %end
  %routine w(%string(*)%name t,%integer max)
  %integer k
    scan; t = ""
    %cycle
      %returnif pos>length(s) %or max<=0
      k = charno(s,pos); pos = pos+1; max = max-1
      %returnif k=' '
      t = t.tostring(k)
    %repeat
  %end
  r = 0
  w(r_name,23); w(r_perms,5); w(r_date,9); w(r_time,9)
  r_blocks = d; r_extents = d
%end

%externalroutine getdir(%string(31)dir,%bytename a)
%bytearray b(0:1535)
%integer n,p,x
  dir = dir.":" %unless dir=""
  dir = dir."directory"
  x=fcomm('S'<<8,dir)
  p = 1
  %cycle
    n = fcommr('X0'+x,"",b(p),1536-p)
    p = p+n
    %while p>2 %and b(p-2)=' ' %cycle
      p = p-1; b(p-1) = nl
    %repeat
  %repeatuntil n#512
  n = fcomm('K0'+x,"")
  b(0) = nl; b(p) = 0
  %while p#1 %cycle
    n = 0
    %cycle
      p = p-1; n = n+1; b(p) = b(p-1)
    %repeatuntil b(p)=nl
    b(p) = n-1
  %repeat
  n = addr(a); p = 0
  %cycle
    p = p+1; byteinteger(n) = b(p); n = n+1
  %repeatuntil b(p)=0
%end

%externalintegerfn wildness(%string(*)%name s)
%integer k,i,w=0
  %for i=1,1,length(s) %cycle
    k = charno(s,i); w = w+1 %if k='*' %or k='%'
  %repeat
  %result = w
%end

%externalpredicate Matches(%string (*) %name s, p)
! S=Subject, P=Pattern. Pattern is the one with the stars in it.
   %integer slen = 0, plen = 0

   %predicate m (%integer spos,ppos)
      %integer psym = 0,ssym = 0

      %cycle
         %if ppos=plen %start
            %true %if spos=slen
            %false
         %finish
         ppos = ppos+1; psym = charno(p,ppos)
         %exitif psym='*'
         %falseif spos=slen
         spos = spos+1; ssym = charno(s,spos)
         psym = ssym %if ssym!32=psym!32 %and 'a'<=psym!32<='z'
         %unless ssym=psym %start
            %falseunless psym='%'
         %finish
      %repeat

      %cycle
         %trueif m(spos,ppos)
         %exitif spos=slen
         spos = spos+1; ssym = charno(s,spos)
      %repeat
      %false
   %end

   slen = length(s)
   plen = length(p)
   %true %if m(0,0)
   %false
%end

