diff --git a/Makefile b/Makefile index 307bd1bc..d0ff0430 100644 --- a/Makefile +++ b/Makefile @@ -26,7 +26,8 @@ SRC = syseng sysen1 sysen2 sysen3 sysnet kshack dragon channa \ draw wl taa tj6 budd sharem ucode rvb kldcp math as imsrc gls demo \ macsym lmcons dmcg hack hibou agb gt40 rug maeda ms kle aap common \ fonts zork 11logo kmp info aplogo bkph bbn pdp11 chsncp sca music1 \ - moon teach ken lmio1 llogo chsgtv clib sys3 lmio turnip mits_s rab + moon teach ken lmio1 llogo chsgtv clib sys3 lmio turnip mits_s rab \ + stan_k DOC = info _info_ sysdoc sysnet syshst kshack _teco_ emacs emacs1 c kcc \ chprog sail draw wl pc tj6 share _glpr_ _xgpr_ inquir mudman system \ xfont maxout ucode moon acount alan channa fonts games graphs humor \ diff --git a/build/misc.tcl b/build/misc.tcl index 521fbf34..7ba1d830 100644 --- a/build/misc.tcl +++ b/build/misc.tcl @@ -497,6 +497,11 @@ respond "*" ":midas;324 /t dsk0:.;@ mlife_rwg;mlife\r" respond "with ^C" "TS==0\r\003" expect ":KILL" +# 340D +respond "*" ":midas stan.k;mod11 bin_340d\r" +expect ":KILL" +respond "*" ":link sys1;ts 340d, stan.k; mod11 bin\r" + # TV-munching square. respond "*" ":midas sys2;ts munch_sysen2;munch\r" expect ":KILL" diff --git a/doc/programs.md b/doc/programs.md index 320424e7..b405a98c 100644 --- a/doc/programs.md +++ b/doc/programs.md @@ -5,6 +5,7 @@ - 11SIM, PDP-11 emulator. - 11STNK, PDP-11 linker. - 20XCVT, convert TOPS-20 CSAVE file to PDUMP. +- 340D, Datapoint emulator for 340 display. - @, cross reference generation tool. - ACNVRT/MCNVRT/PCNVRT/UCNVRT, asciizer and binarator. - ACCLNK, sets com-link accept bit for specified TTY. diff --git a/src/stan_k/340d.1 b/src/stan_k/340d.1 new file mode 100644 index 00000000..84dfd33b --- /dev/null +++ b/src/stan_k/340d.1 @@ -0,0 +1,316 @@ +title 340d - Datapoint emulator for 340 display. + +;Written in 2018 from a vague description. We do know that in 1974, +;there was a link from SYS1; TS 340D to STAN.K; MOD11 BIN. We also +;know some 340D parameters from TCTYP. According to Stan Kugell, the +;input could be from the Stanford keyboard or from the console TTY. +;The original implementation ran on the PDP-6. + +;Possible improvements: +; - Super image mode for TTY input. +; - Double buffering. +; - Display missing characters using incremental mode. +; - Handle STY input from interrupt. +; - Have separate display lists per line, and only update one line at a time. +; - Run on PDP-6. + +width=70. ;Should be 117 +height=40 ;Should be 50 + +a=1 +b=2 +c=3 +d=4 +e=5 +x=10 +y=11 +p=17 + +styi==1 +styo==2 +ttyi==3 + +dstop==003000 +point==020000 +chara==060000 +vecto==100000 +verti==200000 + +loc 42 + tsint + +loc 100 + +start: move p,[-pdllen,,pdl-1] + + setzb x,y ;Initial cursor position. + + .open styo,[.uio,,'STY] + .lose + .open styi,[.uii,,'STY] + .lose + .open ttyi,[.uii,,'TTY] + .lose + .call [ setz + sixbit /cnsget/ + movei styi + movem a ? movem a ? movem a + setzm b ] + .lose + .call [ setz + sixbit /cnsset/ + movei styi + [height] ? [width] ? [%tndp] ? b + ;These bits for 340D are copied from TCTYP. + setz [%TOMVU+%TOMVB+%TOERS+%TOLWR,,%TPORS] ] + .lose + + ;Get the 340 started. + hrlzi a,dstop + movem a,dlist + .dstart [-dlen,,dlist-1] + .lose + + ;Enable interrupts for I/O error and input channels. + .suset [.smask,,[%piioc]] + .suset [.smsk2,,[<0_styi>+<1_ttyi>]] ;STY input disabled for now. + .suset [.rioc+styi,,a] + ldb a,[$tiidx,,a] + movem a,tty + + .iot styo,[^Z] ;Get a HACTRN. + +loop: .iot styi,a ;Couldn't make input from STY work in interrupt. + pushj p,styout ;Loop here instead. + jrst loop + +die: .logout 1, ;Orderly exit. + +;Interrupt handler. +tsint: 0 + 0 + push p,a ;Better save accumulators as long + push p,b ;as there is a main loop. + push p,c + push p,d + move b,tsint + jumpn b,ioint ;Bit 0 means I/O channel interrupt. + trne b,%piioc + jrst iocerr + jrst dismis + +iocerr: .value ;Not prepared to handle I/O errors. + +ioint: trne b,1_ttyi ;TTY input. + pushj p,[.iot ttyi,b ? .iot styo,b ? popj p,] + trne b,1_styi ;STY input. Will not happen for now. + pushj p,styin ;Handled from main loop. +dismis: .suset [.sadf2,,[<1_styi>+<1_ttyi>]] + pop p,d + pop p,c + pop p,b + pop p,a + .dismis tsint+1 + +;Handle input from STY. Read character and put in screen. +styin: .iot styi,a + pushj p,styout + .status styi,a + trnn a,2000 ;Loop if the buffer isn't empty. + jrst styin + popj p, + +;Output character in A to STY. Interpret Datapoint codes. +styout: move b,y + lsh b,7 + add b,x ;B gets character offset in screen. + xct tab(a) + skipge x ;Ensure cursor position inside bounds. + setz x, + cail x,width + movei x,width-1 + skipge y + setz y, + cail y,height ;Scroll if cursor below last line. + pushj p,scroll + + movei a,screen ;Render a display list from screen contents. + move c,[442200,,dlist] + movei d,point+17+<5_4> ;Set intentity and scale, go to point mode. + idpb d,c + movei d,chara+verti+1000. ;Set Y, go to character mode. + idpb d,c + + tlnn c,770000 ;Convert from 18-bit byte pointer to 6-bit. + tlca c,002400 + hrli c,220600 + + setzm mode ;Start out with upper case character set. + +prscr: pushj p,prlin ;Render one line. + movei b,34 ;Insert CR LF in display list. + idpb b,c + movei b,33 + idpb b,c + addi a,200 ;Go to next line. + caie a,screen+200*height ;Unless done. + jrst prscr + + movei b,37 ;Escape from character mode. + idpb b,c + tlnn c,200000 ;Convert from 6-bit byte pointer to 18-bit. + jrst [hrli c,002200 ? jrst .+2] + hrli c,222200 + + pushj p,cursor ;Draw cursor. + + movei b,dstop ;End with a 340 stop instruction. + idpb b,c + popj p, + +;Print line. +prlin: move b,a + move d,a + subi d,screen + lsh d,-7 + movn d,length(d) ;Get negative of line length. + cain d,0 + popj p, ;Empty line. + hrl b,d ;Make AOBJN pointer for line. +prlin0: move d,(b) + xct shift(d) ;Insert shift character if necessary. + move d,char(d) ;Convert ASCII to 340 character code. + idpb d,c + aobjn b,prlin0 + popj p, + +;Insert character in A in screen memory. +insert: movem a,screen(b) + addi x,1 ;Advance cursor. + camle x,length(y) + movem x,length(y) ;Update number of characters in line. + popj p, + +;Shift in. +shin: skipn mode + popj p, + setzm mode + movei e,35 + idpb e,c + popj p, + +;Shift out. +shout: skipe mode + popj p, + setom mode + movei e,36 + idpb e,c + popj p, + +;Scroll entire screen. +scroll: move a,[screen+200,,screen] ;Copy screen contents one line up. + blt a,screen+200*height-200-1 + move a,[length+1,,length] ;Copy line lengths one line up. + blt a,length+height-2 + setzm length+height-1 ;Clear last line. + subi y,1 ;Move cursor back up. + popj p, + +;Erase to end of line. +eralin: movem x,length(y) + popj p, + +;Erase to end of screen. +erascr: pushj p,eralin + move a,y +erasc0: addi a,1 + cain a,height + popj p, + setzm length(a) + jrst erasc0 + +;Draw cursor. +cursor: movei b,point+10 ;Low intensity, go to point mode. + idpb b,c + move b,y + imuli b,12.*2 + movns b + addi b,1000.-3 + addi b,verti+point ;Set Y position. + idpb b,c + + jumpe x,curso0 ;Cursor in column 0 is different. + + move b,x + imuli b,7.*2 + addi b,vecto-2 ;Set X position, go to vector mode. + idpb b,c + movei b,<6.>+<1_16.> ;Draw box for cursor. + idpb b,c + movei b,<9._8.>+<1_16.> + idpb b,c + movei b,<200+6.>+<1_16.> + idpb b,c + movei b,<<200+9>_8.>+<3_16.> ;Escape to parameter mode. + idpb b,c + popj p, + +curso0: movei b,vecto ;Go to vector mode. + idpb b,c + movei b,5+<1_16.> + idpb b,c + movei b,<9._8.>+<1_16.> + idpb b,c + movei b,<200+5>+<3_16.> + idpb b,c + popj p, + +;Table for interpreting Datapoint codes. +tab: repeat 40,jfcl ;Most control codes ignored. + repeat 200-40,pushj p,insert ;Printable characters go into screen. +ifn .-tab-200,.err The tab table is wrong. +ZZZ=. +loc tab+^G ? jfcl +loc tab+^H ? subi x,1 +loc tab+^I ? pushj p,[addi x,8 ? andcmi x,7 ? popj p,] +loc tab+^J ? addi y,1 +loc tab+^K ? .value ;Not implemented: go down without scrolling. +loc tab+^M ? setz x, +loc tab+30 ? addi x,1 +loc tab+31 ? subi x,1 +loc tab+32 ? subi y,1 +loc tab+34 ? pushj p,[setz x, ? movei y,height-1 ? popj p,] +loc tab+35 ? setzb x,y +loc tab+36 ? pushj p,eralin +loc tab+37 ? pushj p,erascr +loc tab+40 ? pushj p,[movem a,screen(b) ? addi x,1 ? popj p,] +loc tab+177 ? jfcl +loc ZZZ + +;Table for converting from ASCII to 340 character codes. +char: repeat 40,0 ;Control characters + repeat 40,.rpcnt+40 ;Space to ? + 00 ;@ + repeat 32,.rpcnt+1 ;A to Z + repeat 6,00 ;[ to ` + repeat 32,.rpcnt+1 ;a to z + repeat 5,00 ;{ to Rubout +ifn .-char-200,.err The char table is wrong. + +;Table for shifting character set. +shift: repeat 65.,jfcl + repeat 26.,pushj p,shin + repeat 6,jfcl + repeat 26.,pushj p,shout + repeat 5,jfcl +ifn .-shift-200,.error The shift table is wrong. + +tty: 0 +mode: 0 ;0 means upper case, -1 means lower case. +screen: block 200*height ;Characters on screen. +length: block height ;Number of characters on each line. + +.vector pdl(pdllen==100) +.vector dlist(dlen==4000) ;Display list. + +end start