/ / PDP-11 C. / Stdio. / / Flush. / .globl fflush .globl _flush .globl _put / / This gets written out for 0 byte / writes in normal mode. / A bug in RSX makes all this necessary. / blank: .ascii " " .even / / fflush(ioptr); / FILE *ioptr; / fflush: jsr r0,_save /Get a stack frame. mov 12(r5),r4 /Grab ioptr. call _ckiov bit $VF_OUT,(r4) /Output IOV. beq 0f /Br if not. bit $VF_UBF,(r4) /Unbuffered IOV. bne 0f /Br if yes call _flush /Do it. 0: jmp _ret /Done. / / This routine flushes the line / buffer in the IOV. / V_R0(r4) is nbytes. / V_R1(r4) is a buffer pointer. / _flush: mov r0,-(sp) /This save may mov r1,-(sp) /No be necessary. mov V_RBUF(r4),r0 /Buffer address mov V_R0(r4),r1 /Byte count beq 0f /Duck out if zero call _put /Out it goes. mov r0,V_R1(r4) /Reset buffer pointer. clr V_R0(r4) /Clear byte count. 0: mov (sp)+,r1 /Return mov (sp)+,r0 / return / / / Put a record. / r0 = address / r1 = byte count. / r4 = iov. / / This routine does newline checking. / The "u" option implies the "n" option / so binary works as advertised. / _put: mov r0,-(sp) /Save the world. mov r1,-(sp) / mov r2,-(sp) / mov r3,-(sp) / mov r0,r2 /Point just past the add r1,r2 /End of the record. / / Record devices. / bit $VF_REC,(r4) /Record device? beq 2f /No bit $VF_NOS,(r4) /No newlines? beq 0f /No clr r2 /Set no slew byte. mov $IO.WAL,r3 /IO.WAL used for the write. br 1f / 0: mov $IO.WVB,r3 /Set default IO.WVB. cmpb -(r2),$12 /Newline bne 0f /No mov $' ,r2 /Set normal slew dec r1 /Remove from byte count bne 1f / mov $blank,r0 /Bug in RSX. inc r1 / br 1f / 0: mov $'$,r2 /Prompt slew. 1: clr -(sp) /Do the I/O. clr -(sp) / clr -(sp) / mov r2,-(sp) /Slew mov r1,-(sp) /Nbytes. mov r0,-(sp) /Address. mov r3,r0 /Do call _qiow /Write. bcs 3f /Error br 4f /All OK. / / Block devices. / 2: bit $VF_NOS,(r4) /No newlines? bne 0f /Yes cmpb -(r2),$12 /Delete trailing newline. bne 0f /Not a newline dec r1 / 0: cmp r1,V_RSIZ(r4) /If this record is longer than blos 0f /The longest record already out mov r1,V_RSIZ(r4) /Reset the size 0: mov r1,-(sp) /Save updated byte count. mov r1,r0 /Put out RCW. call outb / mov (sp),r0 / swab r0 / call outb / mov (sp),r2 /Byte count mov 10(sp),r3 /Address 0: dec r2 /Put out the record bmi 0f / movb (r3)+,r0 / call outb / br 0b / 0: bit $1,(sp)+ /Is this odd length record beq 1f /No clr r0 /Put out NUL. call outb / / / Update EOF location. / 1: cmp V_RBLK(r4),V_EFBK(r4) /EOF high lbn. bhi 0f /Must fix blo 4f /Ok cmp V_RBLK+2(r4),V_EFBK+2(r4) /EOF low lbn. bhi 0f /Must fix blo 4f /Ok cmp V_RBYT(r4),V_FFBY(r4) /EOF byte number. blos 4f /Ok 0: mov V_RBLK(r4),V_EFBK(r4) /Update mov V_RBLK+2(r4),V_EFBK+2(r4) /EOF mov V_RBYT(r4),V_FFBY(r4) /Location. br 4f / 3: bis $VF_ERR,(r4) /Set error flag. 4: mov (sp)+,r3 /Return mov (sp)+,r2 / mov (sp)+,r1 / mov (sp)+,r0 / return / / / Put out a byte to a block buffered / device. / r0 = byte. / Uses r0, r1 / outb: mov V_RBYT(r4),r1 /Get byte location add V_BBUF(r4),r1 / movb r0,(r1) /Save byte inc V_RBYT(r4) /Fix byte number. cmp V_RBYT(r4),$512./Is the block full? blo 0f /No call _wvb /Yes, write it out add $1,V_RBLK+2(r4) /Fix adc V_RBLK(r4) /Blocknumber clr V_RBYT(r4) /And start at byte 0. 0: return /Return