{
File name : fptdiag.mc
Author : Gunawan Santosa
Created : 17-Dec-84 13:00:40
=========================================================================
FPTDIAG.MC
=========================================================================
This program test the floating point circuit board for Xerox
1100 series workstation.
Registers :
REGA: Mostly used for scratch pad
REGB: Mostly used for scratch pad
RESM: To store MS byte of result
RESL: To store LS byte of result
REFREG: To store expected value
STATUS: To store status of floating point chip
FLTCNT: To store total fault count
At DONE :
If FLTCNT = 0, no error, else errors have been detected.
First, perform A+B, there are 4 cases.
In this test, we test input and output buses of the floating point chip,
F2 input line, and status line.
}
START: Q ← 0, c1; {Load Q with 0}
PPort ← Q, c2; {set port direction to read status}
COUNTER ← n04, c3; {There are 4 cases for A+B}
FLTCNT ← n00, c1; {Initialize fault counter}
LOP1: Xbus ← COUNTER LRot0, XDisp, c2; {Check which case}
DISP4[ADDAB, 0C], c3;
{First case, A+B, where A=AAAAAAAA, B=00000000}
CASE1: REGA ← n00, c1, at[0C,10,ADDAB];
UREGA ← REGA, c2; {Load UREGA with 0000}
REGA ← nAA, c3; {Load REGA with 00AA}
REGA ← (REGA LRot8) or REGA, c1; {REGA contains AAAA}
UREGADD ← REGA, c2; {UREGADD contains AAAA}
GOTO[APLB], c3; {Perform A+B}
{Second case, A+B, where A=55555555, B=00000000}
CASE2: REGA ← n55, c1, at[0F,10,ADDAB];
REGA ← (REGA LRot8) or REGA, c2; {REGA contains 5555}
UREGADD ← REGA, GOTO[APLB], c3; {UREGADD contains 5555}
{Third case, A+B, where A=00000000, B=55555555}
CASE3: UREGA ← REGA, c1, at[0E,10,ADDAB];
REGA ← n00, c2; {UREGA contains 5555}
UREGADD ← REGA, GOTO[APLB], c3; {UREGADD contains 0000}
{Fourth case, A+B, where A=00000000, B=AAAAAAAA}
CASE4: REGA ← nAA, c1, at[0D,10,ADDAB];
REGA ← (REGA LRot8) or REGA, c2; {REGA contains AAAA}
UREGA ← REGA, c3; {UREGA contains AAAA}
{Perform A+B}
APLB: FloatMode, FloatFLOW, c1; {load flow thru mode}
FloatAB ← UREGA, c2; {load AB}
FloatAB ← UREGA, c3;
FloatA ← UREGADD, FLPlus, c1; {load A}
FloatA ← UREGADD, c2; {and perform A+B}
FloatNop, c3;
FloatNop, c1;
Noop, c2;
Noop, c3;
Noop, c1;
FloatUnloadS, Float.M, c2; {unload MS word}
FloatUnloadS, Float.L, c3; {unload LS word}
STATUS ← PPort, c1; {read status}
RESM ← FloatResult, c2; {store MS word in RESM}
RESL ← FloatResult, c3; {LS word in RESL}
Noop, c1;
Xbus ← COUNTER LRot0, XDisp, c2; {Calculate expected values}
DISP4[ADDRS, 0C], c3;
{Expected value for case 1}
CS1: REFREG ← nAA, c1, at[0C,10,ADDRS];
REFREG ← (REFREG LRot8) or REFREG, GOTO[MERGE], c2; {Must be AAAAAAAA}
{Expected value for case 2}
CS2: REFREG ← n55, c1, at[0F,10,ADDRS];
REFREG ← (REFREG LRot8) or REFREG, GOTO[MERGE], c2; {Must be 55555555}
{Expected value for case 3}
CS3: Noop, c1, at[0E,10,ADDRS];
GOTO[MERGE], c2; {Must be 55555555}
{Expected value for case 4}
CS4: REFREG ← nAA, c1,at[0D,10,ADDRS];
REFREG ← (REFREG LRot8) or REFREG, GOTO[MERGE], c2; {Must be AAAAAAAAA}
{Test the result}
MERGE: RESM ← RESM - REFREG, ZeroBr, c3; {Test MS byte}
RESL ← RESL - REFREG, ZeroBr, BRANCH[FLS1,TRUE1], c1; {Test LS byte}
FLS1: FLTCNT ← FLTCNT + n01, CANCELBR[$], c2; {MS byte is wrong}
{Increment}
{fault count}
Xbus ← FLTCNT LRot0, ZeroBr, c3; {Check if}
BRANCH[TRUE3,DDCT], c1; {fault count}
{overflow}
TRUE1: BRANCH[FLS3,TRUE2], c2; {MS byte is OK, check LS byte}
FLS3: FLTCNT ← FLTCNT + n01, ZeroBr, c3; {wrong, increment fault count}
BRANCH[TRUE3,DDCT], c1; {Check if fault count overflow}
TRUE3: GOTO[TRUE2], c2; {not overflow, check STATUS}
DDCT: FLTCNT ← FLTCNT - n01, c2; {Else, decrement fault count}
TRUE2: STATUS ← STATUS and n0F, c3; {Get status, mask off unwanted}
{bits}
TP01: REGB ← n0E, c1; {Use REGB as a reference}
Noop, c2;
Noop, c3;
STATUS ← STATUS - REGB, ZeroBr, c1; {Test STATUS}
BRANCH[W000,T000], c2;
W000: FLTCNT ← FLTCNT + n01, ZeroBr, c3; {wrong, increment fault count}
BRANCH[FCNOV,FCOV], c1; {Check if fault count}
{overflow}
FCOV: FLTCNT ← FLTCNT - n01, GOTO[T000], c2; {overflow, decrement count}
FCNOV: Noop, c2; {Else, noop}
T000: COUNTER ← COUNTER - n01, ZeroBr, c3; {Decrement pattern count}
BRANCH[ LOP1,ASUBB], c1; {Check if completed A+B}
{
==========================================================================
A-B
==========================================================================
In this test, we check input line F0.
}
ASUBB: REGA ← n55, c2; {Load REGA with 0055}
REGA ← (REGA LRot8) or REGA, c3; {REGA contains 5555}
UREGA ← REGA, c1; {UREGA contains 5555}
UREGSUB ← REGA, c2; {load UREGSUB with 5555}
FloatAB ← UREGA, c3; {load AB each with 55555555}
FloatAB ← UREGA, c1;
FloatA ← UREGSUB, FLAMinusB, c2; {load A with 55555555}
FloatA ← UREGSUB, c3; {and perform A-B}
FloatNop, c1;
Noop, c2;
Noop, c3;
Noop, c1;
FloatUnloadS, Float.M, c2; {unload MS word of result}
FloatUnloadS, Float.L, c3; {unload MS word of result}
STATUS ← PPort, c1; {load the status}
RESM ← FloatResult, c2;
RESL ← FloatResult, c3;
RESM ← RESM or RESL, ZeroBr, c1; {Test results, must be 00000000}
BRANCH[FLS5,AMULB], c2;
FLS5: FLTCNT ← FLTCNT + n01, ZeroBr, c3; {wrong, increment fault count}
BRANCH[AMULB1,DCT1], c1; {Check for fault count overflow}
AMULB1: GOTO[AMULB], c2; {no overflow, continue}
DCT1: FLTCNT ← FLTCNT - n01, c2; {Else, decrement count}
{
==========================================================================
A.B
==========================================================================
In this test, we check the multiplier chip.
Case 1: A=AAAAAAAA, B=1
Case 2: A=55555555, B=1
}
AMULB: REGA ← nAA, c3; {Load REGA with 00AA}
REGA ← (REGA LRot8) or REGA, c1; {REGA contains AAAA}
UREGMUL ← REGA, c2; {load UREGMUL with AAAAAAAA}
REGA ← n00, c3;
UREGA ← REGA, c1; {UREGA contains 0000}
REGA ← n3F, c2; {load 3F into REGA}
REGB ← n80, c3; {load 80 into REGB}
REGA ← (REGA LRot8) , c1;
REGA ← REGA or REGB, c2; {REGA now contains 3F80(f)=1.0}
UREGB ← REGA, c3; {load UREGB with 3F80(f)=1.0}
COUNTER ← n02, c1; {Initialize counter}
Noop, c2;
Noop, c3;
FloatMode, FloatFLOW, c1; {load flow thru mode}
FloatAB ← UREGB, c2; {load AB each with 3F800000}
FloatAB ← UREGA, c3;
FEDA4: FloatA ← UREGMUL, FLTimes.A.B, c1; {load A with AAAAAAAA or 55555555}
FloatA ← UREGMUL, c2; {and perform A.B}
FloatNop, c3;
Noop, c1;
Noop, c2;
Noop, c3;
FloatUnloadP, Float.M, c1;
FloatUnloadP, Float.L, c2;
STATUS ← PPort, c3; {load status}
RESM ← FloatResult, c1;
RESL ← FloatResult, c2;
RESM ← RESM - REFREG, ZeroBr, c3; {Check MS word of result}
RESL ← RESL - REFREG, ZeroBr, BRANCH[FL01,TR01], c1; {Check LS byte}
FL01: FLTCNT ← FLTCNT + n01, CANCELBR[$], c2; {MS byte}
{is wrong,}
{increment fault}
{count}
Xbus ← FLTCNT LRot0, ZeroBr, c3; {Check if overflow}
BRANCH[TR04,DCT], c1;
TR01: BRANCH[FL02,TR03], c2; {MS word is OK, check LS byte}
FL02: FLTCNT ← FLTCNT + n01, ZeroBr, c3; {LS word is wrong, increment}
{fault count}
BRANCH[TR04,DCT], c1; {Check if fault count overflow}
TR04: GOTO[TR03], c2; {not overflow, continue}
DCT: FLTCNT ← FLTCNT - n01, c2; {Else, decrement count}
TR03: COUNTER ← COUNTER - n01, ZeroBr, c3; {Decrement test counter}
BRANCH[SCPS,SWAB], c1; {Second pass or swap AB}
SCPS: REGA ← n55, c2; {Second pass, use 55555555}
REGA ← (REGA LRot8) or REGA, c3;
UREGMUL ← REGA, c1;
REFREG ← REGA, c2; {Expected value is 55555555}
GOTO[FEDA4], c3;
{
Case 3: A=1, B=AAAAAAAA
Case 4: A=1, B=55555555
}
SWAB: REGA ← n3F, c2; {Load REGA with 003F}
REGA ← REGA LRot8, c3; {REGA contains 3F00}
REGA ← REGA or REGB, c1; {REGA contains 3F80}
UREGMUL ← REGA, c2; {UREGMUL now contains 3F80}
REGA ← nAA, c3; {REGA contains 00AA}
REGA ← (REGA LRot8) or REGA, c1; {REGA contains AAAA}
UREGB ← REGA, c2; {load REGB with AAAA}
COUNTER ← n02, c3; {load counter}
REFREG ← REGA, c1; {REFREG contains AAAA}
FEDB1: FloatMode, FloatFLOW, c2; {load flow mode}
FloatAB ← UREGB, c3; {load A,B with AAAAAAAA or 55555555}
FloatAB ← UREGB, c1;
FloatA ← UREGMUL, FLTimes.A.B, c2; {load A with 3F800000}
FloatA ← UREGA, c3; {and perform A.B}
FloatNop, c1;
Noop, c2;
Noop, c3;
Noop, c1;
Noop, c2;
Noop, c3;
FloatUnloadP, Float.M, c1;
FloatUnloadP, Float.L, c2;
STATUS ← PPort, c3; {Read status}
RESM ← FloatResult, c1;
RESL ← FloatResult, c2;
RESM ← RESM - REFREG, ZeroBr, c3; {Check MS word of result}
RESL ← RESL - REFREG, ZeroBr, BRANCH[FL011,TR011], c1; {Check LS byte}
FL011: FLTCNT ← FLTCNT + n01, CANCELBR[$], c2; {MS byte}
{is wrong,}
{increment fault}
{count}
Xbus ← FLTCNT LRot0, ZeroBr, c3; {Check if}
BRANCH[TR041,DCT11], c1; {overflow}
TR011: BRANCH[FL021,TR031], c2; {If MS word OK, check LS byte}
FL021: FLTCNT ← FLTCNT + n01, ZeroBr, c3; {LS word wrong,}
{increment fault count}
BRANCH[TR041,DCT11], c1; {Check if fault count overflow}
TR041: GOTO[TR031], c2; {no overflow, continue}
DCT11: FLTCNT ← FLTCNT - n01, c2; {Else, decrement count}
TR031: COUNTER ← COUNTER - n01, ZeroBr, c3; {Decrement test count}
BRANCH[SCPS1,STTS], c1; {Do second pass or next test}
SCPS1: REGA ← n55, c2; {Second pass, use 55555555}
REGA ← (REGA LRot8) or REGA, c3;
UREGB ← REGA, c1;
REFREG ← REGA, c2; {Load expected value of 55555555}
Noop, c3;
GOTO[FEDB1], c1;
STTS: STATUS ← STATUS and n0F, c2; {Test status line of multiplier}
REFREG ← n0E, c3; {Load expected value}
STATUS ← STATUS - REFREG, ZeroBr, c1;
BRANCH[STNPA,STPA], c2;
STNPA: FLTCNT ← FLTCNT + n01, ZeroBr, c3; {STATUS is wrong}
{Increment fault count}
BRANCH[SFCRC,SFNCR], c1; {Check if overflow}
SFNCR: FLTCNT ← FLTCNT - n01, c2; {Overflow, decrement count}
STPA: Noop, c3;
{
==========================================================================
Test status signals of the adder (1033)
==========================================================================
This is done by adding invalid numbers
}
Noop, c1;
SFCRC: REGA ← nFF, c2; {REGA contains 00FF}
REGA ← (REGA LRot8) or REGA, c3; {REGA contains FFFF}
UREGADD ← REGA, c1; {UREGADD contains FFFF}
UREGB ← REGA, c2; {UREGB contains FFFF}
REFREG ← n02, c3; {Expected value is 02}
FloatAB ← UREGB, c1; {Load FFFFFFFF into A & B}
FloatAB ← UREGB, c2;
FloatA ← UREGADD, FLPlus, c3; {Perform A+B}
FloatA ← UREGADD, c1;
FloatNop, c2;
Noop, c3;
Noop, c1;
Noop, c2;
Noop, c3;
FloatUnloadS, Float.M, c1; {unload MS word}
FloatUnloadS, Float.L, c2; {unload LS word}
STATUS ← PPort, c3; {read status}
RESM ← FloatResult, c1; {store MS word of result in REGCM}
RESL ← FloatResult, c2; {LS word in REGCL}
STATUS ← STATUS and n0F, c3; {Mask off unwanted bits}
STATUS ← STATUS - REFREG, ZeroBr, c1; {Check STATUS}
BRANCH[STER,STCR], c2;
STCR: GOTO[STCH], c3; {If OK, continue}
STER: FLTCNT ← FLTCNT + n01, ZeroBr, c3; {Else, increment fault count}
BRANCH[FCCR,DFCT], c1; {Check for overflow}
FCCR: Noop, c2; {no overflow, continue}
GOTO[STCH], c3;
DFCT: FLTCNT ← FLTCNT - n01, c2; {Else, decrement fault count}
GOTO[STCH], c3;
{
==========================================================================
Test Funtion input, F1
==========================================================================
This is done by converting 24 bits integer to 32 bits floating point.
}
STCH: REGA ← n02, c1; {Load 02 into REGA}
UREGB ← REGA, c2; {Load it into UREGB}
REGA ← n00, c3; {REGA contains 0000}
UREGFL ← REGA, c1; {Load 0000 into UREGFL}
FloatAB ← UREGFL, c2;
FloatAB ← UREGB, c3;
FloatA ← UREGFL, FLFloatA, c1;
FloatA ← UREGB, c2;
FloatNop, c3;
Noop, c1;
Noop, c2;
Noop, c3;
Noop, c1;
FloatUnloadS, Float.M, c2; {unload MS word}
FloatUnloadS, Float.L, c3; {unload LS word}
STATUS ← PPort, c1; {read status}
RESM ← FloatResult, c2; {store MS word of result in REGCM}
RESL ← FloatResult, c3; {LS word in REGCL}
{Expected value is 40000000}
REFREG ← n40, c1;
REFREG ← REFREG LRot8, c2; {REFREG contains 4000}
REFREG ← RESM - REFREG, ZeroBr, c3; {Check MS byte}
Xbus ← RESL LRot0, ZeroBr, BRANCH[FL012,TR012], c1; {Check LS byte}
FL012: FLTCNT ← FLTCNT + n01, CANCELBR[$], c2; {MS byte}
{is wrong,}
{increment fault}
{count}
Xbus ← FLTCNT LRot0, ZeroBr, c3; {Check if}
{fault count}
BRANCH[F3TS,DCT2], c1; {overflow}
TR012: BRANCH[FL022,TR032], c2; {MS word OK,Check LS byte} FL022: FLTCNT ← FLTCNT + n01, ZeroBr, c3; {LS byte wrong}
{increment fault,count}
BRANCH[F3TS,DCT2], c1; {Check if overflow}
DCT2: FLTCNT ← FLTCNT - n01, c2; {overflow, decrement count}
TR032: Noop, c3;
Noop, c1;
F3TS: Noop, c2;
Noop, c3;
{
==========================================================================
Test Function input, F3
==========================================================================
This is done by doing Abs(A-b) twice,
first : A= 00005555, B=0000AAAA,
then : A= 0000AAAA, B=00005555.
}
COUNTER ← n02, c1; {Load 02 into test counter}
REGA ← n00, c2; {REGA contains 0000}
UREGSBA ← REGA c3; {UREGSBA contains 0000}
REGA ← n55, c1; {REGA contains 0055}
REGA ← (REGA LRot8) or REGA, c2; {REGA contains 5555}
REFREG ← REGA, c3; {Load REFREG with 5555}
{Expected value is 00005555}
UREGB ← REGA, c1; {UREGB contains 5555}
REGA ← REGA LRot1, c2; {REGA contains AAAA}
UREGA ← REGA, c3; {UREGA contains AAAA}
{Perform Abs(A-b), the exponents are 0000}
F3T1: FloatAB ← UREGSBA, c1; {Load AB each with 00005555}
FloatAB ← UREGA, c2; {or 0000AAAA}
FloatA ← UREGSBA, FLAbsOfAMinusB, c3;
FloatA ← UREGB, c1;
FloatNop, c2;
Noop, c3;
Noop, c1;
Noop, c2;
Noop, c3;
FloatUnloadS, Float.M, c1; {unload MS word}
FloatUnloadS, Float.L, c2; {unload LS word}
STATUS ← PPort, c3; {read status}
RESM ← FloatResult, c1; {store MS word of result in REGCM}
RESL ← FloatResult, c2; {LS word in REGCL}
Xbus ← RESM LRot0, ZeroBr, c3; {Check MS byte}
RESL ← RESL - REFREG, ZeroBr, BRANCH[NPS,PASS], c1; {Check LS byte}
NPS: FLTCNT ← FLTCNT + n01, ZeroBr, CANCELBR[$], c2; {MS byte is}
{wrong,}
{increment}
{fault count}
BRANCH[FCNTOK,FCNTWR], c3; {Check if fault count overflow}
PASS: BRANCH[NPS1,PASS1], c2; {MS word OK, check LS byte}
FCNTWR: FLTCNT ← FLTCNT - n01, GOTO[FLTDT1], c1; {fault count overflow}
{decrement count}
FCNTOK: Noop, c1;
FLTDT1: GOTO[PASS1], c2;
NPS1: FLTCNT ← FLTCNT + n01, ZeroBr, c3; {LS word is wrong, increment}
{fault count}
BRANCH[FCPS1,FCWR1], c1; {Check for overflow}
FCWR1: FLTCNT ← FLTCNT - n01, GOTO[PASS1], c2; {overflow, decrement count}
FCPS1: Noop, c2;
PASS1: COUNTER ← COUNTER - n01, ZeroBr, c3; {Decrement test count}
BRANCH[ONEMR,DONE], c1; {Check if test completed}
ONEMR: UREGB ← REGA, c2; {One more test, UREGB contains}
{AAAA}
REGA ← REGA LRot1, c3; {REGA contains 5555}
UREGA ← REGA, c1; {UREGA contains 5555}
Noop, c2;
GOTO[F3T1], c3;
DONE: Noop, c2;
GOTO[START], c3;