diff --git a/src/rz/factor.26 b/src/rz/factor.26 deleted file mode 100644 index 67cfe891..00000000 --- a/src/rz/factor.26 +++ /dev/null @@ -1,403 +0,0 @@ - -TITLE FACTOR - -Z=0 -A=1 -B=2 -C=3 -D=4 -E=5 -DV=5 -P=6 - -.MLLIT==1 -KL10==1 ;;KL10 RUNS SLOWER IN ACS - -TYIC==1 -TYOC==2 -INFOC==3 - -PDLL=100 - -IFE KL10, LOC 7 -TEST: TRC .+1,6 -INCR: ADDI DV,2 -RETEST: MOVE Z,C - MOVE B,D - IDIV Z,DV - DIV A,DV - CAMLE DV,A - JUMPE Z,PRIME - JUMPN B,TEST - JRST FOUND - -IFE KL10, LOC 100 -GO: MOVE P,[-PDLL,,PDL] - .OPEN TYIC,[0,,(SIXBIT /TTY/)] - JRST KILL - .OPEN TYOC,[1,,(SIXBIT /TTY/)] - JRST KILL -DECIMA: MOVEI C,10. -RADSET: MOVEM C,RADX' -RESET: PUSHJ P,PROMPT -ZBC: SETZB B,C - -LOOP: PUSHJ P,TYI - ANDI A,177 - JRST @TYIDIS(A) -TYIDIS: HUH ;^@ - HUH ;^A - HUH ;^B - HUH ;^C - HUH ;^D - HUH ;^E - HUH ;^F - KILL ;^G - HUH ;^H - HUH ;^I - HUH ;^J - HUH ;^K - HUH ;^L - HUH ;^M - HUH ;^N - HUH ;^O - HUH ;^P - HUH ;^Q - HUH ;^R - HUH ;^S - HUH ;^T - HUH ;^U - HUH ;^V - HUH ;^W - HUH ;^X - HUH ;^Y - HUH ;^Z - HUH ;^[ - HUH ;^\ - HUH ;^] - HUH ;^^ - HUH ;^_ - STM2 ;sp - HUH ;! - HUH ;" - HUH ;# - HUH ;$ - HUH ;% - HUH ;& - HUH ;' - HUH ;( - HUH ;) - TIMES ;* - PLUS ;+ - HUH ;, - MINUS ;- - HUH ;. - DIVIDE ;/ - NUMBER ;0 - NUMBER ;1 - NUMBER ;2 - NUMBER ;3 - NUMBER ;4 - NUMBER ;5 - NUMBER ;6 - NUMBER ;7 - NUMBER ;8 - NUMBER ;9 - HUH ;: - HUH ;; - HUH ;< - EQUAL ;= - HUH ;> - INFO ;? - - HUH ;@ - HUH ;A - HUH ;B - CLIST ;C - DECIMA ;D - HUH ;E - FACTOR ;F - HUH ;G - QUERY ;H - HUH ;I - HUH ;J - HUH ;K - LARGE ;L - HUH ;M - LOAD ;N - HUH ;O - HUH ;P - HUH ;Q - RADSET ;R - HUH ;S - HUH ;T - HUH ;U - HUH ;V - HUH ;W - HUH ;X - HUH ;Y - HUH ;Z - HUH ;[ - HUH ;\ - HUH ;] - POWER ;^ - HUH ;_ - HUH ;` - HUH ;a - HUH ;b - CLIST ;c - DECIMAL ;d - HUH ;e - FACTOR ;f - HUH ;g - QUERY ;h - HUH ;i - HUH ;j - HUH ;k - LARGE ;l - HUH ;m - LOAD ;n - HUH ;o - HUH ;p - HUH ;q - RADSET ;r - HUH ;s - HUH ;t - HUH ;u - HUH ;v - HUH ;w - HUH ;x - HUH ;y - HUH ;z - HUH ;{ - HUH ;| - HUH ;} - HUH ;~ - RESET ;rubout - -NUMBER: IMUL B,RADX - MUL C,RADX - ADDI D,-"0(A) - TLZE D,400000 - AOS C - ADD B,C - MOVE C,D - JRST LOOP - -INFO: PUSHJ P,INFOPN - .IOT INFOC,1 - JUMPL A,RESET - CAIE A,3 - CAIN A,14 - JRST RESET - .IOT TYOC,1 - JRST INFO+1 - -INFOPN: .CALL [ SETZ - SIXBIT /OPEN/ - ,,[0,,INFOC] - ,,[SIXBIT /DSK/] - ,,[SIXBIT /FACTOR/] - ,,[SIXBIT /ORDER/] - 400000,,[SIXBIT /.INFO./]] - JRST INFLOS -CPOPJ: POPJ P, - -INFLOS: SUB P,[1,,1] - MOVE B,[440700,,[ASCIZ \Can't open info file\]] - JRST Q3 - -QUERY: MOVE B,[440700,,[ASCIZ/elp /]] - PUSHJ P,OUT - PUSHJ P,INFOPN - .IOT TYIC,2 - PUSHJ P,CR - CAIL 2,"0 - CAILE 2,"9 - JRST Q0 - MOVE 2,[440700,,[ASCIZ/ digit/]] - JRST Q3 -Q0: .IOT INFOC,1 - JUMPL A,Q1 - CAIE 1,12 ;LINE FEED - JRST Q0 - .IOT INFOC,1 - CAME 1,2 - JRST Q0 - .IOT INFOC,1 - JUMPL 1,Q1 - CAIE 1,11 ;TAB - JRST Q0 - JRST .+2 -Q2: .IOT INFOC,1 - .IOT TYOC,1 - CAIE 1,12 ;LINE FEED? - JRST Q2 - .IOT INFOC,1 - CAIN 1,11 ;TAB? - JRST Q2+1 - JRST RESET - -CLIST: SKIPA 2,[440700,,[ASCIZ 7 RD:*;+-/^NLF =QC?7]] -Q1: MOVE 2,[440700,,[ASCIZ/ IGNORED/]] -Q3: ILDB 1,2 - JUMPE 1,RESET - .IOT 2,1 - JRST .-3 - -OUT: ILDB A,B - JUMPE A,CPOPJ - .IOT TYOC,A - JRST .-3 - -LOAD: MOVE B,M1 - MOVE C,M2 - JRST LOOP - -POWER: MOVEI Z,-1(C) - MOVE A,M2 - SETZ B, - MOVE C,A -POW1: IMUL B,A - MUL C,A - ADD B,C - MOVE C,D - SOJG Z,POW1 - JRST STM2 - -DIVIDE: MOVE A,C - MOVE B,M1 - MOVE D,M2 - IDIV B,A - DIV C,A - JRST STM2 - -TIMES: IMUL B,M2 - MOVE A,C - IMUL A,M1 - MUL C,M2 - ADD B,C - ADD B,A - TLZ B,400000 - MOVEM D,M2 - MOVEM B,M1 - JRST ZBC - -MINUS: MOVNS C - ADD C,[SETZ] - AOS B - MOVNS B -PLUS: ADD C,M2 - ADD B,M1 - TLZE C,400000 - AOS B -STM2: PUSHJ P,STM - JRST ZBC - -LARGE: MOVE B,L1' - MOVE C,L2' - JRST STM2 - -STM: MOVEM B,M1' - MOVEM C,M2' - POPJ P, - -EQUAL: MOVE A,M1 - MOVE B,M2 - PUSHJ P,SPRAB - JRST RESET - -FACTOR: SKIPN C - SKIPE B - PUSHJ P,STM - MOVE D,M1 - MOVE DV,M2 -TEST2: JUMPN D,.+3 - CAIG DV,3 - JRST SPRIME - TRNE DV,1 - JRST ODD - ASHC D,-1 - MOVEI B,2 -PRB: SETZM A - PUSHJ P,SPRAB - JRST TEST2 -ODD: MOVE A,D - MOVE C,DV - IDIVI A,3 - DIVI B,3 - JUMPN C,NO3 - MOVE D,A - MOVE DV,B - MOVEI B,3 - JRST PRB -NO3: MOVE C,D - MOVE D,DV - MOVEI DV,5 - HRRI INCR,4 - JRST RETEST - -FOUND: MOVE D,A - SETZM A - MOVE B,DV - PUSHJ P,SPRAB - MOVE C,Z - JRST RETEST - -SPRIME: MOVE C,D - MOVE D,DV - -PRIME: MOVEM C,L1 - MOVEM D,L2 - MOVE A,C - MOVE B,D - PUSHJ P,SPRAB - JRST RESET - -SPRAB: PUSHJ P,SPACE -PRAB: MOVE C,B - IDIVI A,10. - DIVI B,10. - HRLM C,(P) - SKIPN B - SKIPE A - PUSHJ P,PRAB - HLRZ A,(P) - ADDI A,"0 - JRST TYO - -SPACE: PUSH P,A - MOVEI A,40 - PUSHJ P,TYO - POP P,A - POPJ P, - -HUH: MOVEI A,"? - PUSHJ P,TYO - JRST LOOP - -PROMPT: PUSHJ P,CR - MOVEI A,"# - PUSHJ P,TYO - -CR: MOVEI A,15 - PUSHJ P,TYO - MOVEI A,12 - -TYO: .IOT TYOC,A - POPJ P, - -TYI: .IOT TYIC,A - POPJ P, - -KILL: .BREAK 16,160000 - -CONSTANTS -VARIABLES - -PDL: BLOCK PDLL+1 - -PAT: BLOCK 100 - - END GO - \ No newline at end of file diff --git a/src/rz/factor.27 b/src/rz/factor.27 new file mode 100644 index 00000000..e5837d5e --- /dev/null +++ b/src/rz/factor.27 @@ -0,0 +1,414 @@ +;Factor integers using trial division -*-MIDAS-*- + +TITLE FACTOR + +Z=0 +A=1 +B=2 +C=3 +D=4 +E=5 +DV=5 +P=6 + +.MLLIT==1 +KL10==1 ;;KL10 RUNS SLOWER IN ACS + +TYIC==1 +TYOC==2 +INFOC==3 + +PDLL==100 + +IFE KL10, LOC 7 +;This is the inner loop of the trial division code. +;CD is the number being tested. DV is the candidate factor. +;The TRC/ADDI self-modifying code means that it alternates between +;adding 2 and 4 to DV on each iteration, so the factors it tries are +;5, 7, 11, 13, 17, 19, 23, 25... i.e. it skips multiples of 2 and 3. +;(See for more about this sequence.) +TEST: TRC INCR,6 ;Complement the 2 and 4 bits in ADDI below +INCR: ADDI DV,2 ;Next candidate; modified by TEST/NO3 +RETEST: MOVE Z,C + MOVE B,D + IDIV Z,DV ;Z := Z div DV; A := Z mod DV + DIV A,DV ;A := AB div DV; B := AB mod DV + CAMLE DV,A + JUMPE Z,PRIME ;No more factors to try, so CD is prime + JUMPN B,TEST ;Not divisible by E; try the next candidate +;That's the end of the registers; the instruction below is at 20. + JRST FOUND ;Found a factor (but CD may still be composite) + +;Entry point +IFE KL10, LOC 100 +GO: MOVE P,[-PDLL,,PDL] + .OPEN TYIC,[.UAI,,'TTY] + JRST KILL + .OPEN TYOC,[.UAO,,'TTY] + JRST KILL +DECIMA: MOVEI C,10. ;Base 10 input by default +RADSET: MOVEM C,RADX' +RESET: PUSHJ P,PROMPT +ZBC: SETZB B,C ;BC holds current value; clear it + +LOOP: PUSHJ P,TYI ;Read key and dispatch appropriately + ANDI A,177 + JRST @TYIDIS(A) +TYIDIS: HUH ;^@ + HUH ;^A + HUH ;^B + HUH ;^C + HUH ;^D + HUH ;^E + HUH ;^F + KILL ;^G + HUH ;^H + HUH ;^I + HUH ;^J + HUH ;^K + HUH ;^L + HUH ;^M + HUH ;^N + HUH ;^O + HUH ;^P + HUH ;^Q + HUH ;^R + HUH ;^S + HUH ;^T + HUH ;^U + HUH ;^V + HUH ;^W + HUH ;^X + HUH ;^Y + HUH ;^Z + HUH ;^[ + HUH ;^\ + HUH ;^] + HUH ;^^ + HUH ;^_ + STM2 ;sp + HUH ;! + HUH ;" + HUH ;# + HUH ;$ + HUH ;% + HUH ;& + HUH ;' + HUH ;( + HUH ;) + TIMES ;* + PLUS ;+ + HUH ;, + MINUS ;- + HUH ;. + DIVIDE ;/ + NUMBER ;0 + NUMBER ;1 + NUMBER ;2 + NUMBER ;3 + NUMBER ;4 + NUMBER ;5 + NUMBER ;6 + NUMBER ;7 + NUMBER ;8 + NUMBER ;9 + HUH ;: + HUH ;; + HUH ;< + EQUAL ;= + HUH ;> + INFO ;? + + HUH ;@ + HUH ;A + HUH ;B + CLIST ;C + DECIMA ;D + HUH ;E + FACTOR ;F + HUH ;G + QUERY ;H + HUH ;I + HUH ;J + HUH ;K + LARGE ;L + HUH ;M + LOAD ;N + HUH ;O + HUH ;P + HUH ;Q + RADSET ;R + HUH ;S + HUH ;T + HUH ;U + HUH ;V + HUH ;W + HUH ;X + HUH ;Y + HUH ;Z + HUH ;[ + HUH ;\ + HUH ;] + POWER ;^ + HUH ;_ + HUH ;` + HUH ;a + HUH ;b + CLIST ;c + DECIMAL ;d + HUH ;e + FACTOR ;f + HUH ;g + QUERY ;h + HUH ;i + HUH ;j + HUH ;k + LARGE ;l + HUH ;m + LOAD ;n + HUH ;o + HUH ;p + HUH ;q + RADSET ;r + HUH ;s + HUH ;t + HUH ;u + HUH ;v + HUH ;w + HUH ;x + HUH ;y + HUH ;z + HUH ;{ + HUH ;| + HUH ;} + HUH ;~ + RESET ;rubout + +NUMBER: IMUL B,RADX ;A digit - add it to BC + MUL C,RADX + ADDI D,-"0(A) + TLZE D,400000 + AOS C + ADD B,C + MOVE C,D + JRST LOOP + +INFO: PUSHJ P,INFOPN ;Show the whole info file + .IOT INFOC,1 + JUMPL A,RESET + CAIE A,3 + CAIN A,14 + JRST RESET + .IOT TYOC,1 + JRST INFO+1 + +INFOPN: .CALL [ SETZ ;Open the info file + SIXBIT /OPEN/ + ,,[0,,INFOC] + ,,[SIXBIT /DSK/] + ,,[SIXBIT /FACTOR/] + ,,[SIXBIT /ORDER/] + 400000,,[SIXBIT /.INFO./]] + JRST INFLOS +CPOPJ: POPJ P, + +INFLOS: SUB P,[1,,1] ;Info file can't be opened + MOVE B,[440700,,[ASCIZ \Can't open info file\]] + JRST Q3 + +QUERY: MOVE B,[440700,,[ASCIZ/elp /]] ;Look up a key in the info file + PUSHJ P,OUT + PUSHJ P,INFOPN + .IOT TYIC,B ;Get a key + PUSHJ P,CR + CAIL B,"0 ;Digit? + CAILE B,"9 + JRST Q0 + MOVE B,[440700,,[ASCIZ/ digit/]] + JRST Q3 +Q0: .IOT INFOC,A ;Skip chars until LF + JUMPL A,Q1 + CAIE A,12 + JRST Q0 + .IOT INFOC,A ;Read first char + CAME A,B ;Is the key we're after? + JRST Q0 ;No - try next line + .IOT INFOC,A ;Read second char + JUMPL A,Q1 + CAIE A,11 ;Is it tab? + JRST Q0 ;No - try next line + JRST .+2 ;Found it! +Q2: .IOT INFOC,A ;Copy from file to tty until LF + .IOT TYOC,A + CAIE A,12 ;LF + JRST Q2 + .IOT INFOC,A ;Does next line start with tab? + CAIN 1,11 + JRST Q2+1 ;Yes - print it too + JRST RESET + +CLIST: ;List all keys we know about + SKIPA B,[440700,,[ASCIZ 7 RD:*;+-/^NLF =QC?7]] +Q1: ;Key not found in info file + MOVE B,[440700,,[ASCIZ/ IGNORED/]] +Q3: ILDB A,B ;Print the ASCIZ string in B and RESET + JUMPE A,RESET + .IOT TYOC,A + JRST Q3 + +OUT: ILDB A,B ;Print the ASCIZ string in B and return + JUMPE A,CPOPJ + .IOT TYOC,A + JRST .-3 + +LOAD: MOVE B,M1 + MOVE C,M2 + JRST LOOP + +POWER: MOVEI Z,-1(C) + MOVE A,M2 + SETZ B, + MOVE C,A +POW1: IMUL B,A + MUL C,A + ADD B,C + MOVE C,D + SOJG Z,POW1 + JRST STM2 + +DIVIDE: MOVE A,C + MOVE B,M1 + MOVE D,M2 + IDIV B,A + DIV C,A + JRST STM2 + +TIMES: IMUL B,M2 + MOVE A,C + IMUL A,M1 + MUL C,M2 + ADD B,C + ADD B,A + TLZ B,400000 + MOVEM D,M2 + MOVEM B,M1 + JRST ZBC + +MINUS: MOVNS C + ADD C,[SETZ] + AOS B + MOVNS B +PLUS: ADD C,M2 + ADD B,M1 + TLZE C,400000 + AOS B +STM2: PUSHJ P,STM + JRST ZBC + +LARGE: MOVE B,L1' + MOVE C,L2' + JRST STM2 + +STM: MOVEM B,M1' + MOVEM C,M2' + POPJ P, + +EQUAL: MOVE A,M1 + MOVE B,M2 + PUSHJ P,SPRAB + JRST RESET + +FACTOR: SKIPN C ;Factor arg in BC + SKIPE B + PUSHJ P,STM ;Arg isn't 0; set current value from arg + MOVE D,M1 ;Put number being factored into DE + MOVE E,M2 +TEST2: JUMPN D,.+3 ;Is DE small? + CAIG E,3 + JRST SPRIME ; DE < 3 - no need to factor + TRNE E,1 ;Is DE divisible by 2? + JRST ODD ; No + ASHC D,-1 ;Take out a factor of 2 + MOVEI B,2 +PRB: SETZM A + PUSHJ P,SPRAB ;Print factor + JRST TEST2 ;... and factor again + +ODD: MOVE A,D ;Is DE divisible by 3? + MOVE C,E + IDIVI A,3 + DIVI B,3 + JUMPN C,NO3 ; No + MOVE D,A ;Take out a factor of 3 + MOVE E,B + MOVEI B,3 + JRST PRB ;Print and factor again + +NO3: MOVE C,D ;Not divisible by 2 or 3: start trial division + MOVE D,E + MOVEI DV,5 ;First factor to try + HRRI INCR,4 ;Set next trial division step size + JRST RETEST ;... and start the inner loop + +FOUND: MOVE D,A ;Trial division found a factor + SETZM A + MOVE B,DV + PUSHJ P,SPRAB ;Print it + MOVE C,Z + JRST RETEST ;... and keep looking (starting from same DV) + +SPRIME: MOVE C,D ;DE was a trivial prime to start with + MOVE D,E +PRIME: MOVEM C,L1 ;Found the largest prime factor; save it + MOVEM D,L2 + MOVE A,C + MOVE B,D + PUSHJ P,SPRAB ;Print it + JRST RESET ;Done! + +SPRAB: PUSHJ P,SPACE ;Print a space, then... +PRAB: MOVE C,B ;Print number in AB in decimal + IDIVI A,10. + DIVI B,10. + HRLM C,(P) + SKIPN B + SKIPE A + PUSHJ P,PRAB + HLRZ A,(P) + ADDI A,"0 + JRST TYO + +SPACE: PUSH P,A ;Print space + MOVEI A,40 + PUSHJ P,TYO + POP P,A + POPJ P, + +HUH: MOVEI A,"? ;Print ? + PUSHJ P,TYO + JRST LOOP + +PROMPT: PUSHJ P,CR ;Print prompt + MOVEI A,"# + PUSHJ P,TYO + +CR: MOVEI A,15 ;Print CRLF - CR + PUSHJ P,TYO + MOVEI A,12 ;LF + +TYO: .IOT TYOC,A ;Print character in A + POPJ P, + +TYI: .IOT TYIC,A ;Read character into A + POPJ P, + +KILL: .BREAK 16,160000 + +CONSTANTS +VARIABLES + +PDL: BLOCK PDLL+1 + +PAT: BLOCK 100 + + END GO