GenCall.mesa
Copyright © 1985, 1986, 1987 by Xerox Corporation. All rights reserved.
Edward Fiala February 19, 1986 5:19:18 pm PST
Fiala November 5, 1986 11:54:17 am PST Cosmetic edits only.
Fiala March 26, 1987 2:18:01 pm PST Eliminate Reset, Halt, and Pause stuff
to run with GenDebugger; eliminate useless defs for FillXop, FillTrap and entry labels; use withSoftCard BOOLEAN to control memory addresses.
Load with "quad -cx GenDebugger GenCall"; requires "← LizardLiverImpl.careful ← FALSE". This diagnostic tests DFC, LFC, and RET for correct function over all 32 bits of DFC AlphaBetaGammaDelta, all 16 bits of LFC AlphaBeta, and all 8 bits of RET Alpha. All code is executed in Kernel mode with traps disabled.
Since LFC and RETN were already tested by GenReg to the extent of verifying that the PC, L, and the IFU stack changed correctly, and that the different PC bits stored in the IFU stack work, those things aren't checked here. No traps are tested. On correct execution, termination occurs with HALT[177777B] at PC 6777000B, cycle 681, Inst 135.

Note: Lizard's drLFC[x] expects x to be a CARDINAL and should be INTEGER?
DIRECTORY
DebuggerDefs,
DragOpsCross USING [],
--Word, wordsPerPage, bytesPerWord, charsPerWord, bitsPerByte, bitsPerCharacter, bitsPerWord, bytesPerPage, logWordsPerPage, logBitsPerByte, logBitsPerChar, logBytesPerWord, logCharsPerWord, logBitsPerWord, logBytesPerPage, PageCount, PageNumber, maxPagesInVM, SixBitIndex, FiveBitIndex, TwoWords, FourBitIndex, Half, ThreeBitIndex, FourHalves, TwoHalves, Byte, ZerosByte, OnesByte, EightBytes, FourBytes, ByteIndex, BytesPerWord, TwoBytes, Comparison, ByteAddress, WordAddress, FieldDescriptor, RegIndex, PadByte, Lit8, Op4, Op8, JDist8, Inst, OIFormat, OQBformat, LRformat, QRformat, ShortRegQR, OBformat, LRBformat, RRformat, ODBformat, LRRBformat, RJBformat, ShortRegRJB, JBBformat, TrapWidthWords, TrapWidthBytes, XopBase, TrapBase, KernalLimit, TrapIndex, StackUnderflowTrap, IFUPageFaultTrap, ResetTrap, IFUStackOverflowTrap, EUStackOverflowTrap, RescheduleTrap, ALUCondFalse, ALUCondEZ, ALUCondLZ, ALUCondLE, ALUCondSpare, ALUCondNE, ALUCondGE, ALUCondGZ, ALUCondOver, ALUCondBC, ALUCondIL, ALUCondDO, ALUCondNotOver, ALUCondNB, ALUCondNI, ModeFault, MemAccessFault, IOAccessFault, EUPageFault, EUWriteFault, AUFault, euStack, euJunk, euToKBus, euMAR, euField, euConstant, euAux, euBogus, euLast, ifuYoungestL, ifuYoungestPC, ifuEldestL, ifuEldestPC, ifuSLimit, ifuBogus, ifuL, ifuS, ifuPC, ifuLast, EURegs, EULegalRegs, IFURegs, IFULegalRegs, StackedStatusWord, IFUStackIndex, IFUStackSize, IFUOverflow, EUStackIndex, EUStackSize, EULocalIndex, EULocals, EUAuxIndex, EUAuxRegs, EUConstIndex, EUConstants, IOLocation, ioRescheduleRequest, ioResetRequest, IOOperand, PCmdFormat, PCmdByteSelect, PCmdClass, PCmdSpace, PCmdDirection
DragOpsCrossUtils USING [CardToWord],
--InstToBytes, InstToFormat, BytePCToWordAddress, WordAddressToBytePC, IOOperandToCard, CardToIOOperand, FieldDescriptorToCard, CardToFieldDescriptor, BytesToWord, BytesToHalf, WordToBytes, HalfToBytes, HalvesToWord, WordToHalves, HighHalf, LowHalf, LeftHalf, RightHalf, SwapHalves, WordToInt, IntToWord, WordToCard, HalfToCard, ByteToCard, CardToWord, CardToHalf, CardToByte, DragAnd, DragOr, DragXor, DragNot, VanillaAdd, VanillaSub, AddDelta, HalfNot, HalfAnd, HalfOr, HalfXor, HalfShift, DoubleWordShiftLeft, SingleWordShiftLeft, SingleWordShiftRight, XopToBytePC, TrapIndexToBytePC, FieldUnit
HandCoding, --Has opcode and register defs.
HandCodingPseudos, --Label, SetLabel, GenLabel, GenLabelHere, UseLabel8A, UseLabel8B, UseLabel16, UseLabel32, LReg, PReg, SReg, AddReg, SubReg, SetRegConst, MoveReg, MoveRegI, LRegI, IndexedJump, ProcedureEntry, ProcedureExit, SetupField, ExtractField, ShiftLeft, LoadProcessorReg, StoreProcessorReg, CauseReschedule, CauseReset, GetSPLimit, SetSPLimit, GetYoungestPC, GetYoungestStatus, GetEldestPC, GetEldestStatus, SetYoungestPC, SetYoungestStatus, SetEldestPC, SetEldestStatus, Pause, Halt
HandCodingSupport; --Area, GetProc, PutProc, ProcList, NewArea, GenWithArea, Gen1WithArea, ForceOut, GetCurrentArea, LoadArea, GetOutputPC, SetOutputPC, WordAlign, ReserveData, OutputByte, OutputOneByte, OutputAlphaBeta, OutputAlphaBetaGammaDelta, OutputWord
GenCall: CEDAR PROGRAM
IMPORTS DragOpsCrossUtils, HandCoding, HandCodingPseudos, HandCodingSupport
= BEGIN OPEN DebuggerDefs, DragOpsCrossUtils, HandCoding, HandCodingPseudos, HandCodingSupport;
All: PROC = {
area: Area = GetCurrentArea[];
Exercise every bit position of the PC address and every bit position of the alpha byte of RET. The test procedures do something entirely non-sensical, but the purpose of the diagnostic is served.
GenDFCRETTest: PROC [] ~ {
Produce a small procedure consisting of an instruction which counts [S] before a DFC and before RET so that the passage of control through all the procedures can be verified by checking the value in [S] at the end. The change in L at procedure entry by ALS offsets the change in S at procedure exit by RET so that RET[alpha] can be tested for all values of alpha without changing [S].
DoDFC: PROC [destPC: LONG CARDINAL, nArgs: CARDINAL] ~ {
alsArg: CARDINAL = (1 - nArgs) MOD 400B;
retArg: CARDINAL = (nArgs - 1) MOD 400B;
drALS[alsArg]; --ALS[1 - nargs] => set L nArgs below S
drADDB[200B];
drDFC[CardToWord[destPC]];
drADDB[1];
RET does S ← L + alpha; return.
drRET[retArg]; --RET[nResults - 1] => set S nArgs above L
SetOutputPC[destPC];
};
enterDFCRETTestPC: LONG CARDINAL = 1774000B * bytesPerWord;
endDFCRETTestPC: LONG CARDINAL = 1600000B * bytesPerWord;
firstJumpPC: LONG CARDINAL = IF withSoftCard THEN 5000000B ELSE 400100B;
okDFCRET: Label = GenLabel[];
drJQB[CardToWord[enterDFCRETTestPC]];
SetOutputPC[enterDFCRETTestPC];
Exercise every bit position of the PC address.
Must avoid the vector for Xops and Traps between byte positions 4000000B and 4004000B; must avoid the locations occupied by the other tests in the diagnostic.
drLIB[0]; --Counter used to verify that the calls and returns have occurred.
drDFC[CardToWord[firstJumpPC]];
drLIQB[CardToWord[3416B]];
drRJEB[popSrc, belowSrcPop, UseLabel8B[okDFCRET]]; Pause[]; SetLabel[okDFCRET];
drJQB[CardToWord[endDFCRETTestPC]];
SetOutputPC[firstJumpPC];
IF withSoftCard THEN { --1 megabyte limit confines PC to [4,000,000B..10,000,000B).
DoDFC[ 5010020B, 1B]; --[s] = 200B after the SFC, 3416B after the RETN
DoDFC[ 5020040B, 2B]; --[s] = 400B after the SFC, 3415B after the RETN
DoDFC[ 5040100B, 4B]; --[s] = 600B after the SFC, 3414B after the RETN
DoDFC[ 5100200B, 10B]; --[s] = 1000B after the SFC, 3413B after the RETN
DoDFC[ 5200400B, 20B]; --[s] = 1200B after the SFC, 3412B after the RETN
DoDFC[ 5401000B, 40B]; --[s] = 1400B after the SFC, 3411B after the RETN
DoDFC[ 6202000B, 100B]; --[s] = 1600B after the SFC, 3410B after the RETN
DoDFC[ 6004001B, 177B]; --[s] = 2000B after the SFC, 3407B after the RETN
DoDFC[ 4060002B, 3B]; --[s] = 2200B after the SFC, 3406B after the RETN
DoDFC[ 4070004B, 5B]; --[s] = 2400B after the SFC, 3405B after the RETN
DoDFC[ 5100010B, 6B]; --[s] = 2600B after the SFC, 3404B after the RETN
DoDFC[ 4200020B, 7B]; --[s] = 3000B after the SFC, 3403B after the RETN
DoDFC[ 4400040B, 11B]; --[s] = 3200B after the SFC, 3402B after the RETN
DoDFC[ 4677777B, 0B]; --[s] = 3400B after the SFC, 3401B after the RETN
}
ELSE {
DoDFC[ 1000200B, 1B]; --[s] = 200B after the DFC, 3416B after the RETN
DoDFC[ 2000400B, 2B]; --[s] = 400B after the DFC, 3415B after the RETN
DoDFC[ 4010000B, 4B]; --[s] = 600B after the DFC, 3414B after the RETN
DoDFC[ 10002000B, 10B]; --[s] = 1000B after the DFC, 3413B after the RETN
DoDFC[ 20004001B, 20B]; --[s] = 1200B after the DFC, 3412B after the RETN
DoDFC[ 40001002B, 40B]; --[s] = 1400B after the DFC, 3411B after the RETN
DoDFC[ 100020004B, 100B]; --[s] = 1600B after the DFC, 3410B after the RETN
DoDFC[ 200040010B, 177B]; --[s] = 2000B after the DFC, 3407B after the RETN
DoDFC[ 400100020B, 3B]; --[s] = 2200B after the DFC, 3406B after the RETN
DoDFC[ 1000000000B, 5B]; --[s] = 2400B after the DFC, 3405B after the RETN
DoDFC[ 2000000000B, 6B]; --[s] = 2600B after the DFC, 3404B after the RETN
DoDFC[ 4000000000B, 7B]; --[s] = 3000B after the DFC, 3403B after the RETN
DoDFC[10000000000B, 11B]; --[s] = 3200B after the DFC, 3402B after the RETN
DoDFC[20000200040B, 0B]; --[s] = 3400B after the DFC, 3401B after the RETN
};
drRETN[];
SetOutputPC[endDFCRETTestPC];
};
GenLFCTest: PROC [] ~ {
Produce a procedure which counts [S] before and after an LFC and exits with a RETN, and which modifies the PC to point at the procedure called by the LFC. Page creation zeroes unused bytes, so a trap will happen if a wild jump or non-jump occurs.
DoLFC: PROC [destDisp: CARDINAL] ~ {
oldPC: LONG CARDINAL;
drADDB[200B];
oldPC ← GetOutputPC[area];
drLFC[destDisp];
drADDB[1];
drRETN[];
SetOutputPC[oldPC + destDisp + (IF destDisp >= 100000B THEN -200000B ELSE 0)];
};
oldPC: LONG CARDINAL;
endLFCTestPC: LONG CARDINAL = 6777000B;
okLFC: Label = GenLabel[];
Exercise every bit position of the PC displacement.
drLIB[0]; --Counter used to verify that the calls and returns have occurred.
oldPC ← GetOutputPC[area];
drLFC[40000B];
drLIQB[CardToWord[2613B]];
drRJEB[popSrc, belowSrcPop, UseLabel8B[okLFC]]; Pause[]; SetLabel[okLFC];
drJQB[CardToWord[endLFCTestPC]];
SetOutputPC[oldPC + 40000B];
DoLFC[ 20001B]; --[s] = 200B after the LFC, 2613B after the RETN
DoLFC[ 10002B]; --[s] = 400B after the LFC, 2612B after the RETN
DoLFC[ 4004B]; --[s] = 600B after the LFC, 2611B after the RETN
DoLFC[ 2010B]; --[s] = 1000B after the LFC, 2610B after the RETN
DoLFC[ 1000B]; --[s] = 1200B after the LFC, 2607B after the RETN
DoLFC[ 400B]; --[s] = 1400B after the LFC, 2606B after the RETN
DoLFC[ 200B]; --[s] = 1600B after the LFC, 2605B after the RETN
DoLFC[ 100B]; --[s] = 2000B after the LFC, 2604B after the RETN
DoLFC[ 40B]; --[s] = 2200B after the LFC, 2603B after the RETN
DoLFC[ 20B]; --[s] = 2400B after the LFC, 2602B after the RETN
DoLFC[100400B]; --[s] = 2600B after the LFC, 2601B after the RETN
drRETN[];
SetOutputPC[endLFCTestPC];
};
Begin at PC = userBasePC = 1010000B * 4, L = 1, S = 0 as established in GenDebugger.
GenDFCRETTest[];
GenLFCTest[];
Halt[177777B]; --Terminate here at the end of the program
};
END.