This source file includes following definitions.
- get_Cr
- op_desc_str
- do_ITP
- do_ITS
- do_ITS_ITP
- updateIWB
- do_caf
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 #include <stdio.h>
23 #include "dps8.h"
24 #include "dps8_addrmods.h"
25 #include "dps8_sys.h"
26 #include "dps8_faults.h"
27 #include "dps8_scu.h"
28 #include "dps8_iom.h"
29 #include "dps8_cable.h"
30 #include "dps8_cpu.h"
31 #include "dps8_append.h"
32 #include "dps8_ins.h"
33 #include "dps8_iefp.h"
34 #include "dps8_opcodetable.h"
35 #include "dps8_utils.h"
36 #if defined(THREADZ) || defined(LOCKLESS)
37 # include "threadz.h"
38 #endif
39
40 #define DBG_CTR cpu.cycleCnt
41
42
43
44
45
46
47
48 static word18 get_Cr (word4 Tdes)
49 {
50 cpu.ou.directOperandFlag = false;
51
52 if (Tdes == TD_N)
53 return 0;
54
55 if (Tdes & 010)
56 return cpu.rX [X (Tdes)];
57
58 switch (Tdes)
59 {
60 case TD_N:
61 return 0;
62
63 case TD_AU:
64 #ifdef TESTING
65 HDBGRegAR ("au");
66 #endif
67 return GETHI (cpu.rA);
68
69 case TD_QU:
70 #ifdef TESTING
71 HDBGRegAR ("qu");
72 #endif
73 return GETHI (cpu.rQ);
74
75 case TD_DU:
76 cpu.ou.directOperand = 0;
77 SETHI (cpu.ou.directOperand, cpu.rY);
78 cpu.ou.directOperandFlag = true;
79
80 sim_debug (DBG_ADDRMOD, & cpu_dev,
81 "%s(TD_DU): rY=%06o directOperand=%012"PRIo64"\n",
82 __func__, cpu.rY, cpu.ou.directOperand);
83
84 return 0;
85
86 case TD_IC:
87 return cpu.PPR.IC;
88
89 case TD_AL:
90 #ifdef TESTING
91 HDBGRegAR ("al");
92 #endif
93 return GETLO (cpu.rA);
94
95 case TD_QL:
96 #ifdef TESTING
97 HDBGRegAR ("ql");
98 #endif
99 return GETLO (cpu.rQ);
100
101 case TD_DL:
102 cpu.ou.directOperand = 0;
103 SETLO (cpu.ou.directOperand, cpu.rY);
104 cpu.ou.directOperandFlag = true;
105
106 sim_debug (DBG_ADDRMOD, & cpu_dev,
107 "%s(TD_DL): rY=%06o directOperand=%012"PRIo64"\n",
108 __func__, cpu.rY, cpu.ou.directOperand);
109
110 return 0;
111 }
112 return 0;
113 }
114
115 static char * op_desc_str (char * temp)
116 {
117 DCDstruct * i = & cpu.currentInstruction;
118
119 strcpy (temp, "");
120
121 if (READOP (i))
122 {
123 switch (operand_size ())
124 {
125 case 1:
126 strcat (temp, "readCY");
127 break;
128
129 case 2:
130 strcat (temp, "readCYpair2");
131 break;
132
133 case 8:
134 strcat (temp, "readCYblock8");
135 break;
136
137 case 16:
138 strcat (temp, "readCYblock16");
139 break;
140
141 case 32:
142 strcat (temp, "readCYblock32");
143 break;
144 }
145 }
146
147 if (WRITEOP (i))
148 {
149 if (strlen (temp))
150 strcat (temp, "/");
151
152 switch (operand_size ())
153 {
154 case 1:
155 strcat (temp, "writeCY");
156 break;
157
158 case 2:
159 strcat (temp, "writeCYpair2");
160 break;
161
162 case 8:
163 strcat (temp, "writeCYblock8");
164 break;
165
166 case 16:
167 strcat (temp, "writeCYblock16");
168 break;
169
170 case 32:
171 strcat (temp, "writeCYblock32");
172 break;
173 }
174 }
175
176 if (TRANSOP (i))
177 {
178 if (strlen (temp))
179 strcat (temp, "/");
180
181 strcat (temp, "prepareCA (TRA)");
182 }
183
184 if (! READOP (i) && ! WRITEOP (i) && ! TRANSOP (i) &&
185 i -> info -> flags & PREPARE_CA)
186 {
187 if (strlen (temp))
188 strcat (temp, "/");
189
190 strcat (temp, "prepareCA");
191 }
192
193 return temp;
194 }
195
196 static void do_ITP (void)
197 {
198 sim_debug (DBG_APPENDING, & cpu_dev,
199 "ITP Pair: PRNUM=%o BITNO=%o WORDNO=%o MOD=%o\n",
200 GET_ITP_PRNUM (cpu.itxPair), GET_ITP_WORDNO (cpu.itxPair),
201 GET_ITP_BITNO (cpu.itxPair), GET_ITP_MOD (cpu.itxPair));
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219 word3 n = GET_ITP_PRNUM (cpu.itxPair);
220 CPTUR (cptUsePRn + n);
221 #ifdef TESTING
222 HDBGRegPRR (n, "ITP");
223 #endif
224 cpu.TPR.TSR = cpu.PR[n].SNR;
225 cpu.TPR.TRR = max3 (cpu.PR[n].RNR, cpu.RSDWH_R1, cpu.TPR.TRR);
226 cpu.TPR.TBR = GET_ITP_BITNO (cpu.itxPair);
227 cpu.TPR.CA = cpu.PAR[n].WORDNO + GET_ITP_WORDNO (cpu.itxPair);
228 cpu.TPR.CA &= AMASK;
229 cpu.rY = cpu.TPR.CA;
230
231 cpu.rTAG = GET_ITP_MOD (cpu.itxPair);
232
233 cpu.cu.itp = 1;
234 cpu.cu.TSN_PRNO[0] = n;
235 cpu.cu.TSN_VALID[0] = 1;
236
237 return;
238 }
239
240 static void do_ITS (void)
241 {
242 sim_debug (DBG_APPENDING, & cpu_dev,
243 "ITS Pair: SEGNO=%o RN=%o WORDNO=%o BITNO=%o MOD=%o\n",
244 GET_ITS_SEGNO (cpu.itxPair), GET_ITS_RN (cpu.itxPair),
245 GET_ITS_WORDNO (cpu.itxPair), GET_ITS_BITNO (cpu.itxPair),
246 GET_ITS_MOD (cpu.itxPair));
247
248
249
250
251
252
253
254
255
256
257
258
259
260 cpu.TPR.TSR = GET_ITS_SEGNO (cpu.itxPair);
261
262 sim_debug (DBG_APPENDING, & cpu_dev,
263 "ITS Pair Ring: RN %o RSDWH_R1 %o TRR %o max %o\n",
264 GET_ITS_RN (cpu.itxPair), cpu.RSDWH_R1, cpu.TPR.TRR,
265 max3 (GET_ITS_RN (cpu.itxPair), cpu.RSDWH_R1, cpu.TPR.TRR));
266
267 cpu.TPR.TRR = max3 (GET_ITS_RN (cpu.itxPair), cpu.RSDWH_R1, cpu.TPR.TRR);
268 cpu.TPR.TBR = GET_ITS_BITNO (cpu.itxPair);
269 cpu.TPR.CA = GET_ITS_WORDNO (cpu.itxPair);
270 cpu.TPR.CA &= AMASK;
271
272 cpu.rY = cpu.TPR.CA;
273
274 cpu.rTAG = GET_ITS_MOD (cpu.itxPair);
275
276 cpu.cu.its = 1;
277
278 return;
279 }
280
281
282 static void do_ITS_ITP (void)
283 {
284 word6 ind_tag = GET_TAG (cpu.itxPair [0]);
285
286 sim_debug (DBG_APPENDING, & cpu_dev,
287 "do_ITS/ITP: %012"PRIo64" %012"PRIo64"\n",
288 cpu.itxPair[0], cpu.itxPair[1]);
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311 if (ISITS (ind_tag))
312 do_ITS ();
313 else
314 do_ITP ();
315
316
317 cpu.cu.XSF = 1;
318 sim_debug (DBG_APPENDING, & cpu_dev, "do_ITS_ITP sets XSF to 1\n");
319 }
320
321 void updateIWB (word18 addr, word6 tag)
322 {
323 word36 * wb;
324 if (USE_IRODD)
325 wb = & cpu.cu.IRODD;
326 else
327 wb = & cpu.cu.IWB;
328 sim_debug (DBG_ADDRMOD, & cpu_dev,
329 "updateIWB: IWB was %012"PRIo64" %06o %s\n",
330 * wb, GET_ADDR (* wb),
331 extMods [GET_TAG (* wb)].mod);
332
333 putbits36_18 (wb, 0, addr);
334 putbits36_6 (wb, 30, tag);
335 putbits36_1 (wb, 29, 0);
336
337 sim_debug (DBG_ADDRMOD, & cpu_dev,
338 "updateIWB: IWB now %012"PRIo64" %06o %s\n",
339 * wb, GET_ADDR (* wb),
340 extMods [GET_TAG (* wb)].mod);
341
342 decode_instruction (IWB_IRODD, & cpu.currentInstruction);
343 }
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360 void do_caf (void)
361 {
362 if (cpu.currentInstruction.b29 == 0)
363 {
364 cpu.TPR.CA = GET_ADDR (IWB_IRODD);
365 }
366 else
367 {
368 word3 n = GET_PRN(IWB_IRODD);
369 #ifdef TESTING
370 HDBGRegPRR (n, "b29");
371 #endif
372 word15 offset = GET_OFFSET(IWB_IRODD);
373 cpu.TPR.CA = (cpu.PAR[n].WORDNO + SIGNEXT15_18 (offset))
374 & MASK18;
375 }
376 char buf [256];
377 sim_debug (DBG_ADDRMOD, & cpu_dev,
378 "%s(Entry): operType:%s TPR.CA=%06o\n",
379 __func__, op_desc_str (buf), cpu.TPR.CA);
380 sim_debug (DBG_ADDRMOD, & cpu_dev,
381 "%s(Entry): CT_HOLD %o\n",
382 __func__, cpu.cu.CT_HOLD);
383
384 DCDstruct * i = & cpu.currentInstruction;
385
386 word6 Tm = 0;
387 word6 Td = 0;
388
389
390
391 cpu.ou.directOperandFlag = false;
392
393 if (i -> info -> flags & NO_TAG)
394 cpu.rTAG = 0;
395 else
396 cpu.rTAG = GET_TAG (IWB_IRODD);
397
398 int lockupCnt = 0;
399 #define lockupLimit 4096
400
401 startCA:;
402
403 if (++ lockupCnt > lockupLimit)
404 {
405 doFault (FAULT_LUF, fst_zero, "Lockup in addrmod");
406 }
407
408 Td = GET_TD (cpu.rTAG);
409 Tm = GET_TM (cpu.rTAG);
410
411
412
413
414 if (cpu.cu.CT_HOLD)
415 {
416 sim_debug (DBG_ADDRMOD, & cpu_dev,
417 "%s(startCA): restart; CT_HOLD %02o\n",
418 __func__, cpu.cu.CT_HOLD);
419
420 if (cpu.tweaks.isolts_mode &&
421 GET_TM(cpu.cu.CT_HOLD) == TM_IT && GET_TD (cpu.cu.CT_HOLD) == IT_DIC &&
422 cpu.cu.pot == 1 && GET_ADDR (IWB_IRODD) == cpu.TPR.CA)
423 {
424 cpu.TPR.CA--;
425 sim_warn ("%s: correct CA\n", __func__);
426 }
427 if (Tm == TM_IT && (Td == IT_IDC || Td == IT_DIC))
428 {
429 cpu.cu.pot = 1;
430 }
431 }
432 else
433 {
434
435 cpu.cu.its = 0;
436 cpu.cu.itp = 0;
437 cpu.cu.pot = 0;
438 }
439 sim_debug (DBG_ADDRMOD, & cpu_dev,
440 "%s(startCA): TAG=%02o(%s) Tm=%o Td=%o CT_HOLD %02o\n",
441 __func__, cpu.rTAG, get_mod_string (buf, cpu.rTAG), Tm, Td, cpu.cu.CT_HOLD);
442
443 switch (Tm)
444 {
445 case TM_R:
446 goto R_MOD;
447 case TM_RI:
448 goto RI_MOD;
449 case TM_IT:
450 goto IT_MOD;
451 case TM_IR:
452 goto IR_MOD;
453 default:
454 break;
455 }
456
457 sim_printf ("%s(startCA): unknown Tm??? %o\n",
458 __func__, GET_TM (cpu.rTAG));
459 sim_warn ("(startCA): unknown Tmi; can't happen!\n");
460 return;
461
462
463 R_MOD:;
464 {
465 if (Td == TD_N)
466 {
467
468 return;
469 }
470
471 word18 Cr = get_Cr (Td);
472
473 sim_debug (DBG_ADDRMOD, & cpu_dev, "R_MOD: Cr=%06o\n", Cr);
474
475 if (cpu.ou.directOperandFlag)
476 {
477 sim_debug (DBG_ADDRMOD, & cpu_dev,
478 "R_MOD: directOperand = %012"PRIo64"\n",
479 cpu.ou.directOperand);
480 return;
481 }
482
483
484
485 if (cpu.cu.rpt || cpu.cu.rd | cpu.cu.rl)
486 {
487 if (cpu.currentInstruction.b29)
488 {
489 word3 PRn = GET_PRN(IWB_IRODD);
490 #ifdef TESTING
491 HDBGRegPRR (PRn, "rpx b29");
492 #endif
493 CPTUR (cptUsePRn + PRn);
494 cpu.TPR.CA = Cr + cpu.PR [PRn].WORDNO;
495 cpu.TPR.CA &= AMASK;
496 }
497 else
498 {
499 cpu.TPR.CA = Cr;
500 }
501 }
502 else
503 {
504 cpu.TPR.CA += Cr;
505 cpu.TPR.CA &= MASK18;
506 }
507 sim_debug (DBG_ADDRMOD, & cpu_dev, "R_MOD: TPR.CA=%06o\n",
508 cpu.TPR.CA);
509
510 return;
511 }
512
513
514 RI_MOD:;
515 {
516 sim_debug (DBG_ADDRMOD, & cpu_dev, "RI_MOD: Td=%o\n", Td);
517
518 if (Td == TD_DU || Td == TD_DL)
519 doFault (FAULT_IPR, fst_ill_mod,
520 "RI_MOD: Td == TD_DU || Td == TD_DL");
521
522 if (Td != TD_N)
523 {
524 word18 Cr = get_Cr (Td);
525
526
527
528
529 sim_debug (DBG_ADDRMOD, & cpu_dev,
530 "RI_MOD: Cr=%06o CA(Before)=%06o\n", Cr, cpu.TPR.CA);
531
532 if (cpu.cu.rpt || cpu.cu.rd || cpu.cu.rl)
533 {
534 if (cpu.currentInstruction.b29)
535 {
536 word3 PRn = GET_PRN(IWB_IRODD);
537 #ifdef TESTING
538 HDBGRegPRR (PRn, "rpx b29");
539 #endif
540 CPTUR (cptUsePRn + PRn);
541 cpu.TPR.CA = Cr + cpu.PR [PRn].WORDNO;
542 }
543 else
544 {
545 cpu.TPR.CA = Cr;
546 }
547 cpu.TPR.CA &= AMASK;
548 }
549 else
550 {
551 cpu.TPR.CA += Cr;
552 cpu.TPR.CA &= MASK18;
553 }
554 sim_debug (DBG_ADDRMOD, & cpu_dev,
555 "RI_MOD: CA(After)=%06o\n", cpu.TPR.CA);
556 }
557
558
559
560
561 if (GET_TM(cpu.cu.CT_HOLD) == TM_IR)
562 {
563 goto IR_MOD_2;
564 }
565
566
567
568
569 word18 saveCA = cpu.TPR.CA;
570 ReadIndirect ();
571
572 if ((saveCA & 1) == 0 && (ISITP (cpu.itxPair[0]) || ISITS (cpu.itxPair[0])))
573 {
574 do_ITS_ITP ();
575 updateIWB (cpu.TPR.CA, cpu.rTAG);
576 }
577 else
578 {
579 cpu.rTAG = GET_TAG (cpu.itxPair[0]);
580 if (ISITP (cpu.itxPair[0]) || ISITS (cpu.itxPair[0]))
581 {
582 sim_warn ("%s: itp/its at odd address\n", __func__);
583 #ifdef TESTING
584 traceInstruction (0);
585 #endif
586 }
587 if (!(cpu.cu.rpt || cpu.cu.rd || cpu.cu.rl))
588 {
589 updateIWB (GET_ADDR (cpu.itxPair[0]), cpu.rTAG);
590 }
591
592 if (GET_TM (cpu.rTAG) == TM_IT)
593 {
594 if (GET_TD (cpu.rTAG) == IT_F2)
595 {
596 doFault (FAULT_F2, fst_zero, "RI_MOD: IT_F2 (0)");
597 }
598 if (GET_TD (cpu.rTAG) == IT_F3)
599 {
600 doFault (FAULT_F3, fst_zero, "RI_MOD: IT_F3");
601 }
602 }
603 cpu.TPR.CA = GETHI (cpu.itxPair[0]);
604 cpu.rY = cpu.TPR.CA;
605 }
606
607
608
609
610
611
612
613
614
615 sim_debug (DBG_ADDRMOD, & cpu_dev,
616 "RI_MOD: cpu.itxPair[0]=%012"PRIo64
617 " TPR.CA=%06o rTAG=%02o\n",
618 cpu.itxPair[0], cpu.TPR.CA, cpu.rTAG);
619
620
621
622 if (cpu.cu.rpt || cpu.cu.rd || cpu.cu.rl)
623 return;
624
625 goto startCA;
626 }
627
628
629 IR_MOD:;
630 {
631 IR_MOD_1:;
632
633 sim_debug (DBG_ADDRMOD, & cpu_dev,
634 "IR_MOD: CT_HOLD=%o %o\n", cpu.cu.CT_HOLD, Td);
635
636 IR_MOD_2:;
637
638 if (++ lockupCnt > lockupLimit)
639 {
640 doFault (FAULT_LUF, fst_zero, "Lockup in addrmod IR mode");
641 }
642
643 sim_debug (DBG_ADDRMOD, & cpu_dev,
644 "IR_MOD: fetching indirect word from %06o\n",
645 cpu.TPR.CA);
646
647 word18 saveCA = cpu.TPR.CA;
648 ReadIndirect ();
649
650
651 if (GET_TM(cpu.rTAG) == TM_IR)
652 cpu.cu.CT_HOLD = cpu.rTAG;
653
654 if ((saveCA & 1) == 0 && (ISITP (cpu.itxPair[0]) || ISITS (cpu.itxPair[0])))
655 {
656 do_ITS_ITP ();
657 }
658 else
659 {
660 if (ISITP (cpu.itxPair[0]) || ISITS (cpu.itxPair[0]))
661 {
662 sim_warn ("%s: itp/its at odd address\n", __func__);
663 #ifdef TESTING
664 traceInstruction (0);
665 #endif
666 }
667 cpu.TPR.CA = GETHI (cpu.itxPair[0]);
668 cpu.rY = cpu.TPR.CA;
669 cpu.rTAG = GET_TAG (cpu.itxPair[0]);
670 }
671
672 sim_debug (DBG_ADDRMOD, & cpu_dev,
673 "IR_MOD: CT_HOLD=%o\n", cpu.cu.CT_HOLD);
674 Td = GET_TD (cpu.rTAG);
675 Tm = GET_TM (cpu.rTAG);
676
677 sim_debug (DBG_ADDRMOD, & cpu_dev,
678 "IR_MOD1: cpu.itxPair[0]=%012"PRIo64
679 " TPR.CA=%06o Tm=%o Td=%02o (%s)\n",
680 cpu.itxPair[0], cpu.TPR.CA, Tm, Td,
681 get_mod_string (buf, GET_TAG (cpu.itxPair[0])));
682
683 switch (Tm)
684 {
685 case TM_IT:
686 {
687 sim_debug (DBG_ADDRMOD, & cpu_dev,
688 "IR_MOD(TM_IT): Td=%02o => %02o\n",
689 Td, cpu.cu.CT_HOLD);
690
691 if (Td == IT_F2 || Td == IT_F3)
692 {
693 updateIWB(cpu.TPR.CA, cpu.rTAG);
694
695 switch (Td)
696 {
697 case IT_F2:
698 cpu.TPR.CA = saveCA;
699 doFault (FAULT_F2, fst_zero, "TM_IT: IT_F2 (1)");
700
701
702 case IT_F3:
703 cpu.TPR.CA = saveCA;
704 doFault (FAULT_F3, fst_zero, "TM_IT: IT_F3");
705 }
706 }
707
708 #ifndef __SUNPRO_C
709 # ifndef __SUNPRO_CC
710 # ifndef __SUNPRO_CC_COMPAT
711
712
713 # if defined(__GNUC__) && __GNUC__ > 6
714 __attribute__ ((fallthrough));
715 # endif
716
717 # ifdef __clang__
718 (void)0;
719 # endif
720 # endif
721 # endif
722 #endif
723 }
724
725
726 case TM_R:
727 {
728 word6 Td_hold = GET_TD (cpu.cu.CT_HOLD);
729 cpu.rTAG = (TM_R | Td_hold);
730 updateIWB (cpu.TPR.CA, cpu.rTAG);
731 goto startCA;
732 }
733
734 case TM_RI:
735 {
736 if (Td == TD_DU || Td == TD_DL)
737 doFault (FAULT_IPR, fst_ill_mod,
738 "RI_MOD: Td == TD_DU || Td == TD_DL");
739
740 word18 Cr = get_Cr (Td);
741
742 sim_debug (DBG_ADDRMOD, & cpu_dev,
743 "IR_MOD(TM_RI): Td=%o Cr=%06o TPR.CA(Before)=%06o\n",
744 Td, Cr, cpu.TPR.CA);
745
746 cpu.TPR.CA += Cr;
747 cpu.TPR.CA &= MASK18;
748
749 sim_debug (DBG_ADDRMOD, & cpu_dev,
750 "IR_MOD(TM_RI): TPR.CA=%06o\n", cpu.TPR.CA);
751
752 sim_debug (DBG_ADDRMOD, & cpu_dev,
753 "IR_MOD(TM_RI): TPR.CA(After)=%06o\n",
754 cpu.TPR.CA);
755
756
757 updateIWB (cpu.TPR.CA, (TM_RI|TD_N));
758 goto IR_MOD_2;
759 }
760
761 case TM_IR:
762 {
763 updateIWB (cpu.TPR.CA, cpu.rTAG);
764 goto IR_MOD_1;
765 }
766 }
767
768 sim_printf ("%s(IR_MOD): unknown Tm??? %o\n",
769 __func__, GET_TM (cpu.rTAG));
770 return;
771 }
772
773 IT_MOD:;
774 {
775
776
777
778
779
780
781
782
783
784
785 word6 idwtag, delta;
786 word24 Yi = (word24) -1;
787
788 switch (Td)
789 {
790
791 case SPEC_ITP:
792
793 case SPEC_ITS:
794 {
795 doFault(FAULT_IPR, fst_ill_mod, "ITx in IT_MOD)");
796 }
797
798
799 case 2:
800 {
801 sim_debug (DBG_ADDRMOD, & cpu_dev,
802 "IT_MOD(): illegal procedure, illegal modifier, "
803 "fault Td=%o\n", Td);
804 doFault (FAULT_IPR, fst_ill_mod,
805 "IT_MOD(): illegal procedure, illegal modifier, "
806 "fault");
807 }
808
809
810 case IT_F1:
811 {
812 doFault(FAULT_F1, fst_zero, "IT_MOD: IT_F1");
813 }
814
815
816 case IT_F2:
817 {
818 doFault(FAULT_F2, fst_zero, "IT_MOD: IT_F2 (2)");
819 }
820
821
822 case IT_F3:
823 {
824 doFault(FAULT_F3, fst_zero, "IT_MOD: IT_F3");
825 }
826
827
828 case IT_CI:
829
830 case IT_SC:
831
832 case IT_SCR:
833 {
834
835
836
837
838
839
840 sim_debug (DBG_ADDRMOD, & cpu_dev,
841 "IT_MOD CI/SC/SCR reading indirect word from %06o\n",
842 cpu.TPR.CA);
843
844
845
846
847
848 word36 indword;
849 word18 indaddr = cpu.TPR.CA;
850 Read (indaddr, & indword, APU_DATA_READ);
851 #ifdef LOCKLESS
852 word24 phys_address = cpu.iefpFinalAddress;
853 #endif
854
855 sim_debug (DBG_ADDRMOD, & cpu_dev,
856 "IT_MOD CI/SC/SCR indword=%012"PRIo64"\n", indword);
857
858
859
860
861
862 Yi = GET_ADDR (indword);
863 word6 sz = GET_TB (GET_TAG (indword));
864 word3 os = GET_CF (GET_TAG (indword));
865 word12 tally = GET_TALLY (indword);
866
867 sim_debug (DBG_ADDRMOD, & cpu_dev,
868 "IT_MOD CI/SC/SCR size=%o offset=%o Yi=%06o\n",
869 sz, os, Yi);
870
871 if (sz == TB6 && os > 5)
872
873 doFault (FAULT_IPR, fst_ill_mod,
874 "co size == TB6 && offset > 5");
875
876 if (sz == TB9 && os > 3)
877
878 doFault (FAULT_IPR, fst_ill_mod,
879 "co size == TB9 && offset > 3");
880
881
882
883 cpu.TPR.CA = Yi;
884 cpu.ou.character_address = Yi;
885 cpu.ou.characterOperandSize = sz;
886 cpu.ou.characterOperandOffset = os;
887
888
889
890 if (Td == IT_SCR)
891 {
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911 if (os == 0)
912 {
913 if (sz == TB6)
914 os = 5;
915 else
916 os = 3;
917 Yi -= 1;
918 Yi &= MASK18;
919 }
920 else
921 {
922 os -= 1;
923 }
924
925 CPT (cpt2L, 5);
926 tally ++;
927 tally &= 07777;
928
929
930
931 cpu.TPR.CA = Yi;
932 cpu.ou.character_address = Yi;
933 cpu.ou.characterOperandSize = sz;
934 cpu.ou.characterOperandOffset = os;
935 }
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950 cpu.cu.pot = 1;
951
952 #ifdef LOCKLESSXXX
953
954 Read (cpu.TPR.CA, & cpu.ou.character_data, (i->info->flags & RMW) == \
955 STORE_OPERAND ? OPERAND_RMW : OPERAND_READ);
956 #else
957 Read (cpu.TPR.CA, & cpu.ou.character_data, OPERAND_READ);
958 #endif
959 #ifdef LOCKLESS
960 cpu.char_word_address = cpu.iefpFinalAddress;
961 #endif
962
963 sim_debug (DBG_ADDRMOD, & cpu_dev,
964 "IT_MOD CI/SC/SCR data=%012"PRIo64"\n",
965 cpu.ou.character_data);
966
967 cpu.cu.pot = 0;
968
969 if (Td == IT_SC)
970 {
971
972
973
974
975
976
977
978
979
980
981
982
983 os ++;
984
985 if (((sz == TB6) && (os > 5)) ||
986 ((sz == TB9) && (os > 3)))
987 {
988 os = 0;
989 Yi += 1;
990 Yi &= MASK18;
991 }
992 CPT (cpt2L, 6);
993 tally --;
994 tally &= 07777;
995 }
996
997 if (Td == IT_SC || Td == IT_SCR)
998 {
999 sim_debug (DBG_ADDRMOD, & cpu_dev,
1000 "update IT tally now %o\n", tally);
1001
1002
1003
1004
1005
1006
1007 #ifdef LOCKLESS
1008 word36 indword_new;
1009 core_read_lock(phys_address, &indword_new, __func__);
1010 if (indword_new != indword)
1011 sim_warn("indword changed from %llo to %llo\n",
1012 (long long unsigned int)indword,
1013 (long long unsigned int)indword_new);
1014 #endif
1015 putbits36_18 (& indword, 0, Yi);
1016 putbits36_12 (& indword, 18, tally);
1017 putbits36_3 (& indword, 33, os);
1018 #ifdef LOCKLESS
1019 core_write_unlock(phys_address, indword, __func__);
1020 #else
1021 Write (indaddr, indword, APU_DATA_STORE);
1022 #endif
1023
1024 SC_I_TALLY (tally == 0);
1025
1026 sim_debug (DBG_ADDRMOD, & cpu_dev,
1027 "update IT wrote tally word %012"PRIo64
1028 " to %06o\n",
1029 indword, cpu.TPR.CA);
1030 }
1031
1032
1033
1034 cpu.TPR.CA = cpu.ou.character_address;
1035 return;
1036 }
1037
1038 case IT_I:
1039 {
1040 sim_debug (DBG_ADDRMOD, & cpu_dev,
1041 "IT_MOD(IT_I): reading indirect word from %06o\n",
1042 cpu.TPR.CA);
1043
1044
1045 ReadIndirect ();
1046
1047 sim_debug (DBG_ADDRMOD, & cpu_dev,
1048 "IT_MOD(IT_I): indword=%012"PRIo64"\n",
1049 cpu.itxPair[0]);
1050
1051 cpu.TPR.CA = GET_ADDR (cpu.itxPair[0]);
1052 updateIWB (cpu.TPR.CA, (TM_R|TD_N));
1053 return;
1054 }
1055
1056 case IT_AD:
1057 {
1058
1059
1060
1061
1062
1063
1064
1065
1066
1067
1068 sim_debug (DBG_ADDRMOD, & cpu_dev,
1069 "IT_MOD(IT_AD): reading indirect word from %06o\n",
1070 cpu.TPR.CA);
1071
1072 #ifdef THREADZ
1073 lock_rmw ();
1074 #endif
1075
1076 word18 saveCA = cpu.TPR.CA;
1077 word36 indword;
1078 Read (cpu.TPR.CA, & indword, APU_DATA_RMW);
1079
1080 cpu.AM_tally = GET_TALLY (indword);
1081 delta = GET_DELTA (indword);
1082 Yi = GETHI (indword);
1083
1084 sim_debug (DBG_ADDRMOD, & cpu_dev,
1085 "IT_MOD(IT_AD): indword=%012"PRIo64"\n",
1086 indword);
1087 sim_debug (DBG_ADDRMOD, & cpu_dev,
1088 "IT_MOD(IT_AD): address:%06o tally:%04o "
1089 "delta:%03o\n",
1090 Yi, cpu.AM_tally, delta);
1091
1092 cpu.TPR.CA = Yi;
1093 word18 computedAddress = cpu.TPR.CA;
1094
1095 Yi += delta;
1096 Yi &= MASK18;
1097
1098 cpu.AM_tally -= 1;
1099 cpu.AM_tally &= 07777;
1100
1101
1102
1103 SC_I_TALLY (cpu.AM_tally == 0);
1104 indword = (word36) (((word36) Yi << 18) |
1105 (((word36) cpu.AM_tally & 07777) << 6) |
1106 delta);
1107 #ifdef LOCKLESS
1108 core_write_unlock(cpu.iefpFinalAddress, indword, __func__);
1109 #else
1110 Write (saveCA, indword, APU_DATA_STORE);
1111 #endif
1112
1113 #ifdef THREADZ
1114 unlock_rmw ();
1115 #endif
1116
1117 sim_debug (DBG_ADDRMOD, & cpu_dev,
1118 "IT_MOD(IT_AD): wrote tally word %012"PRIo64
1119 " to %06o\n",
1120 indword, saveCA);
1121
1122 cpu.TPR.CA = computedAddress;
1123 updateIWB (cpu.TPR.CA, (TM_R|TD_N));
1124 return;
1125 }
1126
1127 case IT_SD:
1128 {
1129
1130
1131
1132
1133
1134
1135
1136
1137
1138
1139 #ifdef THREADZ
1140 lock_rmw ();
1141 #endif
1142
1143 word18 saveCA = cpu.TPR.CA;
1144 word36 indword;
1145 Read (cpu.TPR.CA, & indword, APU_DATA_RMW);
1146
1147 sim_debug (DBG_ADDRMOD, & cpu_dev,
1148 "IT_MOD(IT_SD): reading indirect word from %06o\n",
1149 cpu.TPR.CA);
1150 cpu.AM_tally = GET_TALLY (indword);
1151 delta = GET_DELTA (indword);
1152 Yi = GETHI (indword);
1153
1154 sim_debug (DBG_ADDRMOD, & cpu_dev,
1155 "IT_MOD(IT_SD): indword=%012"PRIo64"\n",
1156 indword);
1157 sim_debug (DBG_ADDRMOD, & cpu_dev,
1158 "IT_MOD(IT_SD): address:%06o tally:%04o "
1159 "delta:%03o\n",
1160 Yi, cpu.AM_tally, delta);
1161
1162 Yi -= delta;
1163 Yi &= MASK18;
1164 cpu.TPR.CA = Yi;
1165
1166 cpu.AM_tally += 1;
1167 cpu.AM_tally &= 07777;
1168 if (cpu.AM_tally == 0)
1169 SET_I_TALLY;
1170
1171
1172 indword = (word36) (((word36) Yi << 18) |
1173 (((word36) cpu.AM_tally & 07777) << 6) |
1174 delta);
1175 #ifdef LOCKLESS
1176 core_write_unlock(cpu.iefpFinalAddress, indword, __func__);
1177 #else
1178 Write (saveCA, indword, APU_DATA_STORE);
1179 #endif
1180
1181 #ifdef THREADZ
1182 unlock_rmw ();
1183 #endif
1184
1185 sim_debug (DBG_ADDRMOD, & cpu_dev,
1186 "IT_MOD(IT_SD): wrote tally word %012"PRIo64
1187 " to %06o\n",
1188 indword, saveCA);
1189
1190 cpu.TPR.CA = Yi;
1191 updateIWB (cpu.TPR.CA, (TM_R|TD_N));
1192 return;
1193 }
1194
1195 case IT_DI:
1196 {
1197
1198
1199
1200
1201
1202
1203
1204
1205
1206 sim_debug (DBG_ADDRMOD, & cpu_dev,
1207 "IT_MOD(IT_DI): reading indirect word from %06o\n",
1208 cpu.TPR.CA);
1209
1210 #ifdef THREADZ
1211 lock_rmw ();
1212 #endif
1213
1214 word18 saveCA = cpu.TPR.CA;
1215 word36 indword;
1216 Read (cpu.TPR.CA, & indword, APU_DATA_RMW);
1217
1218 Yi = GETHI (indword);
1219 cpu.AM_tally = GET_TALLY (indword);
1220 word6 junk = GET_TAG (indword);
1221
1222 sim_debug (DBG_ADDRMOD, & cpu_dev,
1223 "IT_MOD(IT_DI): indword=%012"PRIo64"\n",
1224 indword);
1225 sim_debug (DBG_ADDRMOD, & cpu_dev,
1226 "IT_MOD(IT_DI): address:%06o tally:%04o\n",
1227 Yi, cpu.AM_tally);
1228
1229 Yi -= 1;
1230 Yi &= MASK18;
1231 cpu.TPR.CA = Yi;
1232
1233 cpu.AM_tally += 1;
1234 cpu.AM_tally &= 07777;
1235 SC_I_TALLY (cpu.AM_tally == 0);
1236
1237
1238
1239 indword = (word36) (((word36) cpu.TPR.CA << 18) |
1240 ((word36) cpu.AM_tally << 6) |
1241 junk);
1242
1243 sim_debug (DBG_ADDRMOD, & cpu_dev,
1244 "IT_MOD(IT_DI): writing indword=%012"PRIo64" to "
1245 "addr %06o\n",
1246 indword, saveCA);
1247
1248 #ifdef LOCKLESS
1249 core_write_unlock(cpu.iefpFinalAddress, indword, __func__);
1250 #else
1251 Write (saveCA, indword, APU_DATA_STORE);
1252 #endif
1253
1254 #ifdef THREADZ
1255 unlock_rmw ();
1256 #endif
1257 cpu.TPR.CA = Yi;
1258 updateIWB (cpu.TPR.CA, (TM_R|TD_N));
1259 return;
1260 }
1261
1262 case IT_ID:
1263 {
1264
1265
1266
1267
1268
1269
1270
1271
1272
1273 word18 saveCA = cpu.TPR.CA;
1274
1275 sim_debug (DBG_ADDRMOD, & cpu_dev,
1276 "IT_MOD(IT_ID): fetching indirect word from %06o\n",
1277 cpu.TPR.CA);
1278
1279 #ifdef THREADZ
1280 lock_rmw ();
1281 #endif
1282
1283 word36 indword;
1284 Read (cpu.TPR.CA, & indword, APU_DATA_RMW);
1285
1286 Yi = GETHI (indword);
1287 cpu.AM_tally = GET_TALLY (indword);
1288
1289 word6 junk = GET_TAG (indword);
1290 sim_debug (DBG_ADDRMOD, & cpu_dev,
1291 "IT_MOD(IT_ID): indword=%012"PRIo64
1292 " Yi=%06o tally=%04o\n",
1293 indword, Yi, cpu.AM_tally);
1294
1295 cpu.TPR.CA = Yi;
1296 word18 computedAddress = cpu.TPR.CA;
1297
1298 Yi += 1;
1299 Yi &= MASK18;
1300
1301 cpu.AM_tally -= 1;
1302 cpu.AM_tally &= 07777;
1303
1304
1305
1306
1307 SC_I_TALLY (cpu.AM_tally == 0);
1308
1309
1310 indword = (word36) (((word36) Yi << 18) |
1311 ((word36) cpu.AM_tally << 6) |
1312 junk);
1313
1314 sim_debug (DBG_ADDRMOD, & cpu_dev,
1315 "IT_MOD(IT_ID): writing indword=%012"PRIo64" to "
1316 "addr %06o\n",
1317 indword, saveCA);
1318
1319 #ifdef LOCKLESS
1320 core_write_unlock(cpu.iefpFinalAddress, indword, __func__);
1321 #else
1322 Write (saveCA, indword, APU_DATA_STORE);
1323 #endif
1324
1325 #ifdef THREADZ
1326 unlock_rmw ();
1327 #endif
1328
1329 cpu.TPR.CA = computedAddress;
1330 updateIWB (cpu.TPR.CA, (TM_R|TD_N));
1331 return;
1332 }
1333
1334
1335 case IT_DIC:
1336 {
1337
1338
1339
1340
1341
1342
1343
1344
1345
1346
1347
1348
1349
1350
1351
1352
1353
1354
1355
1356
1357 sim_debug (DBG_ADDRMOD, & cpu_dev,
1358 "IT_MOD(IT_DIC): fetching indirect word from %06o\n",
1359 cpu.TPR.CA);
1360
1361 #ifdef THREADZ
1362 lock_rmw ();
1363 #endif
1364
1365 word18 saveCA = cpu.TPR.CA;
1366 word36 indword;
1367 Read (cpu.TPR.CA, & indword, APU_DATA_RMW);
1368
1369 cpu.cu.pot = 0;
1370
1371 Yi = GETHI (indword);
1372 cpu.AM_tally = GET_TALLY (indword);
1373 idwtag = GET_TAG (indword);
1374
1375 sim_debug (DBG_ADDRMOD, & cpu_dev,
1376 "IT_MOD(IT_DIC): indword=%012"PRIo64" Yi=%06o "
1377 "tally=%04o idwtag=%02o\n",
1378 indword, Yi, cpu.AM_tally, idwtag);
1379
1380 word24 YiSafe2 = Yi;
1381
1382 Yi -= 1;
1383 Yi &= MASK18;
1384
1385 cpu.AM_tally += 1;
1386 cpu.AM_tally &= 07777;
1387
1388
1389
1390
1391
1392
1393
1394 indword = (word36) (((word36) Yi << 18) |
1395 ((word36) cpu.AM_tally << 6) | idwtag);
1396
1397 sim_debug (DBG_ADDRMOD, & cpu_dev,
1398 "IT_MOD(IT_DIC): writing indword=%012"PRIo64" to "
1399 "addr %06o\n", indword, saveCA);
1400
1401 #ifdef LOCKLESS
1402 core_write_unlock(cpu.iefpFinalAddress, indword, __func__);
1403 #else
1404 Write (saveCA, indword, APU_DATA_STORE);
1405 #endif
1406
1407 #ifdef THREADZ
1408 unlock_rmw ();
1409 #endif
1410
1411
1412
1413
1414
1415
1416
1417
1418 cpu.TPR.CA = Yi;
1419
1420 sim_debug (DBG_ADDRMOD, & cpu_dev,
1421 "IT_MOD(IT_DIC): new CT_HOLD %02o new TAG %02o\n",
1422 cpu.rTAG, idwtag);
1423 cpu.cu.CT_HOLD = cpu.rTAG;
1424 cpu.rTAG = idwtag;
1425
1426 Tm = GET_TM (cpu.rTAG);
1427 if (Tm == TM_RI || Tm == TM_R)
1428 {
1429 if (GET_TD (cpu.rTAG) != 0)
1430 {
1431 doFault (FAULT_IPR, fst_ill_mod,
1432 "DIC Incorrect address modifier");
1433 }
1434 }
1435
1436
1437
1438 SC_I_TALLY (cpu.AM_tally == 0);
1439 if (cpu.tweaks.isolts_mode)
1440 updateIWB (YiSafe2, cpu.rTAG);
1441 else
1442 updateIWB (cpu.TPR.CA, cpu.rTAG);
1443 goto startCA;
1444 }
1445
1446
1447 case IT_IDC:
1448 {
1449
1450
1451
1452
1453
1454
1455
1456
1457
1458
1459
1460
1461
1462
1463
1464
1465
1466
1467
1468
1469 sim_debug (DBG_ADDRMOD, & cpu_dev,
1470 "IT_MOD(IT_IDC): fetching indirect word from %06o\n",
1471 cpu.TPR.CA);
1472
1473 #ifdef THREADZ
1474 lock_rmw ();
1475 #endif
1476
1477 word18 saveCA = cpu.TPR.CA;
1478 word36 indword;
1479 Read (cpu.TPR.CA, & indword, APU_DATA_RMW);
1480
1481 cpu.cu.pot = 0;
1482
1483 Yi = GETHI (indword);
1484 cpu.AM_tally = GET_TALLY (indword);
1485 idwtag = GET_TAG (indword);
1486
1487 sim_debug (DBG_ADDRMOD, & cpu_dev,
1488 "IT_MOD(IT_IDC): indword=%012"PRIo64" Yi=%06o "
1489 "tally=%04o idwtag=%02o\n",
1490 indword, Yi, cpu.AM_tally, idwtag);
1491
1492 word24 YiSafe = Yi;
1493
1494 Yi += 1;
1495 Yi &= MASK18;
1496
1497 cpu.AM_tally -= 1;
1498 cpu.AM_tally &= 07777;
1499
1500
1501
1502
1503
1504 indword = (word36) (((word36) Yi << 18) |
1505 ((word36) cpu.AM_tally << 6) |
1506 idwtag);
1507
1508 sim_debug (DBG_ADDRMOD, & cpu_dev,
1509 "IT_MOD(IT_IDC): writing indword=%012"PRIo64""
1510 " to addr %06o\n",
1511 indword, saveCA);
1512
1513 #ifdef LOCKLESS
1514 core_write_unlock(cpu.iefpFinalAddress, indword, __func__);
1515 #else
1516 Write (saveCA, indword, APU_DATA_STORE);
1517 #endif
1518
1519 #ifdef THREADZ
1520 unlock_rmw ();
1521 #endif
1522
1523
1524
1525
1526
1527
1528
1529
1530
1531
1532 cpu.TPR.CA = YiSafe;
1533
1534 sim_debug (DBG_ADDRMOD, & cpu_dev,
1535 "IT_MOD(IT_IDC): new CT_HOLD %02o new TAG %02o\n",
1536 cpu.rTAG, idwtag);
1537 cpu.cu.CT_HOLD = cpu.rTAG;
1538 cpu.rTAG = idwtag;
1539
1540 Tm = GET_TM (cpu.rTAG);
1541 if (Tm == TM_RI || Tm == TM_R)
1542 {
1543 if (GET_TD (cpu.rTAG) != 0)
1544 {
1545 doFault (FAULT_IPR, fst_ill_mod,
1546 "IDC Incorrect address modifier");
1547 }
1548 }
1549
1550
1551
1552 SC_I_TALLY (cpu.AM_tally == 0);
1553 updateIWB (cpu.TPR.CA, cpu.rTAG);
1554
1555 goto startCA;
1556 }
1557 }
1558 sim_printf ("IT_MOD/Td how did we get here?\n");
1559 return;
1560 }
1561 }