1 /* i7094_sys.c: IBM 7094 simulator interface
3 Copyright (c) 2003-2006, Robert M Supnik
5 Permission is hereby granted, free of charge, to any person obtaining a
6 copy of this software and associated documentation files (the "Software"),
7 to deal in the Software without restriction, including without limitation
8 the rights to use, copy, modify, merge, publish, distribute, sublicense,
9 and/or sell copies of the Software, and to permit persons to whom the
10 Software is furnished to do so, subject to the following conditions:
12 The above copyright notice and this permission notice shall be included in
13 all copies or substantial portions of the Software.
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
18 ROBERT M SUPNIK BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
19 IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
20 CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
22 Except as contained in this notice, the name of Robert M Supnik shall not be
23 used in advertising or otherwise to promote the sale, use or other dealings
24 in this Software without prior written authorization from Robert M Supnik.
26 29-Oct-06 RMS Added additional expanded core instructions
27 08-Jun-06 RMS Added Dave Pitts' binary loader
30 #include "i7094_defs.h"
32 #include "i7094_dat.h"
34 extern DEVICE cpu_dev
;
35 extern DEVICE ch_dev
[NUM_CHAN
];
36 extern DEVICE mt_dev
[NUM_CHAN
];
37 extern DEVICE drm_dev
;
38 extern DEVICE dsk_dev
;
39 extern DEVICE com_dev
, coml_dev
;
40 extern DEVICE cdr_dev
, cdp_dev
;
41 extern DEVICE lpt_dev
;
42 extern DEVICE clk_dev
;
46 uint32
cvt_code_to_ascii (uint32 c
, int32 sw
);
47 uint32
cvt_ascii_to_code (uint32 c
, int32 sw
);
49 /* SCP data structures and interface routines
51 sim_name simulator name string
52 sim_PC pointer to saved PC register descriptor
53 sim_emax number of words for examine
54 sim_devices array of pointers to simulated devices
55 sim_stop_messages array of pointers to stop messages
56 sim_load binary loader
59 char sim_name
[] = "IBM 7094";
61 REG
*sim_PC
= &cpu_reg
[0];
65 DEVICE
*sim_devices
[] = {
94 char ch_bkpt_msg
[] = "Channel A breakpoint, CLC: xxxxxx";
96 const char *sim_stop_messages
[] = {
100 "Undefined instruction",
102 "Nested XEC limit exceeded",
104 "Non-existent channel",
105 "Illegal instruction for 7909 channel",
106 "Illegal instruction for non-7909 channel",
107 "Non-existent device",
108 "Undefined channel instruction",
109 "Write to protected device",
110 "Illegal instruction for device",
111 "Invalid 7631 track format",
112 "7750 buffer pool empty on input",
113 "7750 buffer pool empty on output",
114 "7750 invalid line number",
115 "7750 invalid message",
119 /* Modify channel breakpoint message */
121 t_stat
ch_bkpt (uint32 ch
, uint32 clc
)
123 ch_bkpt_msg
[8] = 'A' + ch
;
124 sprintf (&ch_bkpt_msg
[27], "%06o", clc
);
128 /* Binary loader, not implemented */
130 t_stat
sim_load (FILE *fileref
, char *cptr
, char *fnam
, int flag
)
132 extern t_stat
binloader (FILE *fd
, char *file
, int loadpt
);
135 return binloader (fileref
, cptr
, 0);
141 #define I_V_FL 39 /* inst class */
142 #define I_M_FL 017 /* class mask */
143 #define I_NOP 0000000000000000 /* no operand */
144 #define I_MXR 0010000000000000 /* addr(tag) */
145 #define I_MXN 0020000000000000 /* *addr(tag) */
146 #define I_MXV 0030000000000000 /* var mul/div */
147 #define I_MXC 0040000000000000 /* convert */
148 #define I_DNP 0050000000000000 /* decr, no oper */
149 #define I_DEC 0060000000000000 /* decrement */
150 #define I_SNS 0070000000000000 /* sense */
151 #define I_IMM 0100000000000000 /* 18b immediate */
152 #define I_TAG 0110000000000000 /* tag only */
153 #define I_IOX 0120000000000000 /* IO channel */
154 #define I_TCH 0130000000000000 /* transfer channel */
155 #define I_I9N 0140000000000000 /* 7909 with nostore */
156 #define I_I9S 0150000000000000 /* 7909 */
157 #define IFAKE_7607 0001000000000000 /* fake op extensions */
158 #define IFAKE_7909 0002000000000000
159 #define DFAKE (DMASK|IFAKE_7607|IFAKE_7909)
175 #define INST_P_XIT 0 /* exit */
176 #define INST_P_SKP 1 /* do not print */
177 #define INST_P_PRA 2 /* print always */
178 #define INST_P_PNZ 3 /* print if nz */
179 #define INST_P_PNT 4 /* print if nz, term */
181 static const t_uint64 masks
[14] = {
182 03777700000000, 03777700000000,
183 03777700000000, 03777700000000,
184 03777400000000, 03700000000000,
185 03700000000000, 03777700077777,
186 03777700000000, 03777700000000,
187 03700000200000, 03700000200000,
188 03760000200000, 03740000200000 };
190 static const uint32 fld_max
[14][3] = { /* addr,tag,decr limit */
191 { INST_M_ADDR
, INST_M_TAG
, 0 },
192 { INST_M_ADDR
, INST_M_TAG
, 0 },
193 { INST_M_ADDR
, INST_M_TAG
, 0 },
194 { INST_M_ADDR
, INST_M_TAG
, INST_M_VCNT
},
195 { INST_M_ADDR
, INST_M_TAG
, INST_M_CCNT
},
196 { INST_M_ADDR
, INST_M_TAG
, INST_M_DEC
},
197 { INST_M_ADDR
, INST_M_TAG
, INST_M_DEC
},
198 { 0, INST_M_TAG
, 0 },
200 { INST_M_ADDR
, INST_M_TAG
, 0 },
201 { INST_M_ADDR
, 1, INST_M_DEC
},
202 { INST_M_ADDR
, 1, 0 },
203 { INST_M_ADDR
, 1, 0 },
204 { INST_M_ADDR
, 1, 0 }
207 static const uint32 fld_fmt
[14][3] = { /* addr,tag,decr print */
208 { INST_P_PNT
, INST_P_PNT
, INST_P_XIT
}, /* nop: all optional */
209 { INST_P_PRA
, INST_P_PNT
, INST_P_XIT
}, /* mxr: tag optional */
210 { INST_P_PRA
, INST_P_PNT
, INST_P_XIT
}, /* mxn: tag optional */
211 { INST_P_PRA
, INST_P_PNZ
, INST_P_PRA
}, /* mxv: tag optional */
212 { INST_P_PRA
, INST_P_PNZ
, INST_P_PRA
}, /* cvt: tag optional */
213 { INST_P_PNT
, INST_P_PNT
, INST_P_PNT
}, /* dnp: all optional */
214 { INST_P_PRA
, INST_P_PRA
, INST_P_PRA
}, /* dec: print all */
215 { INST_P_SKP
, INST_P_PNT
, INST_P_XIT
}, /* sns: skip addr, tag opt */
216 { INST_P_PRA
, INST_P_XIT
, INST_P_XIT
}, /* immediate: addr only */
217 { INST_P_PNZ
, INST_P_PRA
, INST_P_XIT
}, /* tag: addr optional */
218 { INST_P_PRA
, INST_P_PNZ
, INST_P_PRA
}, /* iox: tag optional */
219 { INST_P_PRA
, INST_P_PNT
, INST_P_XIT
}, /* tch: tag optional */
220 { INST_P_PRA
, INST_P_PNT
, INST_P_XIT
}, /* i9n: tag optional */
221 { INST_P_PRA
, INST_P_PNT
, INST_P_XIT
} /* i9s: tag optional */
224 static const t_uint64 ind_test
[14] = {
225 0, 0, INST_IND
, 0, 0, 0, 0,
226 0, 0, 0, CHI_IND
, CHI_IND
, CHI_IND
, CHI_IND
229 static const char *opcode
[] = {
238 "LMTM", "SLF", "SLN1",
239 "SLN2", "SLN3", "SLN4",
240 "SWT1", "SWT2", "SWT3",
241 "SWT4", "SWT5", "SWT6",
242 "BTTA", "BTTB", "BTTC",
243 "BTTD", "BTTE", "BTTF",
245 "RICA", "RICB", "RICC",
246 "RICD", "RICE", "RICF",
248 "RDCA", "RDCB", "RDCC",
249 "RDCD", "RDCE", "RDCF",
260 "TCOA", "TCOB", "TCOC",
261 "TCOD", "TCOE", "TCOF",
262 "TCOG", "TCOH", "TSX",
266 "MPY", "VLM", "VLM1",
311 "CLM", "PBT", "EFTM",
312 "SSM", "LFTM", "ESTM",
313 "ECTM", "LTM", "LSNM",
314 "EMTM", "SLT1", "SLT2",
316 "ETTA", "ETTB", "ETTC",
317 "ETTD", "ETTE", "ETTF",
328 "TCNA", "TCNB", "TCNC",
329 "TCND", "TCNE", "TCNF",
333 "MPR", "DFDH", "DFDP",
368 "IOCD", "IOCDN", "TCH",
391 static const t_uint64 opc_v
[] = {
392 0100000000000+I_DEC
, 0200000000000+I_DEC
, 0300000000000+I_DEC
,
393 0500000000000+I_DNP
, 0600000000000+I_DEC
, 0700000000000+I_DEC
,
394 0000000000000+I_MXN
, 0002000000000+I_MXN
, 0002100000000+I_MXN
,
396 0076000000000+I_SNS
, 0076000000001+I_SNS
, 0076000000002+I_SNS
,
397 0076000000003+I_SNS
, 0076000000004+I_SNS
, 0076000000005+I_SNS
,
398 0076000000006+I_SNS
, 0076000000007+I_SNS
, 0076000000010+I_SNS
,
399 0076000000011+I_SNS
, 0076000000012+I_SNS
, 0076000000014+I_SNS
,
400 0076000000016+I_SNS
, 0076000000140+I_SNS
, 0076000000141+I_SNS
,
401 0076000000142+I_SNS
, 0076000000143+I_SNS
, 0076000000144+I_SNS
,
402 0076000000161+I_SNS
, 0076000000162+I_SNS
, 0076000000163+I_SNS
,
403 0076000000164+I_SNS
, 0076000000165+I_SNS
, 0076000000166+I_SNS
,
404 0076000001000+I_SNS
, 0076000002000+I_SNS
, 0076000003000+I_SNS
,
405 0076000004000+I_SNS
, 0076000005000+I_SNS
, 0076000006000+I_SNS
,
406 0076000007000+I_SNS
, 0076000010000+I_SNS
,
407 0076000001350+I_SNS
, 0076000002350+I_SNS
, 0076000003350+I_SNS
,
408 0076000004350+I_SNS
, 0076000005350+I_SNS
, 0076000006350+I_SNS
,
409 0076000007350+I_SNS
, 0076000010350+I_SNS
,
410 0076000001352+I_SNS
, 0076000002352+I_SNS
, 0076000003352+I_SNS
,
411 0076000004352+I_SNS
, 0076000005352+I_SNS
, 0076000006352+I_SNS
,
412 0076000007352+I_SNS
, 0076000010352+I_SNS
,
414 0002200000000+I_MXN
, 0002400000000+I_MXN
,
415 0002600000000+I_MXN
, 0002700000000+I_MXN
,
416 0003000000000+I_MXN
, 0003100000000+I_MXN
,
417 0003200000000+I_MXN
, 0003300000000+I_MXN
,
418 0004000000000+I_MXN
, 0004100000000+I_NOP
, 0004200000000+I_MXR
,
419 0004300000000+I_NOP
, 0004400000000+I_NOP
, 0004600000000+I_MXR
,
420 0005100000000+I_IMM
, 0005400000000+I_IMM
, 0005500000000+I_IMM
,
421 0005600000000+I_IMM
, 0005700000000+I_IMM
,
422 0006000000000+I_MXN
, 0006100000000+I_MXN
, 0006200000000+I_MXN
,
423 0006300000000+I_MXN
, 0006400000000+I_MXN
, 0006500000000+I_MXN
,
424 0006600000000+I_MXN
, 0006700000000+I_MXN
, 0007400000000+I_MXR
,
425 0010000000000+I_MXN
, 0011400000000+I_MXC
, 0012000000000+I_MXN
,
426 0013100000000+I_NOP
, 0014000000000+I_MXN
,
427 0016100000000+I_MXN
, 0016200000000+I_MXN
,
428 0020000000000+I_MXN
, 0020400000000+I_MXV
, 0020500000000+I_MXV
,
429 0022000000000+I_MXN
, 0022100000000+I_MXN
,
430 0022400000000+I_MXV
, 0022500000000+I_MXV
,
431 0022600000000+I_MXV
, 0022700000000+I_MXV
,
432 0024000000000+I_MXN
, 0024100000000+I_MXN
,
433 0026000000000+I_MXN
, 0026100000000+I_MXN
,
434 0030000000000+I_MXN
, 0030100000000+I_MXN
,
435 0030200000000+I_MXN
, 0030300000000+I_MXN
,
436 0030400000000+I_MXN
, 0030500000000+I_MXN
,
437 0030600000000+I_MXN
, 0030700000000+I_MXN
,
438 0032000000000+I_MXN
, 0032200000000+I_MXN
,
439 0034000000000+I_MXN
, 0036100000000+I_MXN
,
440 0040000000000+I_MXN
, 0040100000000+I_MXN
,
441 0040200000000+I_MXN
, 0440000000000+I_MXN
,
442 0042000000000+I_NOP
, 0044000000000+I_MXN
, 0044100000000+I_MXN
,
443 0044200000000+I_MXN
, 0044300000000+I_MXN
, 0044400000000+I_MXN
,
444 0044500000000+I_MXN
, 0044600000000+I_MXN
,
445 0050000000000+I_MXN
, 0050200000000+I_MXN
,
446 0052000000000+I_MXN
, 0052200000000+I_MXN
,
447 0053400000000+I_MXR
, 0053500000000+I_MXR
,
448 0054000000000+I_MXN
, 0054100000000+I_MXN
,
449 0054200000000+I_MXN
, 0054300000000+I_MXN
,
450 0054400000000+I_MXN
, 0054500000000+I_MXN
,
451 0054600000000+I_MXN
, 0054700000000+I_MXN
,
452 0054000000000+I_MXN
, 0054100000000+I_MXN
,
453 0054200000000+I_MXN
, 0054300000000+I_MXN
,
454 0054400000000+I_MXN
, 0054500000000+I_MXN
,
455 0054600000000+I_MXN
, 0054700000000+I_MXN
,
456 0056000000000+I_MXN
, 0056400000000+I_MXN
,
457 0060000000000+I_MXN
, 0060100000000+I_MXN
, 0060200000000+I_MXN
,
458 0060400000000+I_MXN
, 0062100000000+I_MXN
, 0062200000000+I_MXN
,
459 0062500000000+I_MXN
, 0063000000000+I_MXN
,
460 0063400000000+I_MXR
, 0063600000000+I_MXR
,
461 0064000000000+I_MXN
, 0064000000000+I_MXN
,
462 0064200000000+I_MXN
, 0064300000000+I_MXN
,
463 0064400000000+I_MXN
, 0064500000000+I_MXN
,
464 0064600000000+I_MXN
, 0064700000000+I_MXN
,
465 0073400000000+I_TAG
, 0073700000000+I_TAG
,
466 0075400000000+I_TAG
, 0075600000000+I_TAG
,
467 0076000000000+I_MXR
, 0076100000000+I_NOP
, 0076200000000+I_MXR
,
468 0076300000000+I_MXR
, 0076400000000+I_MXR
, 0076500000000+I_MXR
,
469 0076600000000+I_MXR
, 0076700000000+I_MXR
, 0077000000000+I_MXR
,
470 0077100000000+I_MXR
, 0077200000000+I_MXR
, 0077400000000+I_MXR
,
473 0476000000000+I_SNS
, 0476000000001+I_SNS
, 0476000000002+I_SNS
,
474 0476000000003+I_SNS
, 0476000000004+I_SNS
, 0476000000005+I_SNS
,
475 0476000000006+I_SNS
, 0476000000007+I_SNS
, 0476000000010+I_SNS
,
476 0476000000016+I_SNS
, 0476000000141+I_SNS
, 0476000000142+I_SNS
,
477 0476000000143+I_SNS
, 0476000000144+I_SNS
,
478 0476000001000+I_SNS
, 0476000002000+I_SNS
, 0476000003000+I_SNS
,
479 0476000004000+I_SNS
, 0476000005000+I_SNS
, 0476000006000+I_SNS
,
480 0476000007000+I_SNS
, 0476000010000+I_SNS
,
483 0402200000000+I_MXN
, 0402400000000+I_MXN
,
484 0402600000000+I_MXN
, 0402700000000+I_MXN
,
485 0403000000000+I_MXN
, 0403100000000+I_MXN
,
486 0403200000000+I_MXN
, 0403300000000+I_MXN
,
487 0404200000000+I_NOP
, 0404600000000+I_NOP
,
488 0405100000000+I_IMM
, 0405400000000+I_IMM
, 0405500000000+I_IMM
,
489 0405600000000+I_IMM
, 0405700000000+I_IMM
,
490 0406000000000+I_MXN
, 0406100000000+I_MXN
, 0406200000000+I_MXN
,
491 0406300000000+I_MXN
, 0406400000000+I_MXN
, 0406500000000+I_MXN
,
492 0406600000000+I_MXN
, 0406700000000+I_MXN
,
493 0410000000000+I_MXN
, 0411400000000+I_MXC
, 0412000000000+I_MXN
,
494 0413000000000+I_NOP
, 0414000000000+I_MXN
, 0415400000000+I_MXC
,
495 0420000000000+I_MXN
, 0424000000000+I_MXN
, 0424100000000+I_MXN
,
496 0426000000000+I_MXN
, 0426100000000+I_MXN
,
497 0430000000000+I_MXN
, 0430100000000+I_MXN
,
498 0430200000000+I_MXN
, 0430300000000+I_MXN
,
499 0430400000000+I_MXN
, 0430500000000+I_MXN
,
500 0430600000000+I_MXN
, 0430700000000+I_MXN
,
501 0432000000000+I_MXN
, 0434000000000+I_MXN
,
502 0450000000000+I_MXN
, 0450100000000+I_MXN
, 0452000000000+I_MXN
,
503 0453400000000+I_MXR
, 0453500000000+I_MXR
,
504 0454000000000+I_MXN
, 0454100000000+I_MXN
,
505 0454200000000+I_MXN
, 0454300000000+I_MXN
,
506 0454400000000+I_MXN
, 0454500000000+I_MXN
,
507 0454600000000+I_MXN
, 0454700000000+I_MXN
,
508 0454000000000+I_MXN
, 0454100000000+I_MXN
,
509 0454200000000+I_MXN
, 0454300000000+I_MXN
,
510 0454400000000+I_MXN
, 0454500000000+I_MXN
,
511 0454600000000+I_MXN
, 0454700000000+I_MXN
,
512 0460000000000+I_MXN
, 0460200000000+I_MXN
, 0460300000000+I_MXN
,
513 0462000000000+I_MXN
, 0462500000000+I_MXN
,
514 0463400000000+I_MXR
, 0463600000000+I_MXR
,
515 0464000000000+I_MXN
, 0464000000000+I_MXN
,
516 0464200000000+I_MXN
, 0464300000000+I_MXN
,
517 0464400000000+I_MXN
, 0464500000000+I_MXN
,
518 0464600000000+I_MXN
, 0464700000000+I_MXN
,
519 0473400000000+I_TAG
, 0473700000000+I_TAG
,
520 0475400000000+I_TAG
, 0475600000000+I_TAG
,
521 0476000000000+I_MXR
, 0476300000000+I_MXR
, 0476400000000+I_MXR
,
522 0476500000000+I_MXR
, 0477300000000+I_MXR
, 0477200000000+I_MXR
,
525 0010100000000+I_MXN
, 0410100000000+I_MXN
,
526 0056200000000+I_MXN
, 0456400000000+I_MXN
,
527 0476100000041+I_SNS
, 0476100000042+I_SNS
,
528 0476100000043+I_SNS
, 0476100000044+I_SNS
,
530 01000000000000+I_IOX
, 01000000200000+I_IOX
, 01100000000000+I_TCH
,
531 01200000000000+I_IOX
, 01200000200000+I_IOX
,
532 01300000000000+I_IOX
, 01300000200000+I_IOX
,
533 01400000000000+I_IOX
, 01400000200000+I_IOX
,
534 01500000000000+I_IOX
, 01500000200000+I_IOX
,
535 01600000000000+I_IOX
, 01600000200000+I_IOX
,
536 01700000000000+I_IOX
, 01700000200000+I_IOX
,
538 02000000000000+I_TCH
, 02000000200000+I_IOX
,
539 02100000000000+I_TCH
, 02100000200000+I_TCH
,
540 02200000000000+I_I9N
, 02220000000000+I_TCH
,
541 02200000200000+I_I9N
, 02220000200000+I_TCH
,
542 02240000000000+I_I9N
, 02260000000000+I_TCH
,
543 02240000200000+I_I9N
,
544 02300000000000+I_I9S
, 02300000200000+I_I9S
,
545 02340000000000+I_I9S
,
546 02400000000000+I_IOX
,
547 02500000000000+I_IOX
, 02500000200000+I_IOX
,
548 02600000200000+I_I9S
, 02640000000000+I_I9S
, 02640000200000+I_I9S
,
549 02700000000000+I_I9S
, 02700000200000+I_IOX
,
559 *val = pointer to values
560 *uptr = pointer to unit
566 t_stat
fprint_sym (FILE *of
, t_addr addr
, t_value
*val
,
567 UNIT
*uptr
, int32 sw
)
569 uint32 i
, j
, k
, l
, fmt
, c
, fld
[3];
574 if (uptr
== NULL
) uptr
= &cpu_unit
;
575 dptr
= find_dev_from_unit (uptr
);
576 if (dptr
== NULL
) return SCPE_IERR
;
578 if (sw
& SWMASK ('C')) { /* character? */
579 c
= (uint32
) (inst
& 077);
580 fprintf (of
, "%c", cvt_code_to_ascii (c
, sw
));
583 if (sw
& SWMASK ('S')) { /* string? */
584 for (i
= 36; i
> 0; i
= i
- 6) {
585 c
= (uint32
) ((inst
>> (i
- 6)) & 077);
586 fprintf (of
, "%c", cvt_code_to_ascii (c
, sw
));
590 if (!(sw
& (SWMASK ('M')|SWMASK ('I')|SWMASK ('N'))) || /* M, N or I? */
591 (dptr
->dwidth
!= 36)) return SCPE_ARG
;
593 /* Instruction decode */
595 fld
[0] = ((uint32
) inst
& 0777777);
596 fld
[1] = GET_TAG (inst
); /* get 3 fields */
597 fld
[2] = GET_DEC (inst
);
598 if (sw
& SWMASK ('I')) inst
|= IFAKE_7607
; /* decode as 7607? */
599 if (sw
& SWMASK ('N')) inst
|= IFAKE_7909
; /* decode as 7909? */
601 for (i
= 0; opc_v
[i
] > 0; i
++) { /* loop thru ops */
602 j
= (int32
) ((opc_v
[i
] >> I_V_FL
) & I_M_FL
); /* get class */
603 if ((opc_v
[i
] & DFAKE
) == (inst
& masks
[j
])) { /* match? */
604 if (inst
& ind_test
[j
]) /* indirect? */
605 fprintf (of
, "%s*", opcode
[i
]);
606 else fprintf (of
, "%s", opcode
[i
]); /* opcode */
607 for (k
= 0; k
< 3; k
++) fld
[k
] = fld
[k
] & fld_max
[j
][k
];
608 for (k
= 0; k
< 3; k
++) { /* loop thru fields */
609 fmt
= fld_fmt
[j
][k
]; /* get format */
610 if (fmt
== INST_P_XIT
) return SCPE_OK
;
611 switch (fmt
) { /* case on format */
613 case INST_P_PNT
: /* print nz, else term */
614 for (l
= k
, c
= 0; l
< 3; l
++) c
|= fld
[k
];
615 if (c
== 0) return SCPE_OK
;
616 case INST_P_PNZ
: /* print non-zero */
617 fputc (k
? ',': ' ', of
);
618 if (fld
[k
]) fprintf (of
, "%-o", fld
[k
]);
620 case INST_P_PRA
: /* print always */
621 fputc (k
? ',': ' ', of
);
622 fprintf (of
, "%-o", fld
[k
]);
624 case INST_P_SKP
: /* skip */
628 return SCPE_OK
; /* done */
634 /* Convert character to code to ASCII
639 uint32
cvt_code_to_ascii (uint32 c
, int32 sw
)
641 if (sw
& SWMASK ('B')) {
642 if (sw
& SWMASK ('A')) return bcd_to_ascii_a
[c
];
643 else return bcd_to_ascii_h
[c
];
645 else if (sw
& SWMASK ('A')) return nine_to_ascii_a
[c
];
646 else return nine_to_ascii_h
[c
];
652 *cptr = pointer to input string
654 uptr = pointer to unit
655 *val = pointer to output values
658 status = error status
661 t_stat
parse_sym (char *cptr
, t_addr addr
, UNIT
*uptr
, t_value
*val
, int32 sw
)
669 while (isspace (*cptr
)) cptr
++;
670 if ((sw
& SWMASK ('C')) || ((*cptr
== '\'') && cptr
++)) { /* character? */
671 if (cptr
[0] == 0) return SCPE_ARG
; /* must have 1 char */
672 val
[0] = (t_value
) cvt_ascii_to_code (cptr
[0] & 0177, sw
);
675 if ((sw
& SWMASK ('S')) || ((*cptr
== '"') && cptr
++)) { /* sixbit string? */
676 if (cptr
[0] == 0) return SCPE_ARG
; /* must have 1 char */
677 for (i
= 0; i
< 6; i
++) {
679 if (c
) val
[0] = (val
[0] << 6) | ((t_value
) cvt_ascii_to_code (c
, sw
));
681 val
[0] = val
[0] << (6 * (6 - i
));
688 cptr
= get_glyph (cptr
, gbuf
, 0); /* get opcode */
689 j
= strlen (gbuf
); /* get length */
690 if (gbuf
[j
- 1] == '*') { /* indirect? */
695 for (i
= 0; (opcode
[i
] != NULL
) && (strcmp (opcode
[i
], gbuf
) != 0) ; i
++) ;
696 if (opcode
[i
] == NULL
) return SCPE_ARG
;
697 j
= (uint32
) ((opc_v
[i
] >> I_V_FL
) & I_M_FL
); /* get class */
698 val
[0] = opc_v
[i
] & DMASK
;
700 if (ind_test
[j
]) val
[0] |= ind_test
[j
];
701 else return SCPE_ARG
;
704 for (i
= 0; i
< 3; i
++) fld
[i
] = 0; /* clear inputs */
705 for (i
= 0; (i
< 3) && *cptr
; i
++) { /* parse inputs */
706 if (i
< 2) cptr
= get_glyph (cptr
, gbuf
, ','); /* get glyph */
707 else cptr
= get_glyph (cptr
, gbuf
, 0);
708 if (gbuf
[0]) { /* anything? */
709 fld
[i
] = get_uint (gbuf
, 8, fld_max
[j
][i
], &r
);
710 if ((r
!= SCPE_OK
) || (fld_max
[j
][i
] == 0)) return SCPE_ARG
;
713 if (*cptr
!= 0) return SCPE_ARG
; /* junk at end? */
715 val
[0] = val
[0] | fld
[0] | (fld
[1] << INST_V_TAG
) | (fld
[2] << INST_V_DEC
);
719 /* Convert ASCII to character code
723 uint32
cvt_ascii_to_code (uint32 c
, int32 sw
)
725 if (sw
& SWMASK ('B')) return ascii_to_bcd
[c
];
726 else return ascii_to_nine
[c
];