<> <> <> <<>> <> <<>> DIRECTORY DragOpsCross USING [XopBase, TrapBase, TrapWidthBytes, bytesPerWord, TrapIndex, Word], --XopBase, TrapBase, TrapWidthBytes, Inst, wordsPerPage, bytesPerWord, charsPerWord, bitsPerByte, bitsPerCharacter, bitsPerWord, logWordsPerPage, logBitsPerByte, logBitsPerChar, logBytesPerWord, logCharsPerWord, logBitsPerWord, logBytesPerPage, PageCount, PageNumber, maxPagesInVM, SixBitIndex, FiveBitIndex, Word, TwoWords, FourBitIndex, Half, ThreeBitIndex, FourHalves, TwoHalves, Byte, ZerosByte, OnesByte, EightBytes, FourBytes, ByteIndex, BytesPerWord, TwoBytes, Comparison, ByteAddress, WordAddress, FieldDescriptor, TrapWidthWords, KernalLimit, TrapIndex, StackUnderflowTrap, IFUPageFaultTrap, ResetTrap, IFUStackOverflowTrap, EUStackOverflowTrap, RescheduleTrap, ALUCondOver, ALUCondBC, ALUCondIL, ALUCondDO, EUPageFault, EUWriteFault, AUFault, euStack, euJunk, euMAR, euField, euConstant, euAux, euBogus, euLast, ifuXBus, ifuStatus, ifuSLimit, ifuYoungestL, ifuYoungestPC, ifuEldestL, ifuEldestPC, ifuBogus, ifuL, ifuS, ifuPC, ifuLast, IFUStatusRec, IFUStackIndex, IFUStackSize, IFUOverflow, EUStackIndex, EUStackSize, EULocalIndex, EULocals, EUAuxIndex, EUAuxRegs, EUConstIndex, EUConstants, IOLocation, ioRescheduleRequest, ioResetRequest DragOpsCrossUtils USING [IntToWord], --BytePCToWordAddress, WordAddressToBytePC, IOOperandToCard, CardToIOOperand, FieldDescriptorToCard, CardToFieldDescriptor, StatusToWord, WordToStatus, 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, TrapIndexToBytePC, XopToBytePC HandCoding, --Has opcode and register defs. HandCodingPseudos, --GenLabel, GenLabelHere, SetLabel, Halt, Pause, MakeLabelGlobal, UseLabel8B, UseLabel16, UseLabel32, ProcedureEntry, ProcedureExit, EnableTraps, IndexedJump, SetupField, ExtractField, ShiftLeft, LoadProcessorReg, StoreProcessorReg, DisableTraps, CauseReschedule, CauseReset, GetSPLimit, SetSPLimit, GetL, SetL, GetYoungestPC, GetYoungestL, GetEldestPC, GetEldestL, SetYoungestPC, SetYoungestL, SetEldestPC, SetEldestL HandCodingSupport; --Area, GetCurrentArea, ReserveData, SetOutputPC, GetProc, PutProc, ProcList, NewArea, GenWithArea, Gen1WithArea, ForceOut, GetOutputPC, WordAlign, OutputByte, OutputOneByte, OutputAlphaBeta, OutputAlphaBetaGammaDelta, OutputWord GenArith: CEDAR PROGRAM IMPORTS DragOpsCrossUtils, HandCoding, HandCodingPseudos, HandCodingSupport = BEGIN OPEN DragOpsCrossUtils, HandCoding, HandCodingPseudos, HandCodingSupport; Word: TYPE = DragOpsCross.Word; <> aux0: AuxRegSpec = [aux[0]]; aux1: AuxRegSpec = [aux[1]]; aux2: AuxRegSpec = [aux[2]]; aux3: AuxRegSpec = [aux[3]]; aux4: AuxRegSpec = [aux[4]]; aux5: AuxRegSpec = [aux[5]]; aux6: AuxRegSpec = [aux[6]]; aux14: AuxRegSpec = [aux[14]]; aux15: AuxRegSpec = [aux[15]]; const5: ConstSpec = [const[5]]; const6: ConstSpec = [const[6]]; const7: ConstSpec = [const[7]]; const8: ConstSpec = [const[8]]; const9: ConstSpec = [const[9]]; const10: ConstSpec = [const[10]]; const11: ConstSpec = [const[11]]; All: PROC = { <> FillXop: PROC [inst: CARDINAL, dest: Label] = { SetOutputPC[inst * DragOpsCross.TrapWidthBytes + DragOpsCross.XopBase * DragOpsCross.bytesPerWord]; drJDB[UseLabel16[dest]]; }; FillTrap: PROC [tx: DragOpsCross.TrapIndex, dest: Label] = { SetOutputPC[LOOPHOLE[tx, CARDINAL] * DragOpsCross.TrapWidthBytes + DragOpsCross.TrapBase * DragOpsCross.bytesPerWord]; drJDB[UseLabel16[dest]]; }; area: Area = GetCurrentArea[]; savePC: LONG CARDINAL; start: Label = GenLabel[]; dummy: Label = GenLabel[]; ALUOverflow: Label = GenLabel[]; ALUOvfUnexpected: Label = GenLabel[]; enterRUADDTest: Label = GenLabel[]; enterRUSUBTest: Label = GenLabel[]; enterRVADDTest: Label = GenLabel[]; enterRVSUBTest: Label = GenLabel[]; enterRADDTest: Label = GenLabel[]; enterRSUBTest: Label = GenLabel[]; enterADDTest: Label = GenLabel[]; enterSUBTest: Label = GenLabel[]; enterADDBTest: Label = GenLabel[]; enterSUBBTest: Label = GenLabel[]; enterADDDBTest: Label = GenLabel[]; enterSUBDBTest: Label = GenLabel[]; enterQADDTest: Label = GenLabel[]; enterQSUBTest: Label = GenLabel[]; <> GenRUADD: PROC = { <> RUADDTest: PROC [a, b, apbc: INT] ~ { okRUADD: Label = GenLabel[]; badRUADD: Label = GenLabel[]; drLIQB[IntToWord[a]]; drLIQB[IntToWord[b]]; drRUADD[pushDst, reg0, reg1]; drLIQB[IntToWord[a + b]]; drRJEBJ[popSrc, belowSrcPop, UseLabel8B[okRUADD]]; SetLabel[badRUADD]; Pause[]; SetLabel[okRUADD]; <> IF apbc = 1 THEN { drRUADD[pushDst, reg0, const2]; -- a+(-1)+Carry1 has result = a, Carry _ 1 drRJNEB[popSrc, reg0, UseLabel8B[badRUADD]]; <> drRUADD[pushDst, const2, reg1]; -- -1+b+Carry1 has result = b, Carry _ 1 drRJNEB[popSrc, reg1, UseLabel8B[badRUADD]]; <> drRUADD[belowDst, const0, belowSrcPop]; -- 0+a+Carry1 has result = a+1, Carry _ 0 drLIQB[IntToWord[a+1]]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRUADD]]; } ELSE { drRUADD[pushDst, reg0, const0]; --a+0+Carry0 has result = a, Carry _ 0 drRJNEB[popSrc, reg0, UseLabel8B[badRUADD]]; <> drRUADD[pushDst, const0, reg1]; -- 0+b+Carry0 has result = b, Carry _ 0 drRJNEB[popSrc, reg1, UseLabel8B[badRUADD]]; <> drRUADD[topDst, const2, reg0]; drLIQB[IntToWord[a - 1]]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRUADD]]; drRUADD[topDst, const0, const0]; drJNEBB[1, UseLabel8B[badRUADD]]; }; <> }; SetLabel[enterRUADDTest]; drRUADD[const3, const0, const0]; --Eat garbage Carry value and Carry _ 0. drROR[const3, const0, const0]; --Put 0 in const3, indicating Overflow not expected <> RUADDTest[ 1B, 1B, 0]; RUADDTest[ 2B, 2B, 0]; RUADDTest[ 4B, 4B, 0]; RUADDTest[ 10B, 10B, 0]; RUADDTest[ 20B, 20B, 0]; RUADDTest[ 40B, 40B, 0]; RUADDTest[ 100B, 100B, 0]; RUADDTest[ 200B, 200B, 0]; RUADDTest[ 400B, 400B, 0]; RUADDTest[ 1000B, 1000B, 0]; RUADDTest[ 2000B, 2000B, 0]; RUADDTest[ 4000B, 4000B, 0]; RUADDTest[ 10000B, 10000B, 0]; RUADDTest[ 20000B, 20000B, 0]; RUADDTest[ 40000B, 40000B, 0]; RUADDTest[ 100000B, 100000B, 0]; RUADDTest[ 200000B, 200000B, 0]; RUADDTest[ 400000B, 400000B, 0]; RUADDTest[ 1000000B, 1000000B, 0]; RUADDTest[ 2000000B, 2000000B, 0]; RUADDTest[ 4000000B, 4000000B, 0]; RUADDTest[ 10000000B, 10000000B, 0]; RUADDTest[ 20000000B, 20000000B, 0]; RUADDTest[ 40000000B, 40000000B, 0]; RUADDTest[ 100000000B, 100000000B, 0]; RUADDTest[ 200000000B, 200000000B, 0]; RUADDTest[ 400000000B, 400000000B, 0]; RUADDTest[ 1000000000B, 1000000000B, 0]; RUADDTest[ 2000000000B, 2000000000B, 0]; RUADDTest[ 4000000000B, 4000000000B, 0]; RUADDTest[10000000000B, 10000000000B, 0]; <> RUADDTest[ FIRST[INT], FIRST[INT], 1]; RUADDTest[ 6B, 3B, 0]; RUADDTest[ 30B, 14B, 0]; RUADDTest[ 140B, 60B, 0]; RUADDTest[ 600B, 300B, 0]; RUADDTest[ 3000B, 1400B, 0]; RUADDTest[ 14000B, 6000B, 0]; RUADDTest[ 60000B, 30000B, 0]; RUADDTest[ 300000B, 140000B, 0]; RUADDTest[ 1400000B, 600000B, 0]; RUADDTest[ 6000000B, 3000000B, 0]; RUADDTest[ 30000000B, 14000000B, 0]; RUADDTest[ 140000000B, 60000000B, 0]; RUADDTest[ 1600000000B, 700000000B, 0]; RUADDTest[ 6000000000B, 3000000000B, 0]; RUADDTest[-10000000000B, -4000000000B, 1]; RUADDTest[ -2B, FIRST[INT], 1]; RUADDTest[ 17777777777B, FIRST[INT], 0]; RUADDTest[-17777777777B, 17777777777B, 1]; }; <> <> GenRUSUB: PROC = { <> RUSUBTest: PROC [a, b, ambc: INT] ~ { okRUSUB: Label = GenLabel[]; badRUSUB: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; ambx: Word _ IntToWord[a - b]; -- a - b aminusambcarry: Word _ IntToWord[a - ambc]; mbx: Word _ IntToWord[- b]; -- - b drLIQB[ax]; drLIQB[bx]; drRUSUB[pushDst, reg0, reg1]; drLIQB[ambx]; drRJEBJ[popSrc, belowSrcPop, UseLabel8B[okRUSUB]]; SetLabel[badRUSUB]; Pause[]; SetLabel[okRUSUB]; <> <> drRUSUB[pushDst, reg0, const0]; drLIQB[aminusambcarry]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRUSUB]]; <> <> drRUSUB[pushDst, const0, reg1]; drLIQB[mbx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRUSUB]]; <> <> drRUSUB[topDst, reg0, const2]; drRJNEB[popSrc, reg0, UseLabel8B[badRUSUB]]; drRUADD[topDst, const0, const0]; drJNEBB[1, UseLabel8B[badRUSUB]]; }; SetLabel[enterRUSUBTest]; drRUADD[const3, const0, const0]; --Eat garbage Carry value and Carry _ 0. drROR[const3, const0, const0]; --Put 0 in const3, indicating Overflow not expected <> RUSUBTest[ 1B, 2B, 1]; RUSUBTest[ 2B, 1B, 0]; RUSUBTest[ 1B, 1B, 0]; RUSUBTest[ -2B, -2B, 0]; RUSUBTest[ FIRST[INT], FIRST[INT], 0]; RUSUBTest[17777777777B, 12525252525B, 0]; RUSUBTest[17777777777B, 5252525252B, 0]; RUSUBTest[12525252525B, 5252525252B, 0]; RUSUBTest[12525252525B, 12525252526B, 1]; RUSUBTest[ 5252525252B, 5252525253B, 1]; RUSUBTest[ 1B, 17777777777B, 1]; RUSUBTest[ -1B, 17777777777B, 0]; RUSUBTest[ -2B, 17777777777B, 0]; }; <> GenRVADD: PROC = { <> RVADDTest: PROC [a, b: INT] ~ { okRVADD: Label = GenLabel[]; badRVADD: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; apbx: Word _ IntToWord[a + b]; aminus1: Word _ IntToWord[a - 1]; drLIQB[ax]; drLIQB[bx]; drRVADD[pushDst, reg0, const0]; drRJEBJ[popSrc, reg0, UseLabel8B[okRVADD]]; SetLabel[badRVADD]; Pause[]; SetLabel[okRVADD]; drRVADD[pushDst, const0, reg1]; drRJNEB[popSrc, reg1, UseLabel8B[badRVADD]]; drRVADD[pushDst, const2, reg0]; drLIQB[aminus1]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRVADD]]; drRVADD[belowDst, belowSrc, popSrc]; drLIQB[apbx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRVADD]]; }; SetLabel[enterRVADDTest]; drROR[const3, const0, const0]; --Put 0 in const3, indicating Overflow not expected RVADDTest[ 5B, 5B]; RVADDTest[ 12B, 12B]; RVADDTest[ 120B, 120B]; RVADDTest[ 240B, 240B]; RVADDTest[ 2400B, 2400B]; RVADDTest[ 5000B, 5000B]; RVADDTest[ 50000B, 50000B]; RVADDTest[ 120000B, 120000B]; RVADDTest[ 1200000B, 1200000B]; RVADDTest[ 2400000B, 2400000B]; RVADDTest[ 14000000B, 14000000B]; RVADDTest[ 60000000B, 60000000B]; RVADDTest[ 300000000B, 300000000B]; RVADDTest[ 1400000000B, 1400000000B]; RVADDTest[ 6000000000B, 6000000000B]; RVADDTest[-10000000000B, -10000000000B]; RVADDTest[ -2B, FIRST[INT]]; RVADDTest[ -2B, -2B]; RVADDTest[ -1B, -1B]; RVADDTest[ -1B, 1B]; }; <> GenRVSUB: PROC = { <> RVSUBTest: PROC [a, b: INT] ~ { okRVSUB: Label = GenLabel[]; badRVSUB: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; ambx: Word _ IntToWord[a - b]; mbx: Word _ IF b = FIRST[INT] THEN IntToWord[FIRST[INT]] ELSE IntToWord[- b]; m1mbx: Word _ IntToWord[- 1 - b]; ap1x: Word _ IntToWord[a - (- 1)]; drLIQB[ax]; drLIQB[bx]; drRVSUB[pushDst, reg0, const0]; -- a - 0 drRJEBJ[popSrc, reg0, UseLabel8B[okRVSUB]]; SetLabel[badRVSUB]; Pause[]; SetLabel[okRVSUB]; drRVSUB[pushDst, const0, reg1]; -- 0 - b drLIQB[mbx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRVSUB]]; drRVSUB[pushDst, reg0, const2]; -- a - (-1) drLIQB[ap1x]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRVSUB]]; drRVSUB[pushDst, const2, reg1]; -- (-1) - b drLIQB[m1mbx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRVSUB]]; drRVSUB[belowDst, belowSrc, popSrc]; -- a - b drLIQB[ambx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRVSUB]]; }; SetLabel[enterRVSUBTest]; drROR[const3, const0, const0]; --Put 0 in const3, indicating Overflow not expected RVSUBTest[ 1B, 2B]; RVSUBTest[ 2B, 1B]; RVSUBTest[ 1B, 1B]; RVSUBTest[ -2B, -2B]; RVSUBTest[ FIRST[INT], FIRST[INT]]; RVSUBTest[ 0B, -1B]; RVSUBTest[ -1B, 0B]; RVSUBTest[ FIRST[INT], 0B]; }; GenRADD: PROC = { <> RADDNoOvfC0: PROC [a, b: INT] ~ { okRADD: Label = GenLabel[]; badRADD: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; apbx: Word _ IntToWord[a + b]; drLIQB[ax]; drLIQB[bx]; drRUADD[pushDst, const0, const0]; --Make Carry = 0 drRADD[topDst, reg0, reg1]; drLIQB[apbx]; --a + b + carry0 drRJEBJ[popSrc, belowSrcPop, UseLabel8B[okRADD]]; SetLabel[badRADD]; Pause[]; SetLabel[okRADD]; drRADD[belowDst, topSrc, belowSrcPop]; drLIQB[apbx]; --b + a + carry0 drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRADD]]; }; <> RADDNoOvfC1: PROC [a, b: INT] ~ { okRADD: Label = GenLabel[]; badRADD: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; apbp1x: Word _ IntToWord[a + b + 1]; drLIQB[ax]; drLIQB[bx]; drRUADD[pushDst, const2, const2]; --Make Carry = 1 drRADD[topDst, reg0, reg1]; drLIQB[apbp1x]; --a + b + carry1 drRJEBJ[popSrc, belowSrcPop, UseLabel8B[okRADD]]; SetLabel[badRADD]; Pause[]; SetLabel[okRADD]; drRUADD[const5, const2, const2]; --Make Carry = 1 drRADD[belowDst, belowSrc, popSrc]; drLIQB[apbp1x]; --b + a + carry1 drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRADD]]; }; <> RADDOvfC0: PROC [a, b: INT] ~ { okRADD: Label = GenLabel[]; badRADD: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; drLIQB[ax]; drLIQB[bx]; <> drRUADD[pushDst, const2, const2]; --Carry _ 1 drRUADD[topDst, const0, const0]; --Carry _ 0, [S] _ 1 drRADD[topDst, reg1, reg0]; --b + a + carry0 Pause[]; --Overflow trap skips this <> drJEBBJ[1, UseLabel8B[okRADD]]; SetLabel[badRADD]; Pause[]; SetLabel[okRADD]; drLIQB[bx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRADD]]; drLIQB[ax]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRADD]]; }; <> RADDOvfC1: PROC [a, b: INT] ~ { okRADD: Label = GenLabel[]; badRADD: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; drLIQB[ax]; drLIQB[bx]; drRUADD[pushDst, const0, const0]; --Carry _ 0 drRUADD[topDst, const2, const2]; --Carry _ 1, [S] _ -2 drRADD[topDst, reg0, reg1]; --a + b + carry1 Pause[]; --Overflow trap skips this <> drLIQB[IntToWord[-2]]; drRJEBJ[popSrc, belowSrcPop, UseLabel8B[okRADD]]; Pause[]; SetLabel[okRADD]; drLIQB[bx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRADD]]; drLIQB[ax]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRADD]]; }; SetLabel[enterRADDTest]; drRUADD[const3, const0, const0]; --Eat garbage carry value and Carry _ 0 <> drROR[const3, const0, const0]; --const3 = 0 means Overflow not expected RADDNoOvfC0[ 7777777777B, 7777777777B]; RADDNoOvfC1[ 7777777777B, 7777777777B]; RADDNoOvfC0[10000000000B, 7777777777B]; RADDNoOvfC0[ 5252525252B, 2525252525B]; RADDNoOvfC1[ 5252525252B, 2525252525B]; RADDNoOvfC0[17777777776B, 0B]; RADDNoOvfC1[17777777776B, 0B]; RADDNoOvfC0[-10000000000B, -10000000000B]; RADDNoOvfC1[-10000000000B, -10000000000B]; RADDNoOvfC1[-10000000000B, -10000000001B]; RADDNoOvfC0[-17777777777B, -1B]; RADDNoOvfC1[-17777777777B, -2B]; RADDNoOvfC1[ -2B, -17777777777B]; drROR[const3, const2, const2]; --const3 = -1 means Overflow expected RADDOvfC0[17777777777B, 1B]; RADDOvfC1[17777777777B, 1B]; RADDOvfC0[10000000000B, 10000000000B]; RADDOvfC1[10000000000B, 10000000000B]; RADDOvfC1[10000000000B, 7777777777B]; RADDOvfC1[12525252525B, 5252525252B]; RADDOvfC0[-17777777777B, -2B]; RADDOvfC0[ -2B, -17777777777B]; RADDOvfC0[-10000000000B, -10000000001B]; }; GenRSUB: PROC = { <> RSUBNoOvfC0: PROC [a, b: INT] ~ { okRSUB0: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; ambx: Word _ IntToWord[a - b]; drLIQB[ax]; drLIQB[bx]; drRUADD[const5, const0, const0]; --Make Carry = 0 drRSUB[belowDst, belowSrc, popSrc]; drLIQB[ambx]; drRJEBJ[popSrc, belowSrcPop, UseLabel8B[okRSUB0]]; Pause[]; SetLabel[okRSUB0]; }; <> RSUBNoOvfC1: PROC [a, b: INT] ~ { okRSUB0: Label = GenLabel[]; okRSUB1: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; ambm1x: Word _ IntToWord[a - b - 1]; drLIQB[ax]; drLIQB[bx]; drRUADD[const5, const2, const2]; --Make Carry = 1 drRSUB[belowDst, belowSrc, popSrc]; drLIQB[ambm1x]; drRJEBJ[popSrc, belowSrcPop, UseLabel8B[okRSUB0]]; Pause[]; SetLabel[okRSUB0]; }; RSUBOvfC0: PROC [a, b: INT] ~ { okRSUB: Label = GenLabel[]; badRSUB: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; drRUADD[const5, const0, const0]; --Carry _ 0 drLIQB[ax]; drLIQB[bx]; drRSUB[belowDst, belowSrc, popSrc]; --a - b - carry0 Pause[]; --Overflow trap skips this <> drRUADD[pushDst, const0, const0]; drJEBBJ[0, UseLabel8B[okRSUB]]; SetLabel[badRSUB]; Pause[]; SetLabel[okRSUB]; drLIQB[bx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRSUB]]; drLIQB[ax]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRSUB]]; }; RSUBOvfC1: PROC [a, b: INT] ~ { okRSUB: Label = GenLabel[]; badRSUB: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; drRUADD[const5, const2, const2]; drLIQB[ax]; drLIQB[bx]; drRSUB[pushDst, reg0, reg1]; --a - b - carry1 Pause[]; --Overflow trap skips this <> drRUADD[pushDst, const0, const0]; --writes 0 + 0 + carry1 drJEBBJ[1, UseLabel8B[okRSUB]]; SetLabel[badRSUB]; Pause[]; SetLabel[okRSUB]; drLIQB[bx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRSUB]]; drLIQB[ax]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badRSUB]]; }; SetLabel[enterRSUBTest]; drRUADD[const3, const0, const0]; --Eat garbage carry value and Carry _ 0 <> drROR[const3, const0, const0]; --const3 = 0 means Overflow not expected RSUBNoOvfC0[10000000000B, 10000000000B]; RSUBNoOvfC1[10000000000B, 10000000000B]; RSUBNoOvfC1[10000000000B, -10000000000B]; RSUBNoOvfC1[17777777777B, 12525252525B]; RSUBNoOvfC0[17777777777B, 12525252525B]; RSUBNoOvfC1[17777777777B, 5252525252B]; RSUBNoOvfC0[17777777777B, 5252525252B]; RSUBNoOvfC1[ 3333333333B, 2222222222B]; RSUBNoOvfC0[ 3333333333B, 2222222222B]; RSUBNoOvfC1[ 1111111111B, 2222222222B]; RSUBNoOvfC0[ 1111111111B, 3333333333B]; RSUBNoOvfC1[-1111111111B, 12222222222B]; RSUBNoOvfC0[-1111111111B, 13333333333B]; RSUBNoOvfC1[17777777777B, -1B]; RSUBNoOvfC0[-10000000000B, 10000000000B]; drROR[const3, const2, const2]; --const3 = -1 means Overflow expected RSUBOvfC0[FIRST[INT], 1B]; RSUBOvfC1[FIRST[INT], 1B]; RSUBOvfC0[17777777777B, -1B]; RSUBOvfC0[10000000000B, -10000000000B]; RSUBOvfC1[-10000000000B, 10000000000B]; }; GenADD: PROC = { <> ADDNoOvfTest: PROC [a, b: INT] ~ { okADD: Label = GenLabel[]; badADD: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; apbp1x: Word _ IntToWord[a + b + 1]; apbx: Word _ IntToWord[a + b]; drRUADD[const4, const2, const2]; drLIQB[ax]; drLIQB[bx]; drADD[]; drLIQB[apbp1x]; drRJEBJ[popSrc, belowSrcPop, UseLabel8B[okADD]]; SetLabel[badADD]; Pause[]; SetLabel[okADD]; drLIQB[ax]; drLIQB[bx]; drADD[]; drLIQB[apbx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badADD]]; }; ADDOvfTest: PROC [a, b: INT] ~ { okADD: Label = GenLabel[]; badADD: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; drRUADD[const4, const2, const2]; drLIQB[ax]; drLIQB[bx]; drADD[]; --a + b + carry1 Pause[]; Pause[]; Pause[]; --Overflow trap skips these drRUADD[const4, const0, const0]; drADD[]; --a + b + carry0 Pause[]; Pause[]; Pause[]; --Overflow trap skips these <> drLIB[1]; drRJEBJ[popSrc, const4, UseLabel8B[okADD]]; SetLabel[badADD]; Pause[]; SetLabel[okADD]; drLIQB[bx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badADD]]; drLIQB[ax]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badADD]]; }; SetLabel[enterADDTest]; drRUADD[const3, const0, const0]; --Eat garbage carry value and Carry _ 0 <> drROR[const3, const0, const0]; --const3 = 0 means Overflow not expected ADDNoOvfTest[FIRST[INT], 17777777776B]; ADDNoOvfTest[12312323456B, 1231231231B]; drROR[const3, const2, const2]; --const3 = -1 means Overflow expected ADDOvfTest[10000000000B, 10000000000B]; ADDOvfTest[-10000000001B, -10000000001B]; ADDOvfTest[ 1B, 17777777777B]; }; GenSUB: PROC = { <> SUBNoOvfTest: PROC [a, b: INT] ~ { okSUB: Label = GenLabel[]; badSUB: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; ambm1x: Word _ IntToWord[a - b - 1]; ambx: Word _ IntToWord[a - b]; drRUADD[const4, const2, const2]; drLIQB[ax]; drLIQB[bx]; drSUB[]; drLIQB[ambm1x]; drRJEBJ[popSrc, belowSrcPop, UseLabel8B[okSUB]]; SetLabel[badSUB]; Pause[]; SetLabel[okSUB]; drLIQB[ax]; drLIQB[bx]; drSUB[]; drLIQB[ambx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badSUB]]; }; SUBOvfTest: PROC [a, b: INT] ~ { okSUB: Label = GenLabel[]; badSUB: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; drRUADD[const4, const2, const2]; drLIQB[ax]; drLIQB[bx]; drSUB[]; --a - b - carry1 Pause[]; Pause[]; Pause[]; --Overflow trap skips these. drRUADD[const4, const0, const0]; drSUB[]; --a - b - carry0 Pause[]; Pause[]; Pause[]; --Overflow trap skips these. <> drLIB[1]; drRJEBJ[popSrc, const4, UseLabel8B[okSUB]]; SetLabel[badSUB]; Pause[]; SetLabel[okSUB]; drLIQB[bx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badSUB]]; drLIQB[ax]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badSUB]]; }; SetLabel[enterSUBTest]; drRUADD[const3, const0, const0]; --Eat garbage carry value and Carry _ 0 drROR[const3, const0, const0]; --const3 = 0 means Overflow not expected SUBNoOvfTest[10000000000B, 10000000000B]; SUBNoOvfTest[17777777777B, 0B]; SUBNoOvfTest[-17777777777B, 0B]; SUBNoOvfTest[ -1B, 17777777776B]; drROR[const3, const2, const2]; --const3 = -1 means Overflow expected SUBOvfTest[FIRST[INT], 1B]; SUBOvfTest[17777777777B, -2B]; SUBOvfTest[ -2B, 17777777777B]; }; GenADDB: PROC = { <> ADDBNoOvfTest: PROC [a, b: INT] ~ { okADDB: Label = GenLabel[]; badADDB: Label = GenLabel[]; ax: Word _ IntToWord[a]; apbp1x: Word _ IntToWord[a + b + 1]; apbx: Word _ IntToWord[a + b]; drRUADD[const4, const2, const2]; drLIQB[ax]; drADDB[b]; drLIQB[apbp1x]; drRJEBJ[popSrc, belowSrcPop, UseLabel8B[okADDB]]; SetLabel[badADDB]; Pause[]; SetLabel[okADDB]; drLIQB[ax]; drADDB[b]; drLIQB[apbx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badADDB]]; }; ADDBOvfTest: PROC [a, b: INT] ~ { okADDB: Label = GenLabel[]; badADDB: Label = GenLabel[]; ax: Word _ IntToWord[a]; drRUADD[const4, const2, const2]; drLIQB[ax]; drADDB[b]; --a + b + carry1 Pause[]; Pause[]; --Overflow trap skips these. drRUADD[const4, const0, const0]; drADDB[b]; --a + b + carry0 Pause[]; Pause[]; --Overflow trap skips these. <> drLIB[1]; drRJEBJ[popSrc, const4, UseLabel8B[okADDB]]; SetLabel[badADDB]; Pause[]; SetLabel[okADDB]; drLIQB[ax]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badADDB]]; }; SetLabel[enterADDBTest]; <> drROR[const3, const0, const0]; --const3 = 0 means Overflow not expected ADDBNoOvfTest[ 10000000000B, 377B]; ADDBNoOvfTest[ 7777777777B, 0B]; ADDBNoOvfTest[ 17777777776B, 0B]; ADDBNoOvfTest[-17777777776B, 377B]; ADDBNoOvfTest[-17777777776B, 0B]; ADDBNoOvfTest[-17777777777B, 0B]; ADDBNoOvfTest[-17777777777B, 1B]; ADDBNoOvfTest[ 13777777777B, 1B]; ADDBNoOvfTest[ 15777777777B, 1B]; ADDBNoOvfTest[ 16777777777B, 1B]; ADDBNoOvfTest[ 17377777777B, 1B]; ADDBNoOvfTest[ 17577777777B, 1B]; ADDBNoOvfTest[ 17677777777B, 1B]; ADDBNoOvfTest[ 17737777777B, 1B]; ADDBNoOvfTest[ 17757777777B, 1B]; ADDBNoOvfTest[ 17767777777B, 1B]; ADDBNoOvfTest[ 17773777777B, 1B]; ADDBNoOvfTest[ 17775777777B, 1B]; ADDBNoOvfTest[ 17776777777B, 1B]; ADDBNoOvfTest[ 17777377777B, 1B]; ADDBNoOvfTest[ 17777577777B, 1B]; ADDBNoOvfTest[ 17777677777B, 1B]; ADDBNoOvfTest[ 17777737777B, 1B]; ADDBNoOvfTest[ 17777757777B, 1B]; ADDBNoOvfTest[ 17777767777B, 1B]; ADDBNoOvfTest[ 17777773777B, 1B]; ADDBNoOvfTest[ 17777775777B, 1B]; ADDBNoOvfTest[ 17777776777B, 1B]; ADDBNoOvfTest[ 17777777377B, 1B]; ADDBNoOvfTest[ 17777777577B, 1B]; ADDBNoOvfTest[ 17777777677B, 1B]; ADDBNoOvfTest[ 17777777737B, 1B]; ADDBNoOvfTest[ 17777777757B, 1B]; ADDBNoOvfTest[ 17777777767B, 1B]; ADDBNoOvfTest[ 17777777773B, 1B]; ADDBNoOvfTest[ 17777777775B, 1B]; drROR[const3, const2, const2]; --const3 = -1 means Overflow expected ADDBOvfTest[17777777776B, 2B]; ADDBOvfTest[17777777777B, 1B]; ADDBOvfTest[17777777401B, 377B]; }; GenSUBB: PROC = { <> SUBBNoOvfTest: PROC [a, b: INT] ~ { okSUBB: Label = GenLabel[]; badSUBB: Label = GenLabel[]; ax: Word _ IntToWord[a]; ambm1x: Word _ IntToWord[a - b - 1]; ambx: Word _ IntToWord[a - b]; drRUADD[const4, const2, const2]; drLIQB[ax]; drSUBB[b]; drLIQB[ambm1x]; drRJEBJ[popSrc, belowSrcPop, UseLabel8B[okSUBB]]; SetLabel[badSUBB]; Pause[]; SetLabel[okSUBB]; drLIQB[ax]; drSUBB[b]; drLIQB[ambx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badSUBB]]; }; SUBBOvfTest: PROC [a, b: INT] ~ { okSUBB: Label = GenLabel[]; badSUBB: Label = GenLabel[]; ax: Word _ IntToWord[a]; drRUADD[const4, const2, const2]; drLIQB[ax]; drSUBB[b]; --a - b - carry1 Pause[]; Pause[]; --Overflow trap skips these. drRUADD[const4, const0, const0]; drSUBB[b]; --a - b - carry0 Pause[]; Pause[]; --Overflow trap skips these. <> drLIB[1]; drRJEBJ[popSrc, const4, UseLabel8B[okSUBB]]; SetLabel[badSUBB]; Pause[]; SetLabel[okSUBB]; drLIQB[ax]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badSUBB]]; }; SetLabel[enterSUBBTest]; drRUADD[const3, const0, const0]; --Eat garbage carry value and Carry _ 0 <> drROR[const3, const0, const0]; --const3 = 0 means Overflow not expected SUBBNoOvfTest[17777777777B, 2B]; SUBBNoOvfTest[-17777777777B, 0B]; SUBBNoOvfTest[-17777777400B, 377B]; drROR[const3, const2, const2]; --const3 = -1 means Overflow expected SUBBOvfTest[FIRST[INT], 1B]; SUBBOvfTest[-17777777402B, 377B]; }; GenADDDB: PROC = { <> ADDDBNoOvfTest: PROC [a, b: INT] ~ { okADDDB: Label = GenLabel[]; badADDDB: Label = GenLabel[]; ax: Word _ IntToWord[a]; apbp1x: Word _ IntToWord[a + b + 1]; apbx: Word _ IntToWord[a + b]; drRUADD[const4, const2, const2]; drLIQB[ax]; drADDDB[b]; drLIQB[apbp1x]; drRJEBJ[popSrc, belowSrcPop, UseLabel8B[okADDDB]]; SetLabel[badADDDB]; Pause[]; SetLabel[okADDDB]; drLIQB[ax]; drADDDB[b]; drLIQB[apbx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badADDDB]]; }; ADDDBOvfTest: PROC [a, b: INT] ~ { okADDDB: Label = GenLabel[]; badADDDB: Label = GenLabel[]; ax: Word _ IntToWord[a]; drRUADD[const4, const2, const2]; drLIQB[ax]; drADDDB[b]; --a + b + carry1 Pause[]; --Overflow trap skips these. drRUADD[const4, const0, const0]; drADDDB[b]; --a + b + carry0 Pause[]; --Overflow trap skips these. <> drLIB[1]; drRJEBJ[popSrc, const4, UseLabel8B[okADDDB]]; SetLabel[badADDDB]; Pause[]; SetLabel[okADDDB]; drLIQB[ax]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badADDDB]]; }; SetLabel[enterADDDBTest]; drRUADD[const3, const0, const0]; --Eat garbage carry value and Carry _ 0 <> drROR[const3, const0, const0]; --const3 = 0 means Overflow not expected ADDDBNoOvfTest[17777600000B, 177776B]; ADDDBNoOvfTest[17777577777B, 177777B]; ADDDBNoOvfTest[17777777776B, 0B]; ADDDBNoOvfTest[17777777775B, 1B]; ADDDBNoOvfTest[12345671234B, 123456B]; drROR[const3, const2, const2]; --const3 = -1 means Overflow expected ADDDBOvfTest[17777777777B, 1B]; ADDDBOvfTest[17777600001B, 177777B]; }; GenSUBDB: PROC = { <> SUBDBNoOvfTest: PROC [a, b: INT] ~ { okSUBDB: Label = GenLabel[]; badSUBDB: Label = GenLabel[]; ax: Word _ IntToWord[a]; ambm1x: Word _ IntToWord[a - b - 1]; ambx: Word _ IntToWord[a - b]; drRUADD[const4, const2, const2]; drLIQB[ax]; drSUBDB[b]; drLIQB[ambm1x]; drRJEBJ[popSrc, belowSrcPop, UseLabel8B[okSUBDB]]; SetLabel[badSUBDB]; Pause[]; SetLabel[okSUBDB]; drLIQB[ax]; drSUBDB[b]; drLIQB[ambx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badSUBDB]]; }; SUBDBOvfTest: PROC [a, b: INT] ~ { okSUBDB: Label = GenLabel[]; badSUBDB: Label = GenLabel[]; ax: Word _ IntToWord[a]; drRUADD[const4, const2, const2]; drLIQB[ax]; drSUBDB[b]; --a - b - carry1 Pause[]; --Overflow trap skips this. drRUADD[const4, const0, const0]; drSUBDB[b]; --a - b - carry0 Pause[]; --Overflow trap skips this. <> drLIB[1]; drRJEBJ[popSrc, const4, UseLabel8B[okSUBDB]]; SetLabel[badSUBDB]; Pause[]; SetLabel[okSUBDB]; drLIQB[ax]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badSUBDB]]; }; SetLabel[enterSUBDBTest]; drRUADD[const3, const0, const0]; --Eat garbage carry value and Carry _ 0 <> drROR[const3, const0, const0]; --const3 = 0 means Overflow not expected SUBDBNoOvfTest[ 17777777777B, 177777B]; SUBDBNoOvfTest[ 10000000000B, 177777B]; SUBDBNoOvfTest[ 0B, 177777B]; SUBDBNoOvfTest[ 0B, 0B]; SUBDBNoOvfTest[-17777777777B, 0B]; SUBDBNoOvfTest[-17777600000B, 177777B]; drROR[const3, const2, const2]; --const3 = -1 means Overflow expected SUBDBOvfTest[-17777777777B, 2B]; SUBDBOvfTest[-17777777777B, 177777B]; SUBDBOvfTest[-17777600002B, 177777B]; }; GenQADD: PROC = { <> QADDNoOvfTest: PROC [a, b: INT] ~ { okQADD: Label = GenLabel[]; badQADD: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; apbp1x: Word _ IntToWord[a + b + 1]; apbx: Word _ IntToWord[a + b]; drLIQB[ax]; drLIQB[bx]; drRUADD[const4, const2, const2]; --Carry _ 1 drQADD[pushAtop, reg0]; drLIQB[apbp1x]; drRJEBJ[popSrc, belowSrcPop, UseLabel8B[okQADD]]; SetLabel[badQADD]; Pause[]; SetLabel[okQADD]; drRUADD[const4, const0, const0]; --Carry _ 0 drQADD[pushAtop, reg0]; drLIQB[apbx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badQADD]]; drAS[376B]; }; QADDOvfTest: PROC [a, b: INT] ~ { okQADD: Label = GenLabel[]; badQADD: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; drLIQB[ax]; drLIQB[bx]; drRUADD[const4, const2, const2]; drQADD[pushAtop, reg0]; --a + b + carry1 Pause[]; Pause[]; --Overflow trap skips these drRUADD[const4, const0, const0]; drQADD[pushAtop, reg0]; --a + b + carry0 Pause[]; Pause[]; --Overflow trap skips these <> drLIB[1]; drRJEBJ[popSrc, const4, UseLabel8B[okQADD]]; SetLabel[badQADD]; Pause[]; SetLabel[okQADD]; drLIQB[bx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badQADD]]; drLIQB[ax]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badQADD]]; }; SetLabel[enterQADDTest]; drRUADD[const3, const0, const0]; --Eat garbage carry value and Carry _ 0 <> drROR[const3, const0, const0]; --const3 = 0 means Overflow not expected QADDNoOvfTest[10000000000B, 7777777776B]; QADDNoOvfTest[17777777776B, 0B]; QADDNoOvfTest[-17777777777B, -1B]; drROR[const3, const2, const2]; --const3 = -1 means Overflow expected QADDOvfTest[10000000000B, 10000000000B]; QADDOvfTest[17777777777B, 1B]; QADDOvfTest[-17777777777B, -3B]; }; GenQSUB: PROC = { <> QSUBNoOvfTest: PROC [a, b: INT] ~ { okQSUB: Label = GenLabel[]; badQSUB: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; ambm1x: Word _ IntToWord[a - b - 1]; ambx: Word _ IntToWord[a - b]; drLIQB[bx]; drLIQB[ax]; drRUADD[const4, const2, const2]; --Carry _ 1 drQSUB[pushAtop, reg0]; drLIQB[ambm1x]; drRJEBJ[popSrc, belowSrcPop, UseLabel8B[okQSUB]]; SetLabel[badQSUB]; Pause[]; SetLabel[okQSUB]; drRUADD[const4, const0, const0]; --Carry _ 0 drQSUB[pushAtop, reg0]; drLIQB[ambx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badQSUB]]; drAS[376B]; }; QSUBOvfTest: PROC [a, b: INT] ~ { okQSUB: Label = GenLabel[]; badQSUB: Label = GenLabel[]; ax: Word _ IntToWord[a]; bx: Word _ IntToWord[b]; drLIQB[bx]; drLIQB[ax]; drRUADD[const4, const2, const2]; drQSUB[pushAtop, reg0]; --a - b - carry1 Pause[]; Pause[]; --Overflow trap skips these. drRUADD[const4, const0, const0]; drQSUB[pushAtop, reg0]; --a - b - carry0 Pause[]; Pause[]; --Overflow trap skips these. <> drLIB[1]; drRJEBJ[popSrc, const4, UseLabel8B[okQSUB]]; SetLabel[badQSUB]; Pause[]; SetLabel[okQSUB]; drLIQB[ax]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badQSUB]]; drLIQB[bx]; drRJNEB[popSrc, belowSrcPop, UseLabel8B[badQSUB]]; }; SetLabel[enterQSUBTest]; drRUADD[const3, const0, const0]; --Eat garbage carry value and Carry _ 0 <> drROR[const3, const0, const0]; --const3 = 0 means Overflow not expected QSUBNoOvfTest[10000000000B, 10000000000B]; QSUBNoOvfTest[10000000000B, -7777777777B]; QSUBNoOvfTest[12233445566B, -2134567770B]; drROR[const3, const2, const2]; --const3 = -1 means Overflow expected QSUBOvfTest[10000000001B, -10000000000B]; QSUBOvfTest[10000000000B, -10000000001B]; QSUBOvfTest[ 7777777777B, -10000000002B]; }; WordAlign[area]; SetLabel[dummy]; Pause[]; Pause[]; Pause[]; Pause[]; Pause[]; Halt[123B]; <> WordAlign[area]; SetLabel[ALUOverflow]; drALS[0]; --ALS[1 - nargs], where nargs includes 1 for IFUstatus drLC3[]; drRJNEB[popSrc, const2, UseLabel8B[ALUOvfUnexpected]]; <> GetYoungestPC[]; --Advance return PC by 4 drRVADD[topDst, topSrc, const6]; SetYoungestPC[]; drRETK[377B]; --RETK[nResults - 1] SetLabel[ALUOvfUnexpected]; Pause[]; <> <> savePC _ GetOutputPC[area]; FillTrap[ResetTrap, start]; FillTrap[ALUCondOver, ALUOverflow]; FillXop[0, dummy]; FillXop[377B, dummy]; SetOutputPC[savePC]; WordAlign[area]; SetLabel[start]; --Simulator execution begins here on a Reset. <> drASL[255]; <> drLIQB[IntToWord[-1]]; drROR[const2, topSrc, popSrc]; --Put -1 in const2. drLIB[4]; drROR[const6, topSrc, popSrc]; --Put 4 in const6 for overflow trap GenRUADD[]; GenRUSUB[]; GenRVADD[]; GenRVSUB[]; GenRADD[]; GenRSUB[]; GenADD[]; GenSUB[]; GenADDB[]; GenSUBB[]; GenADDDB[]; GenSUBDB[]; GenQADD[]; GenQSUB[]; Halt[177777B]; --Terminate here at the end of the program }; END.