!REGION: procedures for accessing parts (regions) of files %include "inc:util.imp" %include "inc:fs.imp" %bytemap put(%integer k,%bytename b) b = k; %result == b[1] %end %byteintegermap putnum(%integer n,%bytename b) b == putnum(n>>4,b) %and n = n&15 %if n>=64 %result == put(n+'0',b) %end %routine add(%integer x,%string(*)%name s) s = s.tostring(x) %end %routine addnum(%integer x,%string(*)%name s) addnum(x>>4,s) %and x = x&15 %if x>=64 add(x+'0',s) %end %byteintegermap num(%bytename b,%integername x) %integer k x = 0 %cycle k = b-'0'; b == b[1] %result == b %if k<0 x = x<<4+k %repeat %end %routine move(%integer bytes,%bytename from,to) *sub.l #1,d0 *swap d0 a:*swap d0 b:*move.b (a0)+,(a1)+ *dbra d0,b *swap d0 *dbra d0,a %end ! ACCESS FILE ! Opens the file and returns in SIZE the number of bytes in the file, ! and in REF a token (actually the filestore transaction number) which ! must be passed to DEACCESS FILE, READ REGION, and WRITE REGION. ! MODE=0: Read-only, MODE=1: Read-modify. %externalroutine access file(%string(255)filename,%integer mode, %integername ref,size) %string(255)s="" %integer blocks %bytename b mode = 'A'-'S' %unless mode=0 add(mode+'S',s); add(userno+'0',s); s = s.filename; add(nl,s) b == charno(s,1) etherwrite(lsap,b,length(s)) length(s) = etherread(lsap,b,255) %signal 3,3,b[1]-'0',substring(s,3,length(s)-1) %if b='-' b == num(b,ref) b == num(b,blocks) b == num(b,size) size = blocks<<9-size %end ! DEACCESS FILE ! Just closes the file %externalroutine deaccess file(%integer ref) %string(255)s="" %bytename b add('K',s); add(ref+'0',s); add(nl,s) b == charno(s,1) etherwrite(lsap,b,length(s)) length(s) = etherread(lsap,b,255) %end ! READ REGION ! Reads BYTES bytes from the file specified by REF into store at BUFFER, ! starting with byte BYTE of the file (BYTE=0 means beginning of file). %externalroutine read region(%integer ref,byte,bytes,%bytename buffer) %string(31)s="" %bytearray temp(1:516) %bytename b,p %integer lo,hi,i,count %returnif bytes<=0 b == temp(1) lo = byte>>9; hi = (byte+bytes-1)>>9 add('U',s); add(ref+'0',s); addnum(lo,s); add(nl,s); !Set to required block etherwrite(lsap,charno(s,1),length(s)) i = etherread(lsap,b,515) ->shit %if b='-' s = "" add('X',s); add(ref+'0',s) addnum(hi-lo+1,s); !Multi-block read! add(nl,s) etherwrite(lsap,charno(s,1),length(s)) count = 512-byte&511 p == b[byte&511+3] %cycle i = etherread(lsap,b,515) %if b='-' %start shit: lo = b[1]-'0'; b[1] = i-3 %signal 3,4,lo,string(addr(b)+1) %finish count = bytes %if byteshi %signal 3,4,0,"Read region: internal error" %unless lo>=hi %and bytes<=0 %end %externalroutine write region(%integer ref,byte,bytes,%bytename buffer) %bytearray temp(1:532) %integer count,block,i %bytename b,b0 b0 == temp(1) count = 512; count = bytes %if bytes>9 b == put('W',b0) b == put(ref+'0',b) b == putnum(block,b) b == put(',',b) b == putnum(count,b) b == put(nl,b) %if byte&511#0 %start; !First block not aligned readregion(ref,block<<9,512,b) count = count-byte&511 move(count,buffer,b[byte&511]) bytes = bytes+byte&511 %else move(count,buffer,b) %finish %cycle etherwrite(lsap,temp(1),addr(b)-addr(b0)+count) i = etherread(lsap,b0,255) %if b0='-' %start count = b0[1]-'0'; b0[1] = i-3 %signal 3,4,count,string(addr(b0)+1) %finish buffer == buffer[count] bytes = bytes-count %exitif bytes<=0 count = 512; count = bytes %if bytes