<> <> <> <> <<>> <> <<>> DIRECTORY Core, CoreCreate, ICTest, Ports, Rope, TestCable, IO, FS, Convert; TestNMos: CEDAR PROGRAM IMPORTS CoreCreate, ICTest, Ports, TestCable, Rope, IO, FS, Convert = BEGIN <<-- Types>> ROPE: TYPE = Rope.ROPE; VectorEntries: TYPE = RECORD [entrymode: ATOM, entryvalue: LONG CARDINAL]; TestVector: TYPE = ARRAY [0..20] OF VectorEntries; <<-- Vector Assignments>> vectorStream,outstream: IO.STREAM; endofvectors: BOOL; vectors: TestVector; debugging: BOOL; <<-- Port Assignments >> hold: NAT = 0; interrupt: NAT = 1; refresh: NAT = 2; reset: NAT = 3; holdA: NAT = 4; outputInterrupt: NAT = 5; writeEnableBar: NAT = 6; casBar: NAT = 7; rasBar: NAT = 8; dataBus: NAT = 9; <<-- Special Raddr>> rAddr: NAT = 10; rasRaddr: NAT = 10; casRaddr: NAT = 11; <<-- Program Controled Ports:>> precharge: NAT = 11; clock: NAT = 12; clockD10: NAT = 13; clockD35: NAT = 14; gnd: NAT = 15; vdd: NAT = 16; cycle: NAT = 17; <<-- Other Globals:>> AssignList: TYPE = LIST OF ICTest.Assignments; assignments: AssignList; thisTest: Rope.ROPE = "TamarinNMos Tester"; PrintAssignments: PROC = { stream: FS.STREAM _ FS.StreamOpen["///user/krivacic.pa/pinout.txt",$create]; j: ICTest.Assignments; i: AssignList _ assignments; WHILE i#NIL DO { j _ i.first; IO.PutF[stream,"Signal: %15g ",IO.rope[j.name]]; IF j.group = 0 THEN IO.PutF[stream," "] ELSE IO.PutF[stream,"Side: %g Pod: %g Byte: %g Bit: %1g ", IO.char[IF j.loadBoardSide = R THEN 'R ELSE 'L], IO.rope[ SELECT j.podPair FROM AB => "A", CD => "C", EF => "E", GH => "G", IJ => "I", KL => "K", ENDCASE => "??"], IO.char[SELECT j.pod FROM A => 'A, B => 'B, ENDCASE => '?], IO.int[j.channel], ]; IO.PutF[stream,"Pin: %3g \n",IO.int[j.probeCardPin]]; i _ i.rest; }; ENDLOOP; IO.Close[stream]; }; Init: PROC = { R: PROC [a: ICTest.Assignments] = {assignments _ CONS[a, assignments]}; groups: LIST OF ICTest.Group _ NIL; ct: Core.CellType _ CoreCreate.Cell[name:"TamarinNMos", public: CoreCreate.WireList[LIST[ "hold", "interrupt", "refresh", "reset", "holdA", "outputInterrupt", "writeEnableBar", "casBar", CoreCreate.Seq["rasBar",4], CoreCreate.Seq["dataBus",32], CoreCreate.Seq["rAddr",10], "precharge","clock","clockD10","clockD35", "gnd","vdd","cycle"]], onlyInternal: NIL, instances: NIL ]; assignments _ NIL; groups _ LIST [ [number: 1, name: "CtlIn", directionality: force, format: DNRZ, delay: 50], [number: 2, name: "CtlOut", directionality: acquire, format: DNRZ, sample: 100], [number: 3, name: "DataBus", directionality: biDirectional, format: DNRZ, sample: 100, delay: 50], [number: 4, name: "Clocks", directionality: force, format: DNRZ, delay: 0], [number: 7, name: "ClockCycle", directionality: force, format: RZ, delay: 0, width: 200], [number: 5, name: "Row/ColAddrs", directionality: acquire, format: DNRZ, sample: 100], [number: 6, name: "Cas", directionality: acquire, format: DNRZ, sample: 100] ]; assignments _ NIL; << L>> << o >> << a T>> << d e>> << s>> << B t D>> << o e U>> << a P r T>> << r o C D>> << d d h H H U>> << G B a e e T>> << r o S P B n a a >> << o a i a y n d d P>> << u r d i t e e e i>> <> R[["gnd", 0,0,R,AB, A,1,001,001,02]]; R[["gnd", 0,0,R,AB, A,1,001,001,03]]; R[["gnd", 0,0,R,AB, A,1,001,001,04]]; R[["gnd", 0,0,R,AB, A,1,001,001,05]]; R[["gnd", 0,0,R,AB, A,1,001,001,06]]; R[["gnd", 0,0,R,AB, A,1,001,001,07]]; R[["gnd", 0,0,R,AB, A,1,001,001,08]]; R[["gnd", 0,0,R,AB, A,1,001,001,16]]; R[["gnd", 0,0,R,AB, A,1,001,001,17]]; R[["gnd", 0,0,R,AB, A,1,001,001,18]]; R[["gnd", 0,0,R,AB, A,1,001,001,33]]; R[["gnd", 0,0,R,AB, A,1,001,001,65]]; R[["gnd", 0,0,R,AB, A,1,001,001,99]]; R[["vdd", 0,0,R,AB, A,0,001,001,34]]; R[["vdd", 0,0,R,AB, A,0,001,001,59]]; R[["vdd", 0,0,R,AB, A,0,001,001,60]]; R[["vdd", 0,0,R,AB, A,0,001,001,61]]; R[["vdd", 0,0,R,AB, A,0,001,001,62]]; R[["vdd", 0,0,R,AB, A,0,001,001,63]]; R[["vdd", 0,0,R,AB, A,0,001,001,64]]; R[["vdd", 0,0,R,AB, A,0,001,001,67]]; R[["vdd", 0,0,R,AB, A,0,001,001,100]]; R[["vdd", 0,0,R,AB, A,0,001,001,132]]; R[["v10", 0,0,R,AB, A,0,001,001,01]]; R[["v10", 0,0,R,AB, A,0,001,001,66]]; R[["cycle", 7,0,R,AB, A,3,001,001,200]]; R[["precharge", 4,6,L,CD, B,0,001,001,78]]; R[["clock", 4,6,L,CD, B,1,001,001,77]]; R[["clockD10", 4,6,L,CD, B,2,001,001,75]]; R[["clockD35", 4,6,L,CD, B,3,001,001,76]]; R[["hold", 1,0,R,AB, B,0,001,001,71]]; R[["interrupt", 1,0,R,AB, B,1,001,001,74]]; R[["refresh", 1,0,R,AB, B,2,001,001,69]]; R[["reset", 1,0,R,AB, B,3,001,001,73]]; R[["holdA", 2,1,R,CD, A,0,001,001,70]]; R[["outputInterrupt", 2,1,R,CD, A,1,001,001,72]]; R[["writeEnableBar", 2,1,R,CD, A,2,001,001,79]]; R[["rasBar[0]", 2,1,R,CD, A,4,001,001,81]]; R[["rasBar[1]", 2,1,R,CD, A,5,001,001,82]]; R[["rasBar[2]", 2,1,R,CD, A,6,001,001,83]]; R[["rasBar[3]", 2,1,R,CD, A,7,001,001,84]]; R[["casBar", 6,1,R,CD, B,0,001,001,80]]; R[["rAddr[0]", 5,2,R,EF, A,0,001,001,85]]; R[["rAddr[1]", 5,2,R,EF, A,1,001,001,86]]; R[["rAddr[2]", 5,2,R,EF, A,2,001,001,87]]; R[["rAddr[3]", 5,2,R,EF, A,3,001,001,88]]; R[["rAddr[4]", 5,2,R,EF, A,4,001,001,89]]; R[["rAddr[5]", 5,2,R,EF, A,5,001,001,90]]; R[["rAddr[6]", 5,2,R,EF, A,6,001,001,91]]; R[["rAddr[7]", 5,2,R,EF, A,7,001,001,92]]; R[["rAddr[8]", 5,2,R,EF, B,0,001,001,93]]; R[["rAddr[9]", 5,2,R,EF, B,1,001,001,94]]; R[["dataBus[0]", 3,3,R,GH, A,0,001,001,95]]; R[["dataBus[1]", 3,3,R,GH, A,1,001,001,96]]; R[["dataBus[2]", 3,3,R,GH, A,2,001,001,97]]; R[["dataBus[3]", 3,3,R,GH, A,3,001,001,98]]; R[["dataBus[4]", 3,3,R,GH, A,4,001,001,101]]; R[["dataBus[5]", 3,3,R,GH, A,5,001,001,102]]; R[["dataBus[6]", 3,3,R,GH, A,6,001,001,103]]; R[["dataBus[7]", 3,3,R,GH, A,7,001,001,104]]; R[["dataBus[8]", 3,3,R,GH, B,0,001,001,105]]; R[["dataBus[9]", 3,3,R,GH, B,1,001,001,106]]; R[["dataBus[10]", 3,3,R,GH, B,2,001,001,107]]; R[["dataBus[11]", 3,3,R,GH, B,3,001,001,108]]; R[["dataBus[12]", 3,3,R,GH, B,4,001,001,109]]; R[["dataBus[13]", 3,3,R,GH, B,5,001,001,110]]; R[["dataBus[14]", 3,3,R,GH, B,6,001,001,111]]; R[["dataBus[15]", 3,3,R,GH, B,7,001,001,112]]; R[["dataBus[16]", 3,4,R,IJ, A,0,001,001,113]]; R[["dataBus[17]", 3,4,R,IJ, A,1,001,001,114]]; R[["dataBus[18]", 3,4,R,IJ, A,2,001,001,115]]; R[["dataBus[19]", 3,4,R,IJ, A,3,001,001,117]]; R[["dataBus[20]", 3,4,R,IJ, A,4,001,001,118]]; R[["dataBus[21]", 3,4,R,IJ, A,5,001,001,119]]; R[["dataBus[22]", 3,4,R,IJ, A,6,001,001,120]]; R[["dataBus[23]", 3,4,R,IJ, A,7,001,001,121]]; R[["dataBus[24]", 3,4,R,IJ, B,0,001,001,122]]; R[["dataBus[25]", 3,4,R,IJ, B,1,001,001,123]]; R[["dataBus[26]", 3,4,R,IJ, B,2,001,001,124]]; R[["dataBus[27]", 3,4,R,IJ, B,3,001,001,125]]; R[["dataBus[28]", 3,4,R,IJ, B,4,001,001,126]]; R[["dataBus[29]", 3,4,R,IJ, B,5,001,001,127]]; R[["dataBus[30]", 3,4,R,IJ, B,6,001,001,128]]; R[["dataBus[31]", 3,4,R,IJ, B,7,001,001,129]]; [] _ Ports.InitPort[ct.public[dataBus],lc]; [] _ Ports.InitPort[ct.public[rAddr],c]; [] _ Ports.InitPort[ct.public[rasBar],c]; [] _ Ports.InitPort[ct.public[precharge],c]; [] _ Ports.InitPort[ct.public[clock],c]; [] _ Ports.InitPort[ct.public[clockD10],c]; [] _ Ports.InitPort[ct.public[clockD35],c]; [] _ Ports.InitPort[ct.public[hold],c]; [] _ Ports.InitPort[ct.public[hold],c]; [] _ Ports.InitPort[ct.public[interrupt],c]; [] _ Ports.InitPort[ct.public[refresh],c]; [] _ Ports.InitPort[ct.public[reset],c]; [] _ Ports.InitPort[ct.public[holdA],c]; [] _ Ports.InitPort[ct.public[outputInterrupt],c]; [] _ Ports.InitPort[ct.public[writeEnableBar],c]; [] _ Ports.InitPort[ct.public[casBar],c]; [] _ Ports.InitPort[ct.public[cycle],b]; Ports.InitTesterDrive[ct.public[vdd],force]; Ports.InitTesterDrive[ct.public[gnd],force]; Ports.InitTesterDrive[ct.public[cycle],force]; Ports.InitTesterDrive[ct.public[precharge],force]; Ports.InitTesterDrive[ct.public[clock],force]; Ports.InitTesterDrive[ct.public[clockD10],force]; Ports.InitTesterDrive[ct.public[clockD35],force]; Ports.InitTesterDrive[ct.public[hold],force]; Ports.InitTesterDrive[ct.public[interrupt],force]; Ports.InitTesterDrive[ct.public[refresh],force]; Ports.InitTesterDrive[ct.public[reset],force]; Ports.InitTesterDrive[ct.public[holdA],none]; Ports.InitTesterDrive[ct.public[outputInterrupt],none]; Ports.InitTesterDrive[ct.public[writeEnableBar],none]; Ports.InitTesterDrive[ct.public[casBar],none]; Ports.InitTesterDrive[ct.public[rasBar],none]; Ports.InitTesterDrive[ct.public[rAddr],none]; Ports.InitTesterDrive[ct.public[dataBus],none]; TestCable.Init[groups, assignments, "cycle"]; ICTest.MakeStandardViewer[ testName: thisTest, cellType: ct, clockAName: "cycle", groups: groups, assignments: assignments, period: 200]; }; NextVector: PROC = { <<-- Read in the next cycle's test vectors>> i,j: INT; needrparen: BOOL; token: ROPE; needrparen _ TRUE; j_0; i_0; IF ~ IO.EndOf[vectorStream] THEN { WHILE needrparen AND ~ endofvectors AND ~ IO.EndOf[vectorStream] DO { j _ j+1; token _ IO.GetTokenRope[vectorStream].token; SELECT Rope.Fetch[token,0] FROM ') => needrparen _ FALSE; '( => i _ 0; 'S => { vectors[i].entryvalue _ Convert.CardFromRope[Rope.Substr[token,1]]; vectors[i].entrymode _ $Set; i _ i + 1; }; 'x => { vectors[i].entryvalue _ 0; vectors[i].entrymode _ $Ignore; i _ i + 1; }; 'E => endofvectors _ TRUE; '0,'1,'2,'3,'4,'5,'6,'7,'8,'9 => { vectors[i].entryvalue _ Convert.CardFromRope[token]; vectors[i].entrymode _ $Check; i _ i + 1; }; ENDCASE; }; ENDLOOP; } ELSE endofvectors _ TRUE; }; OpenVectors: PROC [filename: ROPE] = { vectorStream _ FS.StreamOpen["/eris/tamarin/tsim/vectors.txt"]; endofvectors _ FALSE; NextVector[]; }; CloseVectors: PROC = { IO.Close[vectorStream]}; DoTest: ICTest.TestProc = { SetP: PROC [vectorindex, value: LONG CARDINAL, mode: Ports.Drive] = { wireindex: INT; wireindex _ IF vectorindex = casRaddr THEN rasRaddr ELSE vectorindex; p[wireindex].d _ mode; IF wireindex = dataBus THEN p[wireindex].lc _ value ELSE p[wireindex].c _ value; }; ClearEntry: PROC [vectorindex: INT] = { SetP[vectorindex, 0, none]; }; Clocks: PROC [pre, clk, clk10, clk35: INT] = { p[precharge].c _ IF pre=0 THEN 1 ELSE 0; p[clock].c _ IF clk=0 THEN 1 ELSE 0; p[clockD10].c _ clk10; p[clockD35].c _ clk35; }; SetEntry: PROC [vectorindex: INT] = { SELECT vectors[vectorindex].entrymode FROM $Set => SetP[vectorindex, vectors[vectorindex].entryvalue, force]; $Check => SetP[vectorindex, vectors[vectorindex].entryvalue, expect]; $Ignore => SetP[vectorindex, 0, none]; ENDCASE; }; DoEval: PROC = { p[cycle].b _ TRUE; IF debugging THEN FOR i: INT _ 0, i+1 DO { IF i > vdd THEN {IO.Put[outstream,IO.char[15C]]; EXIT;} ELSE { IO.PutF[outstream, SELECT p[i].d FROM expect => "Check: ", force => "Set: ", drive => "Drive: ", none => "x ", ENDCASE => "Unknown: " ]; IF p[i].d # none THEN IO.Put[outstream,IO.int[p[i].c],IO.char[32C]]; }; }; ENDLOOP ELSE Eval[]; }; Cycle: PROC = { -- Start of Cycle: <<- clocks: 0 0 0 0 --------------------------------------------------------- set dataBus if necessary.>> << >> Clocks[0,0,0,0]; IF vectors[dataBus].entrymode = $Set THEN SetEntry[dataBus]; DoEval[]; <<-- clocks: 1 0 0 0 --------------------------------------------------------- check: casBar.>> Clocks[1,0,0,0]; SetEntry[casBar]; DoEval[]; ClearEntry[casBar]; <<-- clocks: 0 0 0 0 --------------------------------------------------------- set: interrupt, reset, refresh hold.>> Clocks[0,0,0,0]; SetEntry[interrupt]; SetEntry[hold]; SetEntry[reset]; SetEntry[refresh]; DoEval[]; <<-- clocks: 0 1 0 0 --------------------------------------------------------- check: writeEnable, rasBar, rasRaddr, dataBus.>> <<>> Clocks[0,1,0,0]; SetEntry[writeEnableBar]; SetEntry[outputInterrupt]; SetEntry[holdA]; SetEntry[rasBar]; SetEntry[rasRaddr]; IF vectors[dataBus].entrymode = $Check THEN SetEntry[dataBus]; DoEval[]; ClearEntry[writeEnableBar]; ClearEntry[rasBar]; ClearEntry[rasRaddr]; ClearEntry[dataBus]; ClearEntry[holdA]; ClearEntry[outputInterrupt]; <<-- clocks: 0 1 1 0 --------------------------------------------------------- check: rasRaddr.>> <<>> Clocks[0,1,1,0]; SetEntry[casRaddr]; DoEval[]; ClearEntry[casRaddr]; <<>> <<-- clocks: 0 1 1 1 --------------------------------------------------------->> Clocks[0,1,1,1]; DoEval[]; -------------------------------------------------------------------------- }; InitState: PROC = { FOR i: INT _ 0, i+1 DO ClearEntry[i]; IF i = casRaddr THEN EXIT; ENDLOOP; p[gnd].c _ 0; p[gnd].d _ force; p[vdd].c _ 1; p[vdd].d _ force; }; InitState[]; OpenVectors["/Phylum/Tamarin/NMos/TestVectors/Test1.Vectors"]; WHILE ~endofvectors DO Cycle[]; NextVector[]; ENDLOOP; CloseVectors[]; }; Runit: PROC = { debugging _ FALSE; Init[]; ICTest.RegisterTestProc[thisTest,"DoTest",DoTest]; ICTest.RegisterTestProc[thisTest,"TestCable",TestCable.TestCable]; }; Runit[]; END.