1 /* hp3000_cpu.h: HP 3000 CPU declarations
2 
3    Copyright (c) 2016-2021, J. David Bryan
4 
5    Permission is hereby granted, free of charge, to any person obtaining a copy
6    of this software and associated documentation files (the "Software"), to deal
7    in the Software without restriction, including without limitation the rights
8    to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9    copies of the Software, and to permit persons to whom the Software is
10    furnished to do so, subject to the following conditions:
11 
12    The above copyright notice and this permission notice shall be included in
13    all copies or substantial portions of the Software.
14 
15    THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16    IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17    FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL THE
18    AUTHOR BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
19    ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20    WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
21 
22    Except as contained in this notice, the name of the author shall not be used
23    in advertising or otherwise to promote the sale, use or other dealings in
24    this Software without prior written authorization from the author.
25 
26    08-Apr-21    JDB     Expanded bank register widths from 4 to 6 bits
27    07-Apr-21    JDB     Added UNIT_SERIES_IIIX CPU model
28    11-Oct-20    JDB     Moved UNIT_OPTS here from hp3000_cpu.c for updating ease
29    09-Oct-20    JDB     Renamed trap_Word_Count_Overflow to trap_Invalid_Decimal_Length
30    07-Oct-20    JDB     Corrected EXEC trace to omit PSERV events
31    05-Sep-20    JDB     Added the EIS dispatcher, corrected EIS_SDEC_MASK value
32    18-Feb-19    JDB     Added SS_PAUSE_RESUMED simulation stop condition
33    25-Jul-18    JDB     Fixed typo in "cpu_setup_code_segment" declaration
34    07-Nov-16    JDB     Added SETR and SETR_X for SETR executor use
35                         Renamed cpu_byte_to_word_ea to cpu_byte_ea
36    03-Nov-16    JDB     Added LABEL_LOCAL for PARC/XBR/ENDP executor use
37    01-Nov-16    JDB     Added debug flag for per-instruction trace capability
38    22-Oct-16    JDB     Added "cpu_interrupt_pending" global from cpu_base.c
39    07-Oct-16    JDB     Added "cpu_dev" external so executors can trace instructions
40    28-Sep-16    JDB     Added CIS definitions
41    22-Sep-16    JDB     Added cpu_byte_to_word_ea, STATUS_CS macro
42    21-Sep-16    JDB     Added STATUS_CCI, UNIT_CIS, and the CIS dispatcher
43    12-Sep-16    JDB     Added the PCN_SERIES_II and PCN_SERIES_III constants
44    02-Sep-16    JDB     Added the POWER_STATE enumeration type, the UNIT_PFARS
45                         flag, and the "cpu_power_state" external declaration
46    24-Aug-16    JDB     Fixed the UNIT_CPU_MODEL test macro
47    23-Aug-16    JDB     Added the MOD (module control) register
48    12-Jul-16    JDB     Renamed "loading" EXEC_STATE to "waiting"
49    21-Mar-16    JDB     Changed cpu_ccb_table type from uint16 to HP_WORD
50    14-Feb-16    JDB     First release version
51    11-Dec-12    JDB     Created
52 
53 
54    This file provides the declarations for interoperation between the CPU and
55    its supporting modules.  It provides the symbols that allow direct
56    manipulation of the CPU registers and determination of currently installed
57    features.
58 */
59 
60 
61 
62 #include <setjmp.h>
63 
64 
65 
66 /* Supported breakpoint switches */
67 
68 #define BP_EXEC             (SWMASK ('E'))      /* an execution breakpoint */
69 #define BP_SUPPORTED        (BP_EXEC)           /* the list of supported breakpoint types */
70 
71 
72 /* Unit flags and accessors */
73 
74 #define UNIT_MODEL_SHIFT    (UNIT_V_UF + 0)     /* the CPU model (2 bits) */
75 #define UNIT_EIS_SHIFT      (UNIT_V_UF + 2)     /* the Extended Instruction Set firmware option */
76 #define UNIT_CALTIME_SHIFT  (UNIT_V_UF + 3)     /* the process clock timing mode */
77 #define UNIT_PFARS_SHIFT    (UNIT_V_UF + 4)     /* the power-fail auto-restart mode */
78 #define UNIT_CIS_SHIFT      (UNIT_V_UF + 5)     /* the COBOL II Extended Instruction Set firmware option */
79 
80 #define UNIT_MODEL_MASK     0000003u            /* model ID mask */
81 
82 #define UNIT_MODEL          (UNIT_MODEL_MASK << UNIT_MODEL_SHIFT)
83 
84 #define UNIT_SERIES_II      (0u << UNIT_MODEL_SHIFT)    /* the CPU is a Series II */
85 #define UNIT_SERIES_III     (1u << UNIT_MODEL_SHIFT)    /* the CPU is a Series III */
86 #define UNIT_SERIES_IIIX    (2u << UNIT_MODEL_SHIFT)    /* the CPU is a Series III with extended memory */
87 #define UNIT_EIS            (1u << UNIT_EIS_SHIFT)      /* the Extended Instruction Set is installed */
88 #define UNIT_CALTIME        (1u << UNIT_CALTIME_SHIFT)  /* the process clock is calibrated to wall time */
89 #define UNIT_PFARS          (1u << UNIT_PFARS_SHIFT)    /* the system will auto-restart after a power failure */
90 #define UNIT_CIS            (1u << UNIT_CIS_SHIFT)      /* the COBOL II Extended Instruction Set is installed */
91 
92 #define UNIT_OPTS           (UNIT_EIS | UNIT_CIS)       /* set of optional features */
93 
94 
95 #define UNIT_CPU_MODEL      (cpu_unit [0].flags & UNIT_MODEL)
96 
97 #define CPU_MODEL(f)        ((f) >> UNIT_MODEL_SHIFT & UNIT_MODEL_MASK)
98 
99 #define MEMSIZE             (cpu_unit [0].capac)        /* the current memory size in 16-bit words */
100 
101 
102 /* CPU debug flags */
103 
104 #define DEB_INSTR           (1u << 0)           /* trace instructions */
105 #define DEB_REG             (1u << 1)           /* trace register values */
106 #define DEB_PSERV           (1u << 2)           /* trace PCLK service events */
107 #define DEB_EXEC            (1u << 3)           /* trace matched instruction executions */
108 
109 #define DEB_ALL             (~DEB_PSERV)        /* trace everything except PCLK service events */
110 
111 #define BOV_FORMAT          "%02o.%06o  %06o  " /* bank-offset-value trace format string */
112 
113 
114 /* CPU stop flags */
115 
116 #define SS_LOOP             (1u << 0)           /* stop on infinite loop */
117 #define SS_PAUSE            (1u << 1)           /* stop on PAUS instruction */
118 #define SS_UNDEF            (1u << 2)           /* stop on undefined instruction */
119 #define SS_UNIMPL           (1u << 3)           /* stop on unimplemented instruction */
120 
121 #define SS_PAUSE_RESUMED    (1u << 30)          /* stop resumes into a PAUS instruction */
122 #define SS_BYPASSED         (1u << 31)          /* stops are bypassed for this instruction */
123 
124 
125 /* Memory access macros */
126 
127 #define cpu_read_memory(c,o,v)      mem_read  (&cpu_dev, c, o, v)
128 #define cpu_write_memory(c,o,v)     mem_write (&cpu_dev, c, o, v)
129 
130 
131 
132 /* System power state.
133 
134    The HP 3000 power supply uses two signals to indicate its state: PON (power
135    on) and PFW (power-fail warning).  PON is asserted when the DC power levels
136    are within their operating ranges.  PFW is asserted when AC power is lost.
137    When a power failure occurs, PFW will be asserted at least three milliseconds
138    before PON is denied.  When power is restored, PFW denies immediately, but
139    PON does not assert until the DC output voltages have stabilized, and the
140    machine is ready to resume execution.
141 
142    In simulation, the four states of these two signals are modeled with
143    enumeration constants, as follows:
144 
145      PON  PFW  State            Simulator Action
146      ---  ---  ---------------  ----------------------------
147       1    0   power on         executing normally
148       1    1   power failing    executing with cpx1_PFINTR
149       0    1   power off        will not execute
150       0    0   power returning  executing with trap_Power_On
151 */
152 
153 typedef enum {
154     power_on,
155     power_failing,
156     power_off,
157     power_returning
158     } POWER_STATE;
159 
160 
161 /* Micromachine execution state */
162 
163 typedef enum {
164     running,                                    /* the micromachine is running */
165     paused,                                     /* a PAUS instruction has been executed */
166     waiting,                                    /* a cold load or dump is in progress */
167     halted                                      /* a programmed or front panel HALT has been executed */
168     } EXEC_STATE;
169 
170 
171 /* CPX register flags.
172 
173    The CPX1 register contains flags that designate the run-time interrupts.  The
174    CPX2 register contains flags for halt-time interrupts.
175 
176 
177    Implementation notes:
178 
179     1. These are implemented as enumeration types to allow the "gdb" debugger to
180        display the CPX register values as bit sets.
181 */
182 
183 typedef enum {
184     cpx1_INTOVFL  = 0100000u,                   /* integer overflow */
185     cpx1_BNDVIOL  = 0040000u,                   /* bounds violation */
186     cpx1_ILLADDR  = 0020000u,                   /* illegal address */
187     cpx1_CPUTIMER = 0010000u,                   /* CPU timer */
188     cpx1_SYSPAR   = 0004000u,                   /* system parity error */
189     cpx1_ADDRPAR  = 0002000u,                   /* address parity error */
190     cpx1_DATAPAR  = 0001000u,                   /* data parity error */
191     cpx1_MODINTR  = 0000400u,                   /* module interrupt */
192     cpx1_EXTINTR  = 0000200u,                   /* external interrupt */
193     cpx1_PFINTR   = 0000100u,                   /* power fail interrupt */
194 /*  cpx1_UNUSED   = 0000040u,                      unused, always 0 */
195     cpx1_ICSFLAG  = 0000020u,                   /* ICS flag */
196     cpx1_DISPFLAG = 0000010u,                   /* dispatcher-is-active flag */
197     cpx1_EMULATOR = 0000004u,                   /* emulator-in-use flag */
198     cpx1_IOTIMER  = 0000002u,                   /* I/O timeout */
199     cpx1_OPTION   = 0000001u                    /* option present */
200     } CPX1FLAG;
201 
202 #define CPX1_IRQ_SET        (cpx1_INTOVFL | cpx1_BNDVIOL  | \
203                              cpx1_ILLADDR | cpx1_CPUTIMER | \
204                              cpx1_SYSPAR  | cpx1_ADDRPAR  | \
205                              cpx1_DATAPAR | cpx1_MODINTR  | \
206                              cpx1_EXTINTR | cpx1_PFINTR)        /* the set of CPX1 interrupt requests */
207 
208 typedef enum {
209     cpx2_RUNSWCH  = 0100000u,                   /* RUN switch */
210     cpx2_DUMPSWCH = 0040000u,                   /* DUMP switch */
211     cpx2_LOADSWCH = 0020000u,                   /* LOAD switch */
212     cpx2_LOADREG  = 0010000u,                   /* load register */
213     cpx2_LOADADDR = 0004000u,                   /* load address */
214     cpx2_LOADMEM  = 0002000u,                   /* load memory */
215     cpx2_DISPMEM  = 0001000u,                   /* display memory */
216     cpx2_SNGLINST = 0000400u,                   /* single instruction */
217     cpx2_EXECSWCH = 0000200u,                   /* EXECUTE switch */
218     cpx2_INCRADDR = 0000100u,                   /* increment address */
219     cpx2_DECRADDR = 0000040u,                   /* decrement address */
220 /*  cpx2_UNUSED   = 0000020u,                      unused, always 0 */
221 /*  cpx2_UNUSED   = 0000010u,                      unused, always 0 */
222     cpx2_INHPFARS = 0000004u,                   /* inhibit power-fail auto-restart */
223     cpx2_SYSHALT  = 0000002u,                   /* system halt */
224     cpx2_RUN      = 0000001u                    /* run flip-flop */
225     } CPX2FLAG;
226 
227 #define CPX2_IRQ_SET        (cpx2_RUNSWCH  | cpx2_DUMPSWCH | \
228                              cpx2_LOADSWCH | cpx2_LOADREG  | \
229                              cpx2_LOADADDR | cpx2_LOADMEM  | \
230                              cpx2_DISPMEM  | cpx2_SNGLINST | \
231                              cpx2_EXECSWCH)                     /* the set of CPX2 interrupt requests */
232 
233 
234 /* Interrupt classifications.
235 
236    Interrupts are generated by setting CPX1 bits, by microcode aborts (traps),
237    or by the DISP or IXIT instructions to run the OS dispatcher or in response
238    to an external interrupt.  Each interrupt source is serviced by a procedure
239    in the Segment Transfer Table of segment 1, and the classification values are
240    chosen to match the STT numbers.
241 
242 
243    Implementation notes:
244 
245     1. The STT numbers are relevant only for interrupts that come from setting
246        the CPX1 bits (except for bit 8).  The enumeration values for external,
247        trap, DISP, and IXIT interrupts are not significant.
248 */
249 
250 typedef enum {
251 /*  identifier                STT        Source  Description               */
252 /*  -----------------------   ---        ------  ------------------------- */
253     irq_Integer_Overflow    = 000,    /* CPX1.0  Integer Overflow          */
254     irq_Bounds_Violation    = 001,    /* CPX1.1  Bounds Violation          */
255     irq_Illegal_Address     = 002,    /* CPX1.2  Illegal Memory Address    */
256     irq_Timeout             = 003,    /* CPX1.3  Non-Responding Module     */
257     irq_System_Parity       = 004,    /* CPX1.4  System Parity Error       */
258     irq_Address_Parity      = 005,    /* CPX1.5  Address Parity Error      */
259     irq_Data_Parity         = 006,    /* CPX1.6  Data Parity Error         */
260     irq_Module              = 007,    /* CPX1.7  Module Interrupt          */
261     irq_External            = 010,    /* CPX1.8  External Interrupt        */
262     irq_Power_Fail          = 011,    /* CPX1.9  Power Fail Interrupt      */
263     irq_Trap                = 012,    /* uABORT  System or user trap       */
264     irq_Dispatch            = 013,    /* DISP    Run the dispatcher        */
265     irq_IXIT                = 014     /* IXIT    External interrupt        */
266     } IRQ_CLASS;
267 
268 
269 /* Trap classifications.
270 
271    Except for the power-on trap, all traps result from microcode aborts.  In
272    hardware, these result in microcode jumps to the appropriate trap handlers.
273    In simulation, a MICRO_ABORT executes a "longjmp" to the trap handler just
274    before the main instruction loop.  As with interrupts, each trap is serviced
275    by a procedure in the Segment Transfer Table of segment 1, and the
276    classification values are chosen to match the STT numbers.
277 
278    Traps are invoked by the MICRO_ABORT macro, which takes as its parameter a
279    trap classification value.  Some traps require an additional parameter and
280    must be invoked by the MICRO_ABORTP macro, which takes a trap classification
281    value and a trap-specific value as parameters.
282 
283    Accessors are provided to separate the TRAP_CLASS and the parameter from the
284    combined longjmp value.
285 
286 
287    Implementation notes:
288 
289     1. Trap classifications must be > 0 for longjmp compatibility.
290 
291     2. A System Halt trap does not call an OS procedure but instead stops the
292        simulator.  The parameter number indicates the reason for the halt.
293 
294     3. The User trap is subdivided into traps for a number of arithmetic
295        conditions.  These are indicated by their corresponding parameter numbers
296        in the upper words of the longjmp values.
297 */
298 
299 typedef enum {
300 /*  identifier                 STT        Source  Description               */
301 /*  ------------------------   ---        ------  ------------------------- */
302     trap_None                = 000,    /*   --    (none)                    */
303     trap_Bounds_Violation    = 001,    /* ucode   Bounds Violation          */
304     trap_Unimplemented       = 020,    /* ucode   Unimplemented Instruction */
305     trap_STT_Violation       = 021,    /* ucode   STT Violation             */
306     trap_CST_Violation       = 022,    /* ucode   CST Violation             */
307     trap_DST_Violation       = 023,    /* ucode   DST Violation             */
308     trap_Stack_Underflow     = 024,    /* ucode   Stack Underflow           */
309     trap_Privilege_Violation = 025,    /* ucode   Privileged Mode Violation */
310     trap_Stack_Overflow      = 030,    /* ucode   Stack Overflow            */
311     trap_User                = 031,    /* ucode   User Trap                 */
312     trap_CS_Absent           = 037,    /* ucode   Absent Code Segment       */
313     trap_Trace               = 040,    /* ucode   Trace                     */
314     trap_Uncallable          = 041,    /* ucode   STT Entry Uncallable      */
315     trap_DS_Absent           = 042,    /* ucode   Absent Data Segment       */
316     trap_Power_On            = 043,    /*  hdwe   Power On                  */
317     trap_Cold_Load           = 044,    /* ucode   Cold Load                 */
318     trap_System_Halt         = 045     /* ucode   System Halt               */
319     } TRAP_CLASS;
320 
321 #define trap_Integer_Overflow       TO_DWORD (001, trap_User)
322 #define trap_Float_Overflow         TO_DWORD (002, trap_User)
323 #define trap_Float_Underflow        TO_DWORD (003, trap_User)
324 #define trap_Integer_Zero_Divide    TO_DWORD (004, trap_User)
325 #define trap_Float_Zero_Divide      TO_DWORD (005, trap_User)
326 #define trap_Ext_Float_Overflow     TO_DWORD (010, trap_User)
327 #define trap_Ext_Float_Underflow    TO_DWORD (011, trap_User)
328 #define trap_Ext_Float_Zero_Divide  TO_DWORD (012, trap_User)
329 #define trap_Decimal_Overflow       TO_DWORD (013, trap_User)
330 #define trap_Invalid_ASCII_Digit    TO_DWORD (014, trap_User)
331 #define trap_Invalid_Decimal_Digit  TO_DWORD (015, trap_User)
332 #define trap_Invalid_Word_Count     TO_DWORD (016, trap_User)
333 #define trap_Invalid_Decimal_Length TO_DWORD (017, trap_User)
334 #define trap_Decimal_Zero_Divide    TO_DWORD (020, trap_User)
335 
336 #define trap_SysHalt_STTV_1         TO_DWORD ( 1, trap_System_Halt)
337 #define trap_SysHalt_Absent_ICS     TO_DWORD ( 2, trap_System_Halt)
338 #define trap_SysHalt_Absent_1       TO_DWORD ( 3, trap_System_Halt)
339 #define trap_SysHalt_Overflow_ICS   TO_DWORD ( 4, trap_System_Halt)
340 #define trap_SysHalt_IO_Timeout     TO_DWORD ( 6, trap_System_Halt)
341 #define trap_SysHalt_PSEB_Enabled   TO_DWORD ( 9, trap_System_Halt)
342 #define trap_SysHalt_CSTV_1         TO_DWORD (13, trap_System_Halt)
343 #define trap_SysHalt_LOCK_EI        TO_DWORD (23, trap_System_Halt)
344 #define trap_SysHalt_Trace_1        TO_DWORD (33, trap_System_Halt)
345 
346 #define PARAM(i)            (uint32)     UPPER_WORD (i)
347 #define TRAP(i)             (TRAP_CLASS) LOWER_WORD (i)
348 
349 #define MICRO_ABORT(t)      longjmp (cpu_save_env, (t))
350 #define MICRO_ABORTP(t,p)   longjmp (cpu_save_env, TO_DWORD ((p),(t)))
351 
352 
353 /* Central Data Bus module definitions */
354 
355 #define MODULE_MEMORY_LOWER     0               /* lower memory MCL address */
356 #define MODULE_MEMORY_UPPER     2               /* upper memory MCL address */
357 #define MODULE_MEMORY           3               /* upper bound of MCL addresses */
358 #define MODULE_PORT_CNTLR       4               /* selector channel port controller address */
359 #define MODULE_CPU              5               /* CPU MCU address */
360 #define MODULE_UNDEFINED        6               /* addresses 6-7 are unused */
361 
362 #define MOP_NOP                 0               /* module operation 00 = no operation */
363 #define MOP_WRITE               1               /* module operation 01 = write */
364 #define MOP_READ                2               /* module operation 10 = read */
365 #define MOP_READ_WRITE_ONES     3               /* module operation 11 = read/write ones */
366 
367 
368 /* Module control register accessors.
369 
370    The module control register, MOD, has this format:
371 
372        0 | 1   2   3 | 4   5   6 | 7   8   9 |10  11  12 |13  14  15
373      +---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+
374      | 0   0 |  MOP  | 0 |   FROM    | 0   0   0   0 | B | A | 0   0 |
375      +---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+
376 
377    Where:
378 
379      MOP  = module operation
380      FROM = source module address
381      B    = this CPU is CPU #2
382      A    = this CPU is CPU #1
383 */
384 
385 #define MOD_MOP_MASK        0030000u            /* MOD register MOP field mask */
386 #define MOD_FROM_MASK       0003400u            /* MOD register FROM field mask */
387 #define MOD_CPU_2           0000010u            /* CPU number 2 MCU */
388 #define MOD_CPU_1           0000004u            /* CPU number 1 MCU */
389 
390 #define MOD_MOP_SHIFT       12                  /* MOD register MOP field alignment shift */
391 #define MOD_FROM_SHIFT      8                   /* MOD register FROM field alignment shift */
392 
393 #define TO_MOD_MOP(v)       ((v) << MOD_MOP_SHIFT  & MOD_MOP_MASK)
394 #define TO_MOD_FROM(v)      ((v) << MOD_FROM_SHIFT & MOD_FROM_MASK)
395 
396 
397 /* Status register accessors.
398 
399    The CPU status register, STA, has this format:
400 
401        0 | 1   2   3 | 4   5   6 | 7   8   9 |10  11  12 |13  14  15
402      +---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+
403      | M | I | T | R | O | C | ccode |  current code segment number  |
404      +---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+
405 
406    Where:
407 
408      M = user mode/protected mode (0/1)
409      I = external interrupts are enabled
410      T = user traps are enabled
411      R = right-hand stack operation executes next
412      O = arithmetic overflow has occurred
413      C = arithmetic carry has occurred
414 
415    Condition Code:
416 
417      00 = CCG (greater than)
418      01 = CCL (less than)
419      10 = CCE (equal to)
420      11 = invalid
421 */
422 
423 #define STATUS_M            0100000u            /* mode flag */
424 #define STATUS_I            0040000u            /* interrupt flag */
425 #define STATUS_T            0020000u            /* trap flag */
426 #define STATUS_R            0010000u            /* right-hand stack op flag */
427 #define STATUS_O            0004000u            /* overflow flag */
428 #define STATUS_C            0002000u            /* carry flag */
429 
430 #define STATUS_CCG          0000000u            /* condition code greater than */
431 #define STATUS_CCL          0000400u            /* condition code less than */
432 #define STATUS_CCE          0001000u            /* condition code equal to */
433 #define STATUS_CCI          0001400u            /* condition code invalid */
434 
435 #define STATUS_CC_MASK      0001400u            /* condition code mask */
436 #define STATUS_CC_SHIFT     8                   /* condition code alignment */
437 
438 #define STATUS_CS_MASK      0000377u            /* code segment mask */
439 #define STATUS_CS_SHIFT     0                   /* code segment alignment */
440 #define STATUS_CS_WIDTH     8                   /* code segment mask width */
441 
442 #define STATUS_CS(s)       (((s) & STATUS_CS_MASK) >> STATUS_CS_SHIFT)
443 
444 
445 #define STATUS_OVTRAP       (STATUS_T | STATUS_O)
446 #define STATUS_NPRV         (STATUS_T | STATUS_O | STATUS_C | STATUS_CC_MASK)
447 
448 #define TO_CCN(s)           (((s) & STATUS_CC_MASK) >> STATUS_CC_SHIFT)
449 
450 
451 /* Status register mode tests */
452 
453 #define PRIV                (STA & STATUS_M)            /* current mode is privileged */
454 #define NPRV                (!PRIV)                     /* current mode is non-privileged */
455 
456 
457 /* Condition code flags.
458 
459    Several instructions define "condition code flags" that specify condition
460    code tests to be performed.  These flags are ANDed with the condition code
461    from the status register to establish whether the test passes.  CCE and CCL
462    are encoded in the status register by bits 6 and 7, respectively, but CCG is
463    encoded as 00, causing a direct AND to fail.  This is resolved in microcode
464    by the "CC" S-bus micro-order, which copies bits 6 and 7 to bits 8 and 9 of
465    the S-bus register and also sets bit 7 if bits 8 and 9 are zero (CCG).  The
466    result is a single bit set for each condition code that may be ANDed with the
467    CCF field of the instruction.
468 
469    The MVBW (Move Bytes While) instruction moves bytes from the source to the
470    destination while the bytes are alphabetic, numeric, or either, depending on
471    the A and N bits in the instruction.  The CCB classification table is used to
472    determine the type of each byte moved.  If both A and N bits are set, then a
473    table entry of either CCG or CCE will succeed.  Matching via a single AND
474    operation is possible only if the encoding of all three conditions is
475    disjoint.
476 
477    We implement this scheme without the two-bit right-shift, so that ANDing a
478    CCF with STATUS_CC_MASK will produce the correctly aligned status register
479    value.  The TO_CCF macro converts the current condition code in the status
480    register to a condition code flag.
481 */
482 
483 #define CFL                 0000400u            /* condition code flag less than */
484 #define CFE                 0001000u            /* condition code flag equal to */
485 #define CFG                 0002000u            /* condition code flag greater than */
486 
487 #define TO_CCF(s)           ((s) & STATUS_CC_MASK ? (s) & STATUS_CC_MASK : CFG)
488 
489 
490 /* Condition code patterns.
491 
492    Machine instructions typically set the condition code field of the status
493    register to reflect the values of their operands, which may be on the top of
494    the stack, in the X register, or in memory.  Each instruction that affects
495    the condition code field commonly uses one of the following patterns to set
496    the field:
497 
498      CCA (arithmetic) sets CC to:
499        - CCG (00) if the operand is > 0
500        - CCL (01) if the operand is < 0
501        - CCE (10) if the operand is = 0
502 
503      CCB (byte) sets CC to:
504        - CCG (00) if the operand is numeric (byte value is 060-071)
505        - CCL (01) if the operand is any other character
506        - CCE (10) if the operand is alphabetic (0101-0132 or 0141-0172)
507 
508      CCC (comparison) sets CC to:
509        - CCG (00) if operand 1 is > operand 2
510        - CCL (01) if operand 1 is < operand 2
511        - CCE (10) if operand 1 is = operand 2
512 
513      CCD (direct I/O) sets CC to:
514        - CCG (00) if the device is not ready
515        - CCL (01) if the device controller is not responding
516        - CCE (10) if the device is ready and controller is responding
517 
518    The operand(s) may be a byte, word, double word, triple word, or quadruple
519    word, and may be signed (integer) or unsigned (logical).
520 
521    Statement macros are provided to set the condition code explicitly, as well
522    as to set the code using patterns CCA, CCB, or CCC.  The CCA macro takes two
523    parameters: an upper word and a lower word.  The CCB macro takes a single
524    byte parameter.  The CCC macro takes four parameters: an upper and lower word
525    for each of the two operands.
526 
527    No macro is provided for pattern CCD, as that pattern reflects the
528    operational status of the target device and interface, rather than the
529    condition of an operand.  The I/O instructions use the explicit macros to set
530    the codes for pattern D.
531 */
532 
533 #define SET_CCG             STA = STA & ~STATUS_CC_MASK | STATUS_CCG
534 #define SET_CCL             STA = STA & ~STATUS_CC_MASK | STATUS_CCL
535 #define SET_CCE             STA = STA & ~STATUS_CC_MASK | STATUS_CCE
536 
537 
538 /* Condition code pattern CCA (arithmetic).
539 
540    Semantics:
541 
542      if operand > 0
543        then CCG
544      else if operand < 0
545        then CCL
546      else
547        CCE
548 
549    Macro:
550 
551      SET_CCA (upper, lower)
552 
553    Implementation:
554 
555      if upper = 0 or lower = 0
556        then CCE
557      else if upper.sign = 1
558        then CCL
559      else CCG
560 
561    Usage:
562 
563      SET_CCA (RA, 0)            -- a 16-bit integer value
564      SET_CCA (0, RA)            -- a 16-bit logical value
565      SET_CCA (RB, RA)           -- a 32-bit integer value
566      SET_CCA (0, RB | RA)       -- a 32-bit logical value
567      SET_CCA (RC, RB | RA)      -- a 48-bit integer value
568      SET_CCA (RD, RC | RB | RA) -- a 64-bit integer value
569 
570 
571    Implementation notes:
572 
573     1. When either "upper" or "lower" is 0, the corresponding test is optimized
574        away.
575 */
576 
577 #define SET_CCA(u,l)        STA = STA & ~STATUS_CC_MASK | \
578                               (((u) | (l)) == 0 \
579                                 ? STATUS_CCE \
580                                 : (u) & D16_SIGN \
581                                     ? STATUS_CCL \
582                                     : STATUS_CCG)
583 
584 
585 /* Condition code pattern CCB (byte).
586 
587    Semantics:
588 
589      if operand in 060 .. 071
590        then CCG
591      else if operand in 0101 .. 0132 or operand in 0141 .. 0172
592        then CCE
593      else
594        CCL
595 
596    Macro:
597 
598      SET_CCB (byte)
599 
600    Implementation:
601 
602      CCx = ccb_lookup_table [byte]
603 
604    Usage:
605 
606      SET_CCB (RA)
607 
608 
609    Implementation notes:
610 
611     1. The byte parameter is not masked before being used as an array index, so
612        the caller must ensure that the value is between 0 and 255.
613 
614     2. The table value must be masked if it is to be stored in the status
615        register because CCG is returned as 100 (base 2) to ensure that all
616        values are disjoint for the MVBW and Bcc instructions.
617 */
618 
619 #define SET_CCB(b)          STA = STA & ~STATUS_CC_MASK | \
620                               cpu_ccb_table [(b)] & STATUS_CC_MASK
621 
622 
623 /* Condition code pattern CCC (conditional).
624 
625    Semantics:
626 
627      if operand_1 > operand_2
628        then CCG
629      else if operand_1 < operand_2
630        then CCL
631      else
632        CCE
633 
634    Macro:
635 
636      SET_CCC (upper_1, lower_1, upper_2, lower_2)
637 
638    Implementation:
639 
640      if upper_1 = upper_2
641        then
642          if lower_1 = lower_2
643            then CCE
644          else if lower_1 < lower_2
645            then CCL
646          else CCG
647      else if |upper_1| < |upper_2|
648        then CCL
649      else CCG
650 
651    Usage:
652 
653      SET_CCC (RA,  0, RB,  0) -- 16-bit integer comparison
654      SET_CCC ( 0, RA,  0, RB) -- 16-bit logical comparison
655      SET_CCC (RB, RA, RD, RC) -- 32-bit integer comparison
656 
657 
658    Implementation notes:
659 
660     1. When any of the parameters are 0, the corresponding tests are optimized
661        away.
662 
663     2. Complementing the signs of the upper words allows an unsigned comparison
664        to substitute for a signed comparison.
665 */
666 
667 #define SET_CCC(u1,l1,u2,l2)  STA = STA & ~STATUS_CC_MASK | \
668                                 ((u1) == (u2) \
669                                   ? ((l1) == (l2) \
670                                       ? STATUS_CCE \
671                                       : ((l1) < (l2) \
672                                           ? STATUS_CCL \
673                                           : STATUS_CCG)) \
674                                   : (((u1) ^ D16_SIGN) < ((u2) ^ D16_SIGN) \
675                                       ? STATUS_CCL \
676                                       : STATUS_CCG))
677 
678 /* Set carry and overflow.
679 
680    These macros are used by arithmetic operations to set the carry and overflow
681    bits in the status register.  In addition to setting the overflow bit, if
682    user traps are enabled, the Integer Overflow bit in the CPX1 register is set,
683    which will cause an interrupt
684 */
685 
686 #define SET_CARRY(b)        STA = ((b) ? STA | STATUS_C : STA & ~STATUS_C)
687 
688 #define SET_OVERFLOW(b)     if (b) { \
689                                 STA |= STATUS_O; \
690                                 if (STA & STATUS_T) \
691                                     CPX1 |= cpx1_INTOVFL; \
692                                 } \
693                             else \
694                                 STA &= ~STATUS_O
695 
696 /* SR preadjust.
697 
698    The PREADJUST_SR macro is called to ensure that the correct number of TOS
699    registers are valid prior to instruction execution.
700 */
701 
702 #define PREADJUST_SR(n)     if (SR < (n)) \
703                                 cpu_adjust_sr (n)
704 
705 
706 /* Machine instruction bit-field accessors */
707 
708 #define BITS_0_3_MASK       0170000u            /* bits 0-3 mask */
709 #define BITS_0_3_SHIFT      12                  /* bits 0-3 alignment shift */
710 
711 #define BITS_0_3(v)         (((v) & BITS_0_3_MASK) >> BITS_0_3_SHIFT)
712 
713 #define BITS_4_5_MASK       0006000u            /* bits 4-5 mask */
714 #define BITS_4_5_SHIFT      10                  /* bits 4-5 alignment shift */
715 
716 #define BITS_4_5(v)         (((v) & BITS_4_5_MASK) >> BITS_4_5_SHIFT)
717 
718 #define BITS_4_7_MASK       0007400u            /* bits 4-7 mask */
719 #define BITS_4_7_SHIFT      8                   /* bits 4-7 alignment shift */
720 
721 #define BITS_4_7(v)         (((v) & BITS_4_7_MASK) >> BITS_4_7_SHIFT)
722 
723 #define BITS_4_9_MASK       0007700u            /* bits 4-9 mask */
724 #define BITS_4_9_SHIFT      6                   /* bits 4-9 alignment shift */
725 
726 #define BITS_4_9(v)         (((v) & BITS_4_9_MASK) >> BITS_4_9_SHIFT)
727 
728 #define BITS_5_9_MASK       0003700u            /* bits 5-9 mask */
729 #define BITS_5_9_SHIFT      6                   /* bits 5-9 alignment shift */
730 
731 #define BITS_5_9(v)         (((v) & BITS_5_9_MASK) >> BITS_5_9_SHIFT)
732 
733 #define BITS_8_11_MASK      0000360u            /* bits 8-11 mask */
734 #define BITS_8_11_SHIFT     4                   /* bits 8-11 alignment shift */
735 
736 #define BITS_8_11(v)        (((v) & BITS_8_11_MASK) >> BITS_8_11_SHIFT)
737 
738 #define BITS_8_12_MASK      0000370u            /* bits 8-12 mask */
739 #define BITS_8_12_SHIFT     3                   /* bits 8-12 alignment shift */
740 
741 #define BITS_8_12(v)        (((v) & BITS_8_12_MASK) >> BITS_8_12_SHIFT)
742 
743 #define BITS_10_15_MASK     0000077u            /* bits 10-15 mask */
744 #define BITS_10_15_SHIFT    0                   /* bits 10-15 alignment shift */
745 
746 #define BITS_10_15(v)       (((v) & BITS_10_15_MASK) >> BITS_10_15_SHIFT)
747 
748 #define BITS_12_15_MASK     0000017u            /* bits 12-15 mask */
749 #define BITS_12_15_SHIFT    0                   /* bits 12-15 alignment shift */
750 
751 #define BITS_12_15(v)       (((v) & BITS_12_15_MASK) >> BITS_12_15_SHIFT)
752 
753 
754 /* Instruction-class accessors */
755 
756 #define SUBOP_MASK          BITS_0_3_MASK       /* subopcode mask */
757 #define SUBOP_SHIFT         BITS_0_3_SHIFT      /* subopcode alignment shift */
758 #define SUBOP(v)            BITS_0_3(v)         /* subopcode accessor */
759 
760 #define STACKOP_A_MASK      BITS_4_9_MASK       /* stack operation A mask */
761 #define STACKOP_A_SHIFT     BITS_4_9_SHIFT      /* stack operation A alignment shift */
762 #define STACKOP_A(v)        BITS_4_9(v)         /* stack operation A accessor */
763 
764 #define STACKOP_B_MASK      BITS_10_15_MASK     /* stack operation B mask */
765 #define STACKOP_B_SHIFT     BITS_10_15_SHIFT    /* stack operation B alignment shift */
766 #define STACKOP_B(v)        BITS_10_15(v)       /* stack operation B accessor */
767 
768 #define SBBOP_MASK          BITS_5_9_MASK       /* shift/branch/bit operation mask */
769 #define SBBOP_SHIFT         BITS_5_9_SHIFT      /* shift/branch/bit operation alignment shift */
770 #define SBBOP(v)            BITS_5_9(v)         /* shift/branch/bit operation accessor */
771 
772 #define MSFIFROP_MASK       BITS_4_7_MASK       /* move/special/firmware/immediate/field/register operation mask */
773 #define MSFIFROP_SHIFT      BITS_4_7_SHIFT      /* move/special/firmware/immediate/field/register operation alignment shift */
774 #define MSFIFROP(v)         BITS_4_7(v)         /* move/special/firmware/immediate/field/register operation accessor */
775 
776 #define MSSUBOP_MASK        BITS_8_12_MASK      /* move/special suboperation mask */
777 #define MSSUBOP_SHIFT       BITS_8_12_SHIFT     /* move/special suboperation alignment shift */
778 #define MSSUBOP(v)          BITS_8_12(v)        /* move/special suboperation accessor */
779 
780 #define SPECOP_MASK         BITS_12_15_MASK     /* special operation mask */
781 #define SPECOP_SHIFT        BITS_12_15_SHIFT    /* special operation alignment shift */
782 #define SPECOP(v)           BITS_12_15(v)       /* special operation accessor */
783 
784 #define IOCPIMOP_MASK       BITS_4_7_MASK       /* I-O/control/program/immediate/memory operation mask */
785 #define IOCPIMOP_SHIFT      BITS_4_7_SHIFT      /* I-O/control/program/immediate/memory operation alignment shift */
786 #define IOCPIMOP(v)         BITS_4_7(v)         /* I-O/control/program/immediate/memory operation accessor */
787 
788 #define IOCSUBOP_MASK       BITS_8_11_MASK      /* I-O/control suboperation mask */
789 #define IOCSUBOP_SHIFT      BITS_8_11_SHIFT     /* I-O/control suboperation alignment shift */
790 #define IOCSUBOP(v)         BITS_8_11(v)        /* I-O/control suboperation accessor */
791 
792 #define CNTLOP_MASK         BITS_12_15_MASK     /* control operation mask */
793 #define CNTLOP_SHIFT        BITS_12_15_SHIFT    /* control operation alignment shift */
794 #define CNTLOP(v)           BITS_12_15(v)       /* control operation accessor */
795 
796 #define MLBOP_MASK          BITS_0_3_MASK       /* memory/loop/branch operation mask */
797 #define MLBOP_SHIFT         BITS_0_3_SHIFT      /* memory/loop/branch operation alignment shift */
798 #define MLBOP(v)            BITS_0_3(v)         /* memory/loop/branch operation accessor */
799 
800 #define FIRMEXTOP_MASK      BITS_8_11_MASK      /* firmware extension operation mask */
801 #define FIRMEXTOP_SHIFT     BITS_8_11_SHIFT     /* firmware extension operation alignment shift */
802 #define FIRMEXTOP(v)        BITS_8_11(v)        /* firmware extension operation accessor */
803 
804 #define FMEXSUBOP_MASK      BITS_12_15_MASK     /* firmware extension suboperation mask */
805 #define FMEXSUBOP_SHIFT     BITS_12_15_SHIFT    /* firmware extension suboperation alignment shift */
806 #define FMEXSUBOP(v)        BITS_12_15(v)       /* firmware extension suboperation accessor */
807 
808 
809 /* General instruction accessors */
810 
811 #define IOOP_K_MASK         0000017u            /* I/O K-field mask */
812 #define IOOP_K_SHIFT        0000000u            /* I/O K-field alignment shift */
813 #define IO_K(v)             (((v) & IOOP_K_MASK) >> IOOP_K_SHIFT)
814 
815 #define X_FLAG              0004000u            /* index flag in bit 4 */
816 #define I_FLAG_BIT_4        0004000u            /* indirect flag in bit 4 */
817 #define I_FLAG_BIT_5        0002000u            /* indirect flag in bit 5 */
818 #define M_FLAG              0001000u            /* memory subop flag in bit 6 */
819 
820 #define START_BIT_MASK      0000360u            /* start bit mask for bit field instructions */
821 #define START_BIT_SHIFT     4                   /* start bit alignment shift */
822 #define START_BIT(v)        (((v) & START_BIT_MASK) >> START_BIT_SHIFT)
823 
824 #define BIT_COUNT_MASK      0000017u            /* bit count mask for bit field instructions */
825 #define BIT_COUNT_SHIFT     0                   /* bit count alignment shift */
826 #define BIT_COUNT(v)        (((v) & BIT_COUNT_MASK) >> BIT_COUNT_SHIFT)
827 
828 #define BIT_POSITION_MASK   0000077u            /* bit position mask for bit test instructions */
829 #define BIT_POSITION_SHIFT  0                   /* bit position alignment shift */
830 #define BIT_POSITION(v)     (((v) & BIT_POSITION_MASK) >> BIT_POSITION_SHIFT)
831 
832 #define SHIFT_COUNT_MASK    0000077u            /* shift count mask for shift instructions */
833 #define SHIFT_COUNT_SHIFT   0                   /* shift count alignment shift */
834 #define SHIFT_COUNT(v)      (((v) & SHIFT_COUNT_MASK) >> SHIFT_COUNT_SHIFT)
835 
836 #define SHIFT_RIGHT_FLAG    0000100u            /* shift instructions left/right (0/1) flag */
837 
838 #define MODE_DISP_MASK      0001777u            /* memory-reference mode and displacement mask */
839 #define MODE_MASK           0001700u            /* memory-reference mode mask */
840 #define MODE_SHIFT          6                   /* memory-reference mode alignment shift */
841 
842 #define DISPL_31_SIGN       0000040u            /* sign bit for 0-31 displacements */
843 #define DISPL_255_SIGN      0000400u            /* sign bit for 0-255 displacements */
844 
845 #define DISPL_31_MASK       0000037u            /* mask for 0-31 displacements */
846 #define DISPL_63_MASK       0000077u            /* mask for 0-63 displacements */
847 #define DISPL_127_MASK      0000177u            /* mask for 0-127 displacements */
848 #define DISPL_255_MASK      0000377u            /* mask for 0-255 displacements */
849 
850 #define DISPL_P_FLAG        0001000u            /* P-relative displacement flag */
851 #define DISPL_DB_FLAG       0000400u            /* DB-relative displacement flag */
852 #define DISPL_QPOS_FLAG     0000200u            /* positive Q-relative displacement flag */
853 #define DISPL_QNEG_FLAG     0000100u            /* negative Q-relative displacement flag */
854 
855 #define IMMED_MASK          0000377u            /* mask for immediate values */
856 
857 #define SDEC2_MASK          0000003u            /* two-bit S-decrement mask for move instructions */
858 #define SDEC3_MASK          0000007u            /* three-bit S-decrement mask for move instructions */
859 #define SDEC_SHIFT          0                   /* S-decrement alignment shift */
860 
861 #define SDEC2(v)            (((v) & SDEC2_MASK) >> SDEC_SHIFT)
862 #define SDEC3(v)            (((v) & SDEC3_MASK) >> SDEC_SHIFT)
863 
864 #define DB_FLAG             0000020u            /* base set PB/DB base register flag */
865 #define CIS_DB_FLAG         0000001u            /* CIS set PB/DB base register flag */
866 
867 
868 /* Explicit instruction opcodes and accessors */
869 
870 #define NOP                 0000000u            /* no operation */
871 #define QASR                0015700u            /* quadruple arithmetic right shift */
872 #define DMUL                0020570u            /* double integer multiply */
873 #define DDIV                0020571u            /* double integer divide */
874 #define SETR                0027400u            /* set registers (none) */
875 #define SETR_X              0027404u            /* set registers (index) */
876 #define SED_1               0030041u            /* set enable interrupt */
877 #define HALT_10             0030370u            /* halt 10 */
878 
879 #define MTFDS_MASK          0177730u            /* move to/from data segment mask */
880 #define MTFDS               0020130u            /* move to/from data segment */
881 
882 #define EXIT_MASK           0177400u            /* exit procedure mask */
883 #define EXIT                0031400u            /* exit procedure */
884 
885 #define PAUS_MASK           0177760u            /* pause mask */
886 #define PAUS                0030020u            /* pause */
887 
888 #define BR_MASK             0173000u            /* conditional and unconditional branch mask */
889 #define BR_DBQS_I           0143000u            /* branch unconditionally DB/Q/S-relative indirect */
890 #define BCC                 0141000u            /* branch conditionally */
891 #define BCC_CCF_SHIFT       2                   /* CCF alignment in BCC instruction */
892 
893 #define LSDX_MASK           0175000u            /* load/store double-word indexed mask */
894 #define LDD_X               0155000u            /* load double-word indexed */
895 #define STD_X               0165000u            /* store double-word indexed */
896 
897 #define TBR_MASK            0177000u            /* test and branch mask */
898 #define TBA                 0050000u            /* test and branch, limit in A */
899 #define MTBA                0052000u            /* modify, test and branch, limit in A */
900 #define TBX                 0054000u            /* test and branch, limit in X */
901 #define MTBX                0056000u            /* modify, test and branch, limit in X */
902 
903 #define CMD_TO_MASK         0000007u            /* CMD command word TO field mask */
904 #define CMD_MOP_MASK        0000060u            /* CMD command word MOP field mask */
905 
906 #define CMD_TO_SHIFT        0                   /* CMD command word TO field alignment shift */
907 #define CMD_MOP_SHIFT       4                   /* CMD command word MOP field alignment shift */
908 
909 #define CMD_TO(v)           (((v) & CMD_TO_MASK)  >> CMD_TO_SHIFT)
910 #define CMD_MOP(v)          (((v) & CMD_MOP_MASK) >> CMD_MOP_SHIFT)
911 
912 #define MVBW_CCF            0000030u            /* MVBW condition code flags */
913 #define MVBW_N_FLAG         0000020u            /* MVBW numeric flag */
914 #define MVBW_A_FLAG         0000010u            /* MVBW alphabetic flag */
915 #define MVBW_S_FLAG         0000004u            /* MVBW upshift flag */
916 #define MVBW_CCF_SHIFT      6                   /* CCF alignment in MVBW instruction */
917 
918 #define NABS_FLAG           0000100u            /* CVDA negative absolute value flag */
919 #define ABS_FLAG            0000040u            /* CVDA absolute value flag */
920 
921 #define CVND_SC_MASK        0000016u            /* CVND sign-control mask */
922 #define CVND_SC_SHIFT       1                   /* CVND sign-control field alignment shift */
923 
924 #define EIS_SDEC_FLAG       0000020u            /* EIS S-decrement bit 11 */
925 #define EIS_SDEC_MASK       0000060u            /* EIS S-decrement mask */
926 #define EIS_SDEC_SHIFT      4                   /* EIS S-decrement alignment shift */
927 
928 #define EIS_SDEC(v)         (((v) & EIS_SDEC_MASK) >> EIS_SDEC_SHIFT)
929 
930 #define CIS_SDEC_MASK       0000001u            /* CIS S-decrement mask */
931 #define CIS_SDEC_SHIFT      0                   /* CIS S-decrement alignment shift */
932 
933 #define TCCS_CCF_SHIFT      8                   /* CIS TCCS instruction CCF alignment */
934 
935 
936 /* PSHR/SETR instruction accessors */
937 
938 #define PSR_RL_MASK         0000001u            /* PSHR/SETR register right-to-left mask */
939 #define PSR_LR_MASK         0000200u            /* PSHR/SETR register left-to-right mask */
940 
941 #define PSR_SBANK           0000200u            /* Stack bank register */
942 #define PSR_DB_DBANK        0000100u            /* Data base and data bank registers */
943 #define PSR_DL              0000040u            /* Data limit register */
944 #define PSR_Z               0000020u            /* Stack limit register */
945 #define PSR_STA             0000010u            /* Status register */
946 #define PSR_X               0000004u            /* Index register */
947 #define PSR_Q               0000002u            /* Frame pointer */
948 #define PSR_S               0000001u            /* Stack pointer */
949 
950 #define PSR_PRIV            (PSR_SBANK | PSR_DB_DBANK | PSR_DL | PSR_Z)
951 
952 
953 /* PCN instruction result values */
954 
955 #define PCN_SERIES_II       1                   /* CPU number for the Series II */
956 #define PCN_SERIES_III      2                   /* CPU number for the Series III */
957 
958 
959 /* EDIT instruction subprogram operation values */
960 
961 #define EDIT_SUFS           013                 /* highest opcode with an extended immediate operand */
962 #define EDIT_EXOP           017                 /* extended opcode prefix */
963 
964 #define EDIT_TE             (EDIT_EXOP + 000)   /* first extended opcode with no operand */
965 #define EDIT_MDWO           (EDIT_EXOP + 004)   /* last extended opcode with no operand */
966 #define EDIT_DBNZ           (EDIT_EXOP + 011)   /* last extended opcode */
967 
968 
969 /* Reserved memory addresses */
970 
971 #define CSTB_POINTER        0000000u            /* code segment table base pointer */
972 #define CSTX_POINTER        0000001u            /* code segment table extension pointer */
973 #define DST_POINTER         0000002u            /* data segment table pointer */
974 #define ICS_Q               0000005u            /* interrupt control stack marker pointer (QI) */
975 #define ICS_Z               0000006u            /* interrupt control stack limit (ZI) */
976 #define INTERRUPT_MASK      0000007u            /* interrupt mask */
977 #define SGT_POINTER         0001000u            /* system global tables pointer */
978 
979 
980 /* Code Segment Table accessors */
981 
982 #define CST_A_BIT           0100000u            /* code segment is absent */
983 #define CST_M_BIT           0040000u            /* code segment is privileged */
984 #define CST_R_BIT           0020000u            /* code segment has been referenced flag */
985 #define CST_T_BIT           0010000u            /* code segment is to be traced */
986 #define CST_SEGLEN_MASK     0007777u            /* code segment length mask */
987 #define CST_BANK_MASK       mem_bank_mask       /* code segment bank mask (varies with CPU model) */
988 
989 #define CST_RESERVED        0000300u            /* number of CST entries reserved for the system */
990 
991 
992 /* Data Segment Table accessors */
993 
994 #define DST_A_BIT           0100000u            /* data segment is absent */
995 #define DST_C_BIT           0040000u            /* data segment is clean (not modified) */
996 #define DST_R_BIT           0020000u            /* data segment has been referenced */
997 #define DST_SEGLEN_MASK     0017777u            /* data segment length mask */
998 #define DST_BANK_MASK       mem_bank_mask       /* data segment bank mask (varies with CPU model) */
999 
1000 
1001 /* Segment Transfer Table accessors */
1002 
1003 #define STT_LENGTH_MASK     0000377u            /* STT length mask */
1004 
1005 #define STT_LENGTH_SHIFT    0                   /* STT length alignment shift */
1006 
1007 #define STT_LENGTH(l)       (((l) & STT_LENGTH_MASK) >> STT_LENGTH_SHIFT)
1008 
1009 
1010 /* Program label accessors */
1011 
1012 #define LABEL_EXTERNAL      0100000u            /* external program label flag */
1013 #define LABEL_STTN_MASK     0077400u            /* external program label STT number mask */
1014 #define LABEL_SEGMENT_MASK  0000377u            /* external program label segment mask */
1015 
1016 #define LABEL_STTN_SHIFT    8                   /* STT number alignment shift */
1017 #define LABEL_SEGMENT_SHIFT 0                   /* segment number alignment shift */
1018 
1019 #define LABEL_LOCAL         0000000u            /* local program label flag */
1020 #define LABEL_UNCALLABLE    0040000u            /* local program label uncallable flag */
1021 #define LABEL_ADDRESS_MASK  0037777u            /* local program label address mask */
1022 
1023 #define STT_NUMBER(l)       (((l) & LABEL_STTN_MASK) >> LABEL_STTN_SHIFT)
1024 #define STT_SEGMENT(l)      (((l) & LABEL_SEGMENT_MASK) >> LABEL_SEGMENT_SHIFT)
1025 
1026 #define ISR_SEGMENT         1                   /* segment number containing interrupt service routines */
1027 
1028 #define LABEL_IRQ           (LABEL_EXTERNAL | ISR_SEGMENT)          /* label for interrupt requests */
1029 #define LABEL_STTN_MAX      (LABEL_STTN_MASK >> LABEL_STTN_SHIFT)   /* STT number maximum value */
1030 
1031 #define TO_LABEL(s,n)       ((s) | (n) << LABEL_STTN_SHIFT)     /* s = segment number, n = STT number */
1032 
1033 
1034 /* Stack marker accessors */
1035 
1036 #define STMK_D              0100000u            /* dispatcher flag */
1037 #define STMK_T              0100000u            /* trace flag */
1038 #define STMK_M              0040000u            /* mapped flag */
1039 #define STMK_RTN_ADDR       0037777u            /* PB-relative return address */
1040 
1041 
1042 /* CPU registers */
1043 
1044 extern HP_WORD CIR;                             /* Current Instruction Register */
1045 extern HP_WORD NIR;                             /* Next Instruction Register */
1046 extern HP_WORD PB;                              /* Program Base Register */
1047 extern HP_WORD P;                               /* Program Counter */
1048 extern HP_WORD PL;                              /* Program Limit Register */
1049 extern HP_WORD PBANK;                           /* Program Segment Bank Register */
1050 extern HP_WORD DL;                              /* Data Limit Register */
1051 extern HP_WORD DB;                              /* Data Base Register */
1052 extern HP_WORD DBANK;                           /* Data Segment Bank Register */
1053 extern HP_WORD Q;                               /* Stack Marker Register */
1054 extern HP_WORD SM;                              /* Stack Memory Register */
1055 extern HP_WORD SR;                              /* Stack Register Counter */
1056 extern HP_WORD Z;                               /* Stack Limit Register */
1057 extern HP_WORD SBANK;                           /* Stack Segment Bank Register */
1058 extern HP_WORD TR [4];                          /* Top of Stack Registers */
1059 extern HP_WORD X;                               /* Index Register */
1060 extern HP_WORD STA;                             /* Status Register */
1061 extern HP_WORD SWCH;                            /* Switch Register */
1062 extern HP_WORD CPX1;                            /* Run-Mode Interrupt Flags Register */
1063 extern HP_WORD CPX2;                            /* Halt-Mode Interrupt Flags Register */
1064 extern HP_WORD MOD;                             /* Module Control Register */
1065 extern HP_WORD PCLK;                            /* Process Clock Register */
1066 extern HP_WORD CNTR;                            /* Microcode Counter */
1067 
1068 
1069 /* Top of stack register names */
1070 
1071 #define RA                  TR [0]
1072 #define RB                  TR [1]
1073 #define RC                  TR [2]
1074 #define RD                  TR [3]
1075 
1076 
1077 /* CPU device */
1078 
1079 extern DEVICE cpu_dev;                          /* Central Processing Unit */
1080 
1081 
1082 /* CPU state */
1083 
1084 extern jmp_buf     cpu_save_env;                /* saved environment for microcode aborts */
1085 extern POWER_STATE cpu_power_state;             /* power supply state */
1086 extern EXEC_STATE  cpu_micro_state;             /* micromachine execution state */
1087 extern uint32      cpu_stop_flags;              /* set of simulation stop flags */
1088 extern t_bool      cpu_base_changed;            /* TRUE if any base register has been changed */
1089 extern UNIT        cpu_unit [];                 /* CPU unit array (needed for memory size) */
1090 
1091 
1092 /* Condition Code B mapping table */
1093 
1094 extern const HP_WORD cpu_ccb_table [256];       /* byte-value to condition-code map */
1095 
1096 
1097 /* Global CPU functions */
1098 
1099 extern void cpu_push       (void);
1100 extern void cpu_pop        (void);
1101 extern void cpu_queue_up   (void);
1102 extern void cpu_queue_down (void);
1103 extern void cpu_flush      (void);
1104 extern void cpu_adjust_sr  (uint32 target);
1105 extern void cpu_mark_stack (void);
1106 
1107 extern void   cpu_ea      (HP_WORD mode_disp, ACCESS_CLASS *class, HP_WORD *offset, BYTE_SELECTOR *selector);
1108 extern uint32 cpu_byte_ea (ACCESS_CLASS class, uint32 byte_offset, uint32 block_length);
1109 
1110 extern void cpu_setup_irq_handler  (IRQ_CLASS class, HP_WORD parameter);
1111 extern void cpu_setup_ics_irq      (IRQ_CLASS class, TRAP_CLASS trap);
1112 extern void cpu_run_mode_interrupt (HP_WORD device_number);
1113 extern void cpu_setup_code_segment (HP_WORD label, HP_WORD *status, HP_WORD *entry_0);
1114 extern void cpu_setup_data_segment (HP_WORD segment_number, HP_WORD *bank, HP_WORD *address);
1115 extern void cpu_call_procedure     (HP_WORD label, HP_WORD offset);
1116 extern void cpu_exit_procedure     (HP_WORD new_q, HP_WORD new_sm, HP_WORD parameter);
1117 extern void cpu_start_dispatcher   (void);
1118 extern void cpu_update_pclk        (void);
1119 
1120 
1121 /* Global CPU instruction execution routines */
1122 
1123 extern t_bool cpu_interrupt_pending (t_stat *status);
1124 extern t_stat cpu_branch_short      (t_bool check_loop);
1125 
1126 extern HP_WORD cpu_add_16 (HP_WORD augend,       HP_WORD addend);
1127 extern HP_WORD cpu_sub_16 (HP_WORD minuend,      HP_WORD subtrahend);
1128 extern HP_WORD cpu_mpy_16 (HP_WORD multiplicand, HP_WORD multiplier);
1129 
1130 extern t_stat cpu_stack_op                      (void);
1131 extern t_stat cpu_shift_branch_bit_op           (void);
1132 extern t_stat cpu_move_spec_fw_imm_field_reg_op (void);
1133 extern t_stat cpu_io_cntl_prog_imm_mem_op       (void);
1134 extern t_stat cpu_eis_fp_op                     (void);
1135 extern t_stat cpu_eis_dec_op                    (void);
1136 extern t_stat cpu_cis_op                        (void);
1137