;~1,$i&\n / program fopen .mcall fdop$r,fdat$r,exst$s struct bfdb ;buffered fdb's bfdb=-32. member b.lh,b.lhl[4],b.max[1],b.cur[1] member b.type,b.dirty,b.stat,b.seek[4] member b.stype,b.ssize,b.sracc member b.io,b.prec,b.pos,b.check end-struct b.peek=b.lhl struct l.lru ;Lru lists member l.blk[4],l.dirty,l.data[512.] end-struct ;+ ; This is the user interface. It finds an available lun ; allocates an fdb, initializes it, and calls bopen to do ; all the real work. ;- auto i,ptr extern $$err,io.luns,stdin,stdout function fopen[name,type,class] ;+ ; char *name,*type,*class; ; returns an ioptr if successful or null (0) ; if an error occurs, $$err is set to the reason ; to be retreived by ferror() ; name, type, and class are passed onto bopen. ;- loop for i = 0 to #nluns-1 if .io.luns[i] = 0 br gotit fi next i error["Can't open another file"] exit[4] gotit: r4 := alloc[#$$fdsz] clr (r4) moveb[r4,,#$$fdsz-1] ;clear it all mov r4,ptr sub #b.lh,r4 ;set addr to fdb r1 := i + 1 movb r1,f.lun(r4) fdat$r r4,#r.var,#fd.cr b.lh(r4) := 0 movb 4,b.max(r4) b.stat(r4) := 1 b.prec(r4) := 0 b.check(r4) := 12345 $$err := bopen[r4,name,type,class] if $$err ne 1 free[ptr] ret 0 fi .io.luns[i] := r4 ret r4 function fclose[fd] r4 := fd movb f.lun(r4),r1 mov r1,r3 add r3,r3 add #io.luns-2,r3 ;compute offset into table if r1 gt 0 and r1 le #nluns and (r3) = r4 (r3) := 0 bclose[r4] ret else error["Bad ioptr to fclose"] exit[4] fi function ferror[ioptr] mov $$err,r0 ret .end