1; Adapteva EPIPHANY CPU description. -*- Scheme -*-
2; Copyright 1998, 1999, 2000, 2001, 2003, 2006, 2007, 2008, 2009, 2010, 2011
3; Free Software Foundation, Inc.
4;
5; Contributed by Embecosm on behalf of Adapteva, Inc.
6; This file is part of the GNU Binutils and of GDB.
7;
8; This program is free software; you can redistribute it and/or modify
9; it under the terms of the GNU General Public License as published by
10; the Free Software Foundation; either version 3 of the License, or
11; (at your option) any later version.
12;
13; This program is distributed in the hope that it will be useful,
14; but WITHOUT ANY WARRANTY; without even the implied warranty of
15; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16; GNU General Public License for more details.
17;
18; You should have received a copy of the GNU General Public License
19; along with this program; if not, write to the Free Software
20; Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
21; MA 02110-1301, USA.
22
23(include "simplify.inc")
24					; define-arch must appear first
25
26(define-arch
27  (name epiphany) ; name of cpu family
28  (comment "Adapteva, Inc. EPIPHANY family")
29  (default-alignment aligned)
30  (insn-lsb0? #t)
31
32					; - a 16/32 bit instruction machine (the default)
33
34  (machs epiphany32)
35  (isas epiphany)
36  )
37
38					; Attributes.
39
40(define-attr
41  (for insn)
42  (type boolean)
43  (name SHORT-INSN)
44  (comment "instruction is a 16 bit form")
45  )
46
47;; 3 bit add/sub immediate forms - useful for relaxing into 11 bit form
48(define-attr
49  (for insn)
50  (type boolean)
51  (name IMM3)
52  (comment "instruction has a 3 bit immediate form")
53  )
54
55;; 8 bit mov immediate forms - useful for relaxing into 16 bit form
56(define-attr
57  (for insn)
58  (type boolean)
59  (name IMM8)
60  (comment "instruction has a 8 bit immediate form")
61  )
62
63					; Instruction set parameters.
64
65(define-isa
66  (name epiphany)
67  (comment "Adapteva, Inc. EPIPHANY32 ISA")
68
69  (default-insn-word-bitsize 32)
70  (default-insn-bitsize 32)
71  (base-insn-bitsize 32)
72  (decode-assist (3 2 1 0))  ; CGEN can figure this out
73  (liw-insns 1)				; # instructions fetched at once
74  )
75
76					; Cpu family definitions.
77
78
79(define-cpu
80					; cpu names must be distinct from the architecture name and machine names.
81  (name epiphanybf)
82  (comment "Adapteva, Inc. EPIPHANY Family")
83  (endian little)
84  (word-bitsize 32)
85  )
86
87(define-cpu
88  (name epiphanymf)
89  (comment "Adapteva, Inc. EPIPHANY Family")
90  (endian little)
91  (word-bitsize 32)
92  )
93
94
95(define-mach
96  (name epiphany32)
97  (comment "Adapteva EPIPHANY")
98  (cpu epiphanybf)
99  )
100
101
102					; Model descriptions.
103
104(define-model
105  (name epiphany32) (comment "Adapteva EPIPHANY 32/16") (attrs)
106  (mach epiphany32)
107
108  (unit u-exec "Execution Unit" ()
109	1 1 ; issue done
110	() ; state
111	() ; inputs
112	() ; outputs
113	() ; profile action (default)
114	)
115  )
116
117
118
119					; Instruction fields.
120					;
121					; Attributes:
122					; XXX: what EPIPHANY attrs
123					; PCREL-ADDR: pc relative value (for reloc and disassembly purposes)
124					; ABS-ADDR: absolute address (for reloc and disassembly purposes?)
125					; RESERVED: bits are not used to decode insn, must be all 0
126					; RELOC: there is a relocation associated with this field
127
128(define-attr
129  (for ifield operand)
130  (type boolean)
131  (name RELOC)
132  (comment "there is a reloc associated with this field (experiment)")
133  )
134
135;; define the fields of the instruction.
136;;   name            description              ATTR  MSB LEN
137(dnf f-opc	  "primary opcode"	       ()     3 4)
138(dnf f-opc-4-1    "secondary opcode"           ()     4 1)
139(dnf f-opc-6-3    "secondary opcode"           ()     6 3) ;;
140(dnf f-opc-8-5    "tertiary opcode"            ()     8 5) ;;
141(dnf f-opc-19-4   "additional opcode bits"     ()    19 4)
142(dnf f-condcode   "condition codes" 	       ()     7 4)
143(dnf f-secondary-ccs "flag for secondary ccs"  ()     7 1)
144(dnf f-shift      "shift amount"               ()     9 5)
145(dnf f-wordsize   "load/store size"            ()     6 2)
146(dnf f-store      "load/store flag"            ()     4 1) ;; 0==load,1==store
147(dnf f-opc-8-1    "opcode bits"                ()     8 1)
148(dnf f-opc-31-32  "all opcode set"             ()     31 32)
149
150(df f-simm8	  "branch displacement"   (PCREL-ADDR RELOC) 15 8 INT
151    ((value pc) (sra SI (sub SI value pc) 1))
152    ((value pc) (add SI (mul SI value 2) pc)))
153
154(df f-simm24     "branch displacement"	  (PCREL-ADDR RELOC) 31 24 INT
155    ((value pc) (sra SI (sub SI value pc) 1))
156    ((value pc) (add SI (mul SI value 2) pc)))
157
158(df f-sdisp3     "signed immediate 3 bit"      ()     9 3  INT #f #f)
159
160(dnf f-disp3      "address offset"             ()     9 3)
161(dnf f-disp8      "address offset"             ()    23 8)
162
163(dnf f-imm8      "move/add/sub imm8"           ()    12 8)
164(dnf f-imm-27-8  "move/add/sub imm16"          ()    27 8)
165(dnf f-addsubx   "+/- index address"           ()    20 1)
166(dnf f-subd      "+/- displ address"           ()    24 1)
167(dnf f-pm        "post-modify immediate"       ()    25 1)
168
169(dnf f-rm        "short rm"                    ()     9 3)   ;; RM
170(dnf f-rn        "short rn"                    ()    12 3)   ;; RN
171(dnf f-rd        "short rd"                    ()    15 3)   ;; RD
172
173(dnf f-rm-x       "extension rm"               ()    25 3)   ;; RM
174(dnf f-rn-x       "extension rn"               ()    28 3)   ;; RN
175(dnf f-rd-x       "extension rd"               ()    31 3)   ;; RD
176
177(dnf f-dc-9-1     "DC"                 (RESERVED)     9 1)
178
179(dnf f-sn        "short sn"                    ()    12 3)   ;; SN
180(dnf f-sd        "short sd"                    ()    15 3)   ;; SD
181
182(dnf f-sn-x       "extension sn"               ()    28 3)   ;; SN
183(dnf f-sd-x       "extension sd"               ()    31 3)   ;; SD
184
185
186
187(dnf f-dc-7-4     "movts zeros"                 ()     7 4)
188(dnf f-trap-swi-9-1     "trap or swi"                 ()     9 1)
189(dnf f-gien-gidis-9-1     "gien or gidis"                 ()     9 1)
190
191
192(dnf f-dc-15-3    "DC"                 (RESERVED)    15 3)
193(dnf f-dc-15-7    "DC"                 (RESERVED)    15 7)
194(dnf f-dc-15-6    "DC"                 ()            15 6)
195(dnf f-trap-num   "trap number"                ()    15 6)
196
197(dnf f-dc-20-1    "DC"                 (RESERVED)    20 1)
198
199(dnf f-dc-21-1    "DC"                 (RESERVED)    21 1)
200(dnf f-dc-21-2    "DC"                 (RESERVED)    21 2)
201
202(dnf f-dc-22-3    "DC"                 (RESERVED)    22 3)
203(dnf f-dc-22-2    "DC"                 (RESERVED)    22 2)
204(dnf f-dc-22-1    "DC"                 (RESERVED)    22 1)
205
206(dnf f-dc-25-6    "DC"                 (RESERVED)    25 6)
207(dnf f-dc-25-4    "DC"                 (RESERVED)    25 4)
208(dnf f-dc-25-2    "DC"                 (RESERVED)    25 2)
209(dnf f-dc-25-1    "DC"                 (RESERVED)    25 1)
210
211(dnf f-dc-28-1    "DC"                 (RESERVED)    28 1)
212(dnf f-dc-31-3    "DC"                 (RESERVED)    31 3)
213
214(dnmf f-disp11 "Unsigned offset for load/store" () UINT (f-disp3 f-disp8)
215      (sequence ()
216		(set (ifield f-disp8) (and (srl (ifield f-disp11) 3) (const 255)))
217		(set (ifield f-disp3) (and (ifield f-disp11) 7)))
218      (sequence ()
219		(set (ifield f-disp11) (or (sll (ifield f-disp8) 3)
220					   (ifield f-disp3)))
221		)
222      )
223
224
225(dnmf f-sdisp11 "Signed offset for load/store" () INT (f-disp3 f-disp8)
226      (sequence ()			;encode
227		(set (ifield f-disp8) (and #xff (srl SI (ifield f-sdisp11) 3)))
228		(set (ifield f-disp3)  (and SI (ifield f-sdisp11) 7)))
229      (sequence ()			;decode
230		(set (ifield f-sdisp11)
231		     (sub SI (xor (and (or (sll (ifield f-disp8) 3)
232					   (ifield f-disp3))
233				       #x7ff)
234				  #x400)
235			  #x400)))
236      )
237
238(dnmf f-imm16 "Short immediate for move/add/sub" () UINT (f-imm8 f-imm-27-8)
239      (sequence ()
240		(set (ifield f-imm8) (and (ifield f-imm16) #xff))
241		(set (ifield f-imm-27-8) (srl (ifield f-imm16) 8)))
242      (sequence ()
243		(set (ifield f-imm16) (or (sll (ifield f-imm-27-8) 8)
244					  (ifield f-imm8))))
245      )
246
247
248;; 32 bit instructions have the register number broken into two non-contiguous fields
249
250(define-pmacro (x-reg-field reg)
251  (define-multi-ifield
252    (name (.sym "f-" reg "6"))
253    (mode UINT)
254    (subfields (.sym "f-" reg "-x") (.sym "f-" reg))
255    (insert (sequence ()
256		      (set (ifield (.sym "f-" reg))   (and (ifield (.sym "f-" reg "6"))
257							   (const 7)))
258		      (set (ifield (.sym "f-" reg "-x"))  (srl (ifield (.sym "f-" reg "6"))
259							       (const 3)))
260		      ))
261    (extract (sequence ()
262		       (set (ifield (.sym "f-" reg "6")) (or (sll (ifield (.sym "f-" reg "-x"))
263								  (const 3))
264							     (ifield (.sym "f-" reg))))
265		       ))
266    )
267  )
268
269(x-reg-field rd)			; f-rd6
270(x-reg-field rn)			; f-rn6
271(x-reg-field rm)			; f-rm6
272(x-reg-field sd)			; f-sd6
273(x-reg-field sn)			; f-sn6
274
275
276;;;;;;;;;;
277					; Enums. ;
278;;;;;;;;;;
279
280					; insn-opc: bits 3..0 - major family selector
281(define-normal-insn-enum insn-opc "opc enums" () OP4_ f-opc
282  (
283   BRANCH16  ;; 0000
284   LDSTR16X  ;; 0001
285   FLOW16    ;; 0010
286   IMM16     ;; 0011
287   LDSTR16D  ;; 0100
288   LDSTR16P  ;; 0101
289   LSHIFT16  ;; 0110 - logical shift
290   DSP16     ;; 0111 - 3 reg DSP 16 bit insns
291   BRANCH    ;; 1000
292   LDSTRX    ;; 1001
293   ALU16     ;; 1010 - 3 reg 16 bit
294   IMM32     ;; 1011
295   LDSTRD    ;; 1100
296   LDSTRP    ;; 1101
297   ASHIFT16  ;; 1110   ASR, BITR
298   MISC      ;; 1111 - 32 bit shifts, 3 reg ALU, 3 reg DSP, FLOW, BITR
299   )
300  )
301
302(define-normal-insn-enum insn-wordsize "memory access width" () OPW_ f-wordsize
303					; specifies the size of a memory load/store operation
304  (BYTE SHORT WORD DOUBLE)
305  )
306
307(define-normal-insn-enum insn-memory-access "memory access direction" () OP_ f-store
308					; load=0, store=1
309  (LOAD STORE)
310  )
311
312					; enum for trap codes used by simulator
313(define-normal-insn-enum trap-codes "trap instruction dispatch code" () TRAP_ f-trap-num
314  (write read open exit pass fail close other)
315  )
316
317					; cond branch: bits 7..4
318					;
319(define-normal-insn-enum insn-cond "branch conditions" () OPC_ f-condcode
320  (EQ NE GTU GTEU LTEU LTU GT GTE LT LTE BEQ BNE BLT BLTE B BL))
321
322					; dsp 3 operand opcodes
323(define-normal-insn-enum insn-bop "binary operator subcodes" () OPB_ f-opc-6-3
324  (EOR ADD LSL SUB LSR AND ASR ORR))
325
326					; dsp 3 operand opcodes
327(define-normal-insn-enum insn-bopext "binary operator subcodes" () OPBE_ f-opc-6-3
328  (FEXT FDEP LFSR - - - - -))
329
330
331(define-normal-insn-enum insn-fop "floating operators" () OPF_ f-opc-6-3
332  (ADD SUB MUL MADD MSUB FLOAT FIX FABS))
333
334(define-normal-insn-enum insn-fopexn "extended floating operators" () OPF_ f-opc-6-3
335  (FRECIP FSQRT - - - - - -))
336
337
338
339
340; Immediate operation secondary opcodes
341(define-normal-insn-enum insn-immop "immediate operators" () OPI_ f-opc-6-3
342  (- ADD - SUB - - - TRAP) ; TRAP is special extension for simulator
343  )
344
345					; don't care fields
346(define-normal-insn-enum insn-dc-25-2 "don't cares" () OPI_25_2_ f-dc-25-2
347  (MBZ))
348
349; General Register keyword names.
350(define-keyword
351  (name gr-names)
352  (print-name h-registers)
353  (prefix "")
354  (values
355; some preferred aliases
356   (fp 11) (sp 13) (lr 14)
357; the default register names
358   (r0  0)  (r1  1)  (r2  2)  (r3  3)  (r4  4)  (r5  5)  (r6  6)  (r7  7)
359   (r8  8)  (r9  9) (r10 10) (r11 11) (r12 12) (r13 13) (r14 14) (r15 15)
360   (r16 16) (r17 17) (r18 18) (r19 19) (r20 20) (r21 21) (r22 22) (r23 23)
361   (r24 24) (r25 25) (r26 26) (r27 27) (r28 28) (r29 29) (r30 30) (r31 31)
362   (r32 32) (r33 33) (r34 34) (r35 35) (r36 36) (r37 37) (r38 38) (r39 39)
363   (r40 40) (r41 41) (r42 42) (r43 43) (r44 44) (r45 45) (r46 46) (r47 47)
364   (r48 48) (r49 49) (r50 50) (r51 51) (r52 52) (r53 53) (r54 54) (r55 55)
365   (r56 56) (r57 57) (r58 58) (r59 59) (r60 60) (r61 61) (r62 62) (r63 63)
366; some less popular aliases
367   (a1  0) (a2  1) (a3  2) (a4  3) (v1  4) (v2  5) (v3  6) (v4  7)
368   (v5  8) (v6  9) (v7 10) (v8 11)
369   (sb 9) (sl 10) (ip 12)
370   )
371  )
372
373(define-normal-insn-enum post-index "+/- index register" () DIR_ f-addsubx (POSTINC POSTDEC))
374
375(define-normal-insn-enum disp-post-modify "postmodify displacement" () PMOD_ f-pm (DISP POST))
376
377;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
378					; Hardware pieces.
379;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
380
381;; 64 general-purpose registers
382(define-hardware
383  (name h-registers)
384  (comment "all addressable registers")
385  (type register SI (64))
386  (attrs PROFILE CACHE-ADDR)
387  (indices extern-keyword gr-names)
388  )
389
390
391
392;; Same 64 registers as floating point registers
393(define-hardware
394  (name h-fpregisters)
395  (comment "all GPRs as float values")
396  (type register SF (64))
397  (attrs PROFILE VIRTUAL)
398  (indices extern-keyword gr-names)
399  (get (index) (subword SF (reg h-registers index) 0))
400  (set (index newval) (set (reg h-registers index) (subword SI newval 0)))
401  )
402
403;; define processor status bits as physical hardware
404
405(define-pmacro (psw-h-bit name cmt)
406  (dsh name cmt () (register BI)))
407
408(psw-h-bit h-zbit "integer zero bit")
409(psw-h-bit h-nbit "integer neg bit")
410(psw-h-bit h-cbit "integer carry bit")
411(psw-h-bit h-vbit "integer overflow bit")
412(psw-h-bit h-vsbit "integer overflow sticky")
413
414
415(psw-h-bit h-bzbit "floating point zero bit")
416(psw-h-bit h-bnbit "floating point neg bit")
417(psw-h-bit h-bvbit "floating point ovfl bit")
418(psw-h-bit h-bubit "floating point underfl bit")
419(psw-h-bit h-bibit "floating point invalid bit")
420(psw-h-bit h-bcbit "floating point carry bit")
421
422(psw-h-bit h-bvsbit "floating point overflow sticky")
423(psw-h-bit h-bisbit  "floating point invalid sticky")
424(psw-h-bit h-busbit  "floating point underflow sticky")
425
426(psw-h-bit h-expcause0bit  "exceprion cause bit0")
427(psw-h-bit h-expcause1bit  "exceprion cause bit1")
428(psw-h-bit h-expcause2bit  "external load stalled bit")
429(psw-h-bit h-extFstallbit  "external fetch stalled bit")
430
431(psw-h-bit h-trmbit  "0=round to nearest, 1=trunacte select bit")
432(psw-h-bit h-invExcEnbit  "invalid exception enable bit")
433(psw-h-bit h-ovfExcEnbit  "overflow exception enable bit")
434(psw-h-bit h-unExcEnbit  "underflow exception enablebit ")
435
436(psw-h-bit h-timer0bit0  "timer 0 mode selection 0")
437(psw-h-bit h-timer0bit1  "timer 0 mode selection 1")
438(psw-h-bit h-timer0bit2  "timer 0 mode selection 2")
439(psw-h-bit h-timer0bit3  "timer 0 mode selection 3")
440(psw-h-bit h-timer1bit0  "timer 1 mode selection 0")
441(psw-h-bit h-timer1bit1  "timer 1 mode selection 1")
442(psw-h-bit h-timer1bit2  "timer 1 mode selection 2")
443(psw-h-bit h-timer1bit3  "timer 1 mode selection 3")
444
445(psw-h-bit h-mbkptEnbit  "multicore bkpt enable")
446(psw-h-bit h-clockGateEnbit  "clock gating enable bkpt enable")
447
448
449(psw-h-bit h-coreCfgResBit12 "core config bit 12")
450(psw-h-bit h-coreCfgResBit13 "core config bit 13")
451(psw-h-bit h-coreCfgResBit14 "core config bit 14")
452(psw-h-bit h-coreCfgResBit15 "core config bit 15")
453(psw-h-bit h-coreCfgResBit16 "core config bit 16")
454
455
456(psw-h-bit h-coreCfgResBit20 "core config bit 20")
457(psw-h-bit h-coreCfgResBit21 "core config bit 21")
458
459(psw-h-bit h-coreCfgResBit24 "core config bit 24")
460(psw-h-bit h-coreCfgResBit25 "core config bit 25")
461(psw-h-bit h-coreCfgResBit26 "core config bit 26")
462(psw-h-bit h-coreCfgResBit27 "core config bit 27")
463(psw-h-bit h-coreCfgResBit28 "core config bit 28")
464(psw-h-bit h-coreCfgResBit29 "core config bit 29")
465(psw-h-bit h-coreCfgResBit30 "core config bit 30")
466(psw-h-bit h-coreCfgResBit31 "core config bit 31")
467
468
469(psw-h-bit h-arithmetic-modebit0  "arithmetic mode bit0")
470(psw-h-bit h-arithmetic-modebit1  "arithmetic mode bit1")
471(psw-h-bit h-arithmetic-modebit2  "arithmetic mode bit2")
472
473
474(psw-h-bit h-gidisablebit "global interrupt disable bit")
475(psw-h-bit h-kmbit "kernel mode bit")
476(psw-h-bit h-caibit "core active indicator mode bit")
477(psw-h-bit h-sflagbit "sflag bit")
478
479
480					; Define operands for each of the physical bits
481(define-pmacro (psw-bit name hname cmt)
482  (dnop name cmt (SEM-ONLY) hname f-nil)
483  )
484
485(psw-bit zbit h-zbit "integer zero bit")
486(psw-bit nbit h-nbit "integer neg bit")
487(psw-bit cbit h-cbit "integer carry bit")
488(psw-bit vbit h-vbit "integer overflow bit")
489
490(psw-bit bzbit  h-bzbit "floating point zero bit")
491(psw-bit bnbit  h-bnbit "floating point neg bit")
492(psw-bit bvbit  h-bvbit "floating point ovfl bit")
493(psw-bit bcbit  h-bcbit "floating point carry bit")
494
495(psw-bit bubit h-bubit "floating point underfl bit")
496(psw-bit bibit h-bibit "floating point invalid bit")
497
498
499(psw-bit vsbit  h-vsbit  "integer overflow sticky")
500(psw-bit bvsbit h-bvsbit "floating point overflow sticky")
501(psw-bit bisbit  h-bisbit  "floating point invalid sticky")
502(psw-bit busbit  h-busbit  "floating point underflow sticky")
503(psw-bit expcause0bit h-expcause0bit  "exceprion cause bit0")
504(psw-bit expcause1bit h-expcause1bit  "exceprion cause bit1")
505
506
507(psw-bit expcause2bit  h-expcause2bit  "external load stalled bit")
508(psw-bit extFstallbit  h-extFstallbit  "external fetch stalled bit")
509
510(psw-bit trmbit  h-trmbit  "0=round to nearest, 1=trunacte selct bit")
511(psw-bit invExcEnbit  h-invExcEnbit  "invalid exception enable bit")
512(psw-bit ovfExcEnbit  h-ovfExcEnbit  "overflow exception enable bit")
513(psw-bit unExcEnbit  h-unExcEnbit  "underflow exception enable bit")
514
515(psw-bit timer0bit0  h-timer0bit0  "timer 0 mode selection 0")
516(psw-bit timer0bit1  h-timer0bit1  "timer 0 mode selection 1")
517(psw-bit timer0bit2  h-timer0bit2  "timer 0 mode selection 2")
518(psw-bit timer0bit3  h-timer0bit3  "timer 0 mode selection 3")
519
520(psw-bit timer1bit0  h-timer1bit0  "timer 1 mode selection 0")
521(psw-bit timer1bit1  h-timer1bit1  "timer 1 mode selection 1")
522(psw-bit timer1bit2  h-timer1bit2  "timer 1 mode selection 2")
523(psw-bit timer1bit3  h-timer1bit3  "timer 1 mode selection 3")
524
525(psw-bit mbkptEnbit  h-mbkptEnbit "multicore bkpt enable")
526(psw-bit clockGateEnbit  h-clockGateEnbit "clock gate enable enable")
527
528(psw-bit arithmetic-modebit0  h-arithmetic-modebit0  "arithmetic mode bit0")
529(psw-bit arithmetic-modebit1  h-arithmetic-modebit1  "arithmetic mode bit1")
530(psw-bit arithmetic-modebit2  h-arithmetic-modebit2  "arithmetic mode bit2")
531
532(psw-bit coreCfgResBit12  h-coreCfgResBit12 "core config bit 12")
533(psw-bit coreCfgResBit13  h-coreCfgResBit13 "core config bit 13")
534(psw-bit coreCfgResBit14  h-coreCfgResBit14 "core config bit 14")
535(psw-bit coreCfgResBit15  h-coreCfgResBit15 "core config bit 15")
536(psw-bit coreCfgResBit16  h-coreCfgResBit16 "core config bit 16")
537
538(psw-bit coreCfgResBit20  h-coreCfgResBit20 "core config bit 20")
539(psw-bit coreCfgResBit21  h-coreCfgResBit21 "core config bit 21")
540
541(psw-bit coreCfgResBit24  h-coreCfgResBit24 "core config bit 24")
542(psw-bit coreCfgResBit25  h-coreCfgResBit25 "core config bit 25")
543(psw-bit coreCfgResBit26  h-coreCfgResBit26 "core config bit 26")
544(psw-bit coreCfgResBit27  h-coreCfgResBit27 "core config bit 27")
545(psw-bit coreCfgResBit28  h-coreCfgResBit28 "core config bit 28")
546(psw-bit coreCfgResBit29  h-coreCfgResBit29 "core config bit 29")
547(psw-bit coreCfgResBit30  h-coreCfgResBit30 "core config bit 30")
548(psw-bit coreCfgResBit31  h-coreCfgResBit31 "core config bit 31")
549
550
551(psw-bit gidisablebit h-gidisablebit "global interrupt disable bit")
552(psw-bit kmbit h-kmbit "kernel mode bit")
553(psw-bit caibit h-caibit "core actibe indicator bit")
554(psw-bit sflagbit h-sflagbit "sflag bit")
555
556
557
558
559;; Special registers - accessed via MOVTS and MOVFS.
560;;
561;;  "Core control and status" in group MR0=0, MR1=0
562
563(define-keyword
564  (name cr-names)
565  (print-name h-core-registers)
566  (prefix "")
567  (values  (config         0)
568	   (status         1) ; unified condition codes
569	   (pc             2) ; virtualized PC
570	   (debug          3);
571	   (iab            4)
572	   (lc             5);loop counter            Not impemented
573	   (ls             6);loop start address      Not impemented
574	   (le             7);loop end address        Not impemented
575	   (iret           8)
576	   (imask          9)
577	   (ilat           10)
578	   (ilatst         11)
579	   (ilatcl         12)
580	   (ipend          13)
581	   (ctimer0        14)
582	   (ctimer1        15)
583	   (hstatus        16)
584	   )
585  )
586;; DMA registers in group MR0=1, MR1=0
587
588(define-keyword
589  (name crdma-names)
590  (print-name h-coredma-registers)
591  (prefix "")
592  (values
593
594
595   (dma0config     0)
596   (dma0stride     1)
597   (dma0count      2)
598
599   (dma0srcaddr    3)
600   (dma0dstaddr    4)
601
602   (dma0auto0      5)
603   (dma0auto1      6)
604
605   (dma0status     7)
606
607   (dma1config     8)
608   (dma1stride     9)
609   (dma1count      10)
610
611   (dma1srcaddr    11)
612   (dma1dstaddr    12)
613
614   (dma1auto0      13)
615   (dma1auto1      14)
616
617   (dma1status     15)
618
619   )
620  )
621;; mem configuration registers in group MR0=0, MR1=1
622
623(define-keyword
624  (name crmem-names)
625  (print-name h-coremem-registers)
626  (prefix "")
627  (values
628   (memconfig     0)
629   (memstatus     1)
630   (memprotect    2)
631   (memreserve    3)
632   )
633  )
634
635;; mesh configuration registers in group MR0=1, MR1=1
636
637(define-keyword
638  (name crmesh-names)
639  (print-name h-coremesh-registers)
640  (prefix "")
641
642  (values
643
644
645   (meshconfig    0)
646   (coreid    1)
647   (meshmulticast 2)
648   (swreset   3)
649   )
650  )
651
652
653
654
655;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
656					; PC is a byte-addressed register
657;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
658
659(dnh h-pc "program counter" (PC PROFILE) (pc) () () ())
660
661;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
662					; Memory Effective Address wants to be visible
663;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
664
665(dnh h-memaddr "memory effective address" (PROFILE) (register SI) () () ())
666(dnop memaddr "memory effective address" (SEM-ONLY) h-memaddr f-nil)
667
668;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
669					; Special Core Registers
670;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
671;; STATUS
672;; [0]=core active indicator
673;; [1]=global interrupt disable
674;; [2]=processor mode(1=user mode, 0=kernel mode)
675;; [3]=wired AND global flag
676
677;; [4]=integer zero                        zbit
678;; [5]=integer negative                    nbit
679;; [6]=integer carry                       cbit
680;; [7]=integer overflow                    vbit
681
682;; [8]=fpu zero flag                       bzbit
683;; [9]=fpu negative flag                   bnbit
684;; [10]=fpu overflow flag                  bvbit
685;; [11]=fpu carry flag(not used)           bcbit
686
687;; [12]=ialu overflow flag(sticky)         vsbit
688;; [13]=fpu invalid flag(sticky)           bisbit
689;; [14]=fpu overflow flag(sticky)          bvsbit
690;; [15]=fpu underflow flag(sticky)         busbit
691
692;; [17:16]=exception cause 00=no exception 01=load-store exception 10=fpu exception 11=unimplemented instruction
693;;                                         expcause1bit
694;;                                         expcause0bit
695
696;; [18]=external load stalled              expcause2bit
697;; [19]=external fetch stalled             extFstallbit
698
699;; [31:20]=RESERVED
700
701
702
703
704
705(define-hardware
706  (name h-core-registers)
707  (comment "Special Core Registers")
708  (type register USI (17))
709  (attrs)
710  (indices extern-keyword cr-names)
711  (get (index)
712       (cond USI
713	 ((eq index (const 1)) ; STATUS reg ?
714	  (or (or (or (or (sll USI kmbit (const 2))
715			  (sll USI gidisablebit (const 1)))
716		      (or (or (sll USI expcause1bit (const 17))
717			      (sll USI expcause0bit (const 16)))
718			  (or (sll USI expcause2bit (const 18))
719			      (sll USI extFstallbit (const 19)))))
720		  (or (or (or (sll USI busbit (const 15))
721			      (sll USI bisbit (const 13)))
722			  (or (sll USI bvsbit (const 14))
723			      (sll USI vsbit (const 12))))
724		      (or (or (sll USI bvbit (const 10))
725			      (sll USI bcbit (const 11)))
726			  (or (sll USI bnbit (const 9))
727			      (sll USI bzbit (const 8))))))
728	      (or (or (or (sll USI vbit (const 7))
729			  (sll USI cbit (const 6)))
730		      (or (sll USI nbit (const 5))
731			  (sll USI zbit (const 4))))
732		  (or (sll USI sflagbit (const 3))
733		      (sll USI (const 1) (const 0)))))) ;caibit
734	 ((eq index (const 0)) ; Config reg ?
735	  (or (or (or (or (or (or (sll USI timer0bit2 (const 6))
736				  (sll USI timer0bit3 (const 7)))
737			      (or (or (sll USI coreCfgResBit28 (const 28))
738				      (sll USI coreCfgResBit29 (const 29)))
739				  (or (sll USI coreCfgResBit30 (const 30))
740				      (sll USI coreCfgResBit31 (const 31)))))
741			  (or (or (sll USI coreCfgResBit24 (const 24))
742				  (sll USI coreCfgResBit25 (const 25)))
743			      (or (sll USI coreCfgResBit26 (const 26))
744				  (sll USI coreCfgResBit27 (const 27)))))
745		      (or (or (sll USI timer0bit0 (const 4))
746			      (sll USI timer0bit1 (const 5)))
747			  (or (sll USI coreCfgResBit14 (const 14))
748			      (sll USI coreCfgResBit15 (const 15)))))
749		  (or (or (or (or (sll USI timer1bit2 (const 10))
750				  (sll USI timer1bit3 (const 11)))
751			      (or (sll USI coreCfgResBit12 (const 12))
752				  (sll USI coreCfgResBit13 (const 13))))
753			  (or (sll USI clockGateEnbit (const 22))
754			      (sll USI mbkptEnbit (const 23))))
755		      (or (or (sll USI timer1bit0 (const 8))
756			      (sll USI timer1bit1 (const 9)))
757			  (or (sll USI coreCfgResBit20 (const 20))
758			      (sll USI coreCfgResBit21 (const 21))))))
759	      (or (or (sll USI invExcEnbit (const 1))
760		      (sll USI ovfExcEnbit (const 2)))
761		  (or (or (sll USI trmbit (const 0))
762			  (sll USI unExcEnbit (const 3)))
763		      (or (or (sll USI arithmetic-modebit0 (const 17))
764			      (sll USI arithmetic-modebit1 (const 18)))
765			  (or (sll USI arithmetic-modebit2 (const 19))
766			      (sll USI coreCfgResBit16 (const 16)))))))) ;config reg
767
768	 ((eq index (const 2)) (raw-reg USI h-pc)) ;PC reg
769
770	 (else (raw-reg USI h-core-registers index))))
771
772  (set (index val)
773       (cond VOID
774	 ((eq index (const 0)) ; CONFIG reg
775	  (sequence ()
776	    (set trmbit      (and (const 1) (srl val (const 0))))
777	    (set invExcEnbit (and (const 1) (srl val (const 1))))
778	    (set ovfExcEnbit (and (const 1) (srl val (const 2))))
779	    (set unExcEnbit  (and (const 1) (srl val (const 3))))
780	    (set timer0bit0  (and (const 1) (srl val (const 4))))
781	    (set timer0bit1  (and (const 1) (srl val (const 5))))
782	    (set timer0bit2  (and (const 1) (srl val (const 6))))
783	    (set timer0bit3  (and (const 1) (srl val (const 7))))
784	    (set timer1bit0  (and (const 1) (srl val (const 8))))
785	    (set timer1bit1  (and (const 1) (srl val (const 9))))
786	    (set timer1bit2  (and (const 1) (srl val (const 10))))
787	    (set timer1bit3  (and (const 1) (srl val (const 11))))
788
789	    (set coreCfgResBit12 (and (const 1) (srl val (const 12))))
790	    (set coreCfgResBit13 (and (const 1) (srl val (const 13))))
791	    (set coreCfgResBit14 (and (const 1) (srl val (const 14))))
792	    (set coreCfgResBit15 (and (const 1) (srl val (const 15))))
793	    (set coreCfgResBit16 (and (const 1) (srl val (const 16))))
794
795	    (set arithmetic-modebit0 (and (const 1) (srl val (const 17))))
796	    (set arithmetic-modebit1 (and (const 1) (srl val (const 18))))
797	    (set arithmetic-modebit2 (and (const 1) (srl val (const 19))))
798
799	    (set coreCfgResBit20 (and (const 1) (srl val (const 20))))
800	    (set coreCfgResBit21 (and (const 1) (srl val (const 21))))
801
802	    (set clockGateEnbit  (and (const 1) (srl val (const 22))))
803	    (set mbkptEnbit      (and (const 1) (srl val (const 23))))
804
805	    (set coreCfgResBit24 (and (const 1) (srl val (const 24))))
806	    (set coreCfgResBit25 (and (const 1) (srl val (const 25))))
807	    (set coreCfgResBit26 (and (const 1) (srl val (const 26))))
808	    (set coreCfgResBit27 (and (const 1) (srl val (const 27))))
809	    (set coreCfgResBit28 (and (const 1) (srl val (const 28))))
810	    (set coreCfgResBit29 (and (const 1) (srl val (const 29))))
811	    (set coreCfgResBit30 (and (const 1) (srl val (const 30))))
812	    (set coreCfgResBit31 (and (const 1) (srl val (const 31))))
813
814	    (set (raw-reg USI h-core-registers index) val)
815	    ;; check LSB of CONFIG for rounding mode
816	    (c-call "epiphany_set_rounding_mode" val)
817	  )
818	 )
819	 ((eq index (const 1))	;STATUS reg ; TODO check which bits can be set or clear
820	  (sequence ((USI newval))
821	    (set newval (and val (const #xfff2)))
822	    (set extFstallbit  (and (const 1) (srl newval (const 19))))
823	    (set expcause2bit  (and (const 1) (srl newval (const 18))))
824	    (set expcause1bit  (and (const 1) (srl newval (const 17))))
825	    (set expcause0bit  (and (const 1) (srl newval (const 16))))
826	    (set busbit (and (const 1) (srl newval (const 15))))
827	    (set bisbit (and (const 1) (srl newval (const 13))))
828	    (set bvsbit (and (const 1) (srl newval (const 14))))
829	    (set vsbit  (and (const 1) (srl newval (const 12))))
830	    (set bvbit  (and (const 1) (srl newval (const 10))))
831	    (set bcbit  (and (const 1) (srl newval (const 11))))
832	    (set bnbit  (and (const 1) (srl newval (const 9))))
833	    (set bzbit  (and (const 1) (srl newval (const 8))))
834	    (set vbit   (and (const 1) (srl newval (const 7))))
835	    (set cbit   (and (const 1) (srl newval (const 6))))
836	    (set nbit   (and (const 1) (srl newval (const 5))))
837	    (set zbit   (and (const 1) (srl newval (const 4))))
838	    (set sflagbit (and (const 1) (srl newval (const 3))))
839	    (set kmbit  (and (const 1) (srl newval (const 2))))
840	    ;;(set gie    (and (const 1) (srl newval (const 1))))
841	    (set (raw-reg SI h-core-registers (const 1)) newval)
842	   ))
843	 ;; causes simulator errors
844	 ;;	     ((eq index (const 2))	;PC reg
845	 ;;	      (set pc val))
846
847	 (else (set (raw-reg USI h-core-registers index) val))
848       ))
849)
850					; (define-pmacro (hcr-config) (reg h-core-registers 0)) etc.
851(.splice begin (.unsplice (.map
852			   (.pmacro (xname xnum)
853				    (define-pmacro ((.sym hcr- xname)) (reg h-core-registers xnum)))
854
855			   (
856			    config
857			    status
858			    pc
859			    debug
860			    iab
861			    lc
862			    ls
863			    le
864			    iret
865			    imask
866			    ilat
867			    ilatst
868			    ilatcl
869			    ipend
870			    ctimer0
871			    ctimer1
872			    hstatus
873
874
875
876			    )
877
878			   (0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
879			      )
880			   )))
881
882
883
884;; DMA registers in MMR space
885(define-hardware
886  (name h-coredma-registers)
887  (comment "DMA registers in MMR space")
888  (type register USI (16))
889  (attrs)
890  (indices extern-keyword crdma-names)
891  )
892
893;; MEM registers in MMR space
894(define-hardware
895  (name h-coremem-registers)
896  (comment "MEM registers in MMR space")
897  (type register USI (4))
898  (attrs)
899  (indices extern-keyword crmem-names)
900  )
901
902;; MEM registers in MMR space
903(define-hardware
904  (name h-coremesh-registers)
905  (comment "MESH registers in MMR space")
906  (type register USI (4))
907  (attrs)
908  (indices extern-keyword crmesh-names)
909  )
910
911
912
913					; Operands
914
915					; Branch displacements
916(define-operand
917  (name simm24)
918  (comment "branch address pc-relative")
919  (attrs RELAX)
920  (type h-iaddr)
921  (index f-simm24)
922  (handlers (parse "branch_addr")))
923
924(define-operand
925  (name simm8)
926  (comment "branch address pc-relative")
927  (attrs RELAX)
928  (type h-iaddr)
929  (index f-simm8)
930  (handlers (parse "branch_addr")))
931
932
933;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
934					; Register operands
935;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
936
937(define-pmacro (short-regs nm group hw cmt)
938  (define-operand
939    (name nm)
940    (comment cmt)
941    (attrs)
942    (type hw)
943    (index (.sym "f-r" group))
944    (handlers (parse "shortregs") (print "keyword"))
945    )
946  )
947
948(define-pmacro (short-regs-core nm group hw cmt)
949  (define-operand
950    (name nm)
951    (comment cmt)
952    (attrs)
953    (type hw)
954    (index (.sym "f-s" group))
955    (handlers (parse "shortregs") (print "keyword"))
956    )
957  )
958
959
960					; short regs (0-7)
961(short-regs rd d h-registers "destination register")
962(short-regs rn n h-registers "source register")
963(short-regs rm m h-registers "source register")
964
965(short-regs frd d h-fpregisters "fp destination register")
966(short-regs frn n h-fpregisters "fp source register")
967(short-regs frm m h-fpregisters "fp source register")
968
969					; long regs (0-63)
970(dnop rd6 "destination register" () h-registers f-rd6)
971(dnop rn6 "source register"      () h-registers f-rn6)
972(dnop rm6 "source register"      () h-registers f-rm6)
973
974(dnop frd6 "fp destination register" () h-fpregisters f-rd6)
975(dnop frn6 "fp source register"      () h-fpregisters f-rn6)
976(dnop frm6 "fp source register"      () h-fpregisters f-rm6)
977
978					; special regs (0-7)
979(short-regs-core sd d h-core-registers "special destination")
980(short-regs-core sn n h-core-registers "special source")
981
982					; special regs (long form)
983(dnop sd6 "special destination register" () h-core-registers f-sd6)
984(dnop sn6 "special source register"      () h-core-registers f-sn6)
985
986(dnop sddma "dma register" () h-coredma-registers f-sd6)
987(dnop sndma "dma register"      () h-coredma-registers f-sn6)
988(dnop sdmem "mem register" () h-coremem-registers f-sd6)
989(dnop snmem "mem register"      () h-coremem-registers f-sn6)
990(dnop sdmesh "mesh register" () h-coremesh-registers f-sd6)
991(dnop snmesh "mesh register"      () h-coremesh-registers f-sn6)
992
993					; Immediate literals - but don't allow register names!
994(define-pmacro (dimmop nm cmt hwtype idx)
995  (define-operand (name nm) (comment cmt) (type hwtype) (index idx)
996    (attrs RELAX)
997    (handlers (parse "simm_not_reg")
998	      (print "simm_not_reg")))
999  )
1000
1001(dimmop simm3   "signed 3-bit literal"    h-sint f-sdisp3)
1002(dimmop simm11  "signed 11-bit literal"   h-sint f-sdisp11)
1003(dnop disp3  "short data displacement"   () h-uint f-disp3)
1004(dnop trapnum6 "parameter for swi or trap" () h-uint f-trap-num)
1005
1006(define-pmacro (duimmop nm cmt hwtype idx)
1007  (define-operand (name nm) (comment cmt) (type hwtype) (index idx)
1008    (attrs)
1009    (handlers (parse "uimm_not_reg")
1010	      (print "uimm_not_reg")))
1011  )
1012
1013(duimmop swi_num "unsigned 6-bit swi#" h-uint f-trap-num)
1014(duimmop disp11 "sign-magnitude data displacement" h-uint f-disp11)
1015
1016(dnop shift   "immediate shift amount"   () h-uint f-shift)
1017
1018(define-operand (name imm16) (comment "16-bit unsigned literal") (attrs RELAX)
1019  (type h-addr) (index f-imm16) (handlers (parse "imm16")))
1020(define-operand (name imm8) (comment "8-bit unsigned literal") (attrs RELAX)
1021  (type h-addr) (index f-imm8) (handlers (parse "imm8")))
1022
1023(define-operand
1024  (name direction)
1025  (comment "+/- indexing")
1026  (attrs)
1027  (type h-uint)
1028  (index f-addsubx)
1029  (handlers (parse "postindex")
1030	    (print "postindex")))
1031
1032(define-operand
1033  (name dpmi)
1034  (comment "+/- magnitude immediate displacement")
1035  (attrs)
1036  (type h-uint)
1037  (index f-subd)
1038  (handlers (parse "postindex")
1039	    (print "postindex")))
1040
1041
1042
1043;; call exception macro - no check for imask
1044(define-pmacro (call-exception vaddr bit-in-ilat)
1045  (if (eq gidisablebit 0)
1046      (if (eq (and (hcr-imask) bit-in-ilat) 0)
1047	  (sequence ()
1048		    (set kmbit 1)
1049		    (set gidisablebit 1)
1050		    (set (hcr-iret) (add pc (const 2)))
1051		    (set (hcr-ipend) (or (hcr-ipend) (const bit-in-ilat)))
1052		    (set pc (const vaddr))
1053
1054		    )
1055	  ;; schedule interrupt
1056	  (set (hcr-ilat) (or (hcr-ilat) (const  bit-in-ilat)))
1057	  )
1058      )
1059  )
1060
1061
1062;;      (lc             5);loop counter            Not impemented
1063;;       (ls             6);loop start address      Not impemented
1064;;       (le             7);loop end address        Not impemented
1065
1066;;have callback to adjust pc in case od events ( HW loops ... )
1067(define-pmacro (dni_wrapper isnid stdrdesc attr_ strassembl iopcode proceed null_b)
1068  (begin
1069    (dni isnid stdrdesc attr_ strassembl iopcode
1070	 (sequence () proceed
1071		   (sequence ((USI tmpPC))
1072			     ;;(set tmpPC  (c-call  USI "epiphany_post_isn_callback" pc))
1073
1074			     (if (eq pc (hcr-le))
1075				 (set (hcr-lc) (sub (hcr-lc) #x1)))
1076			     (if (and
1077				   (eq pc (hcr-le))
1078				   (not (eq (hcr-lc) #x0)))
1079				 (set pc (hcr-ls)))
1080			     )
1081		   )
1082	 null_b)
1083    )
1084  )
1085
1086
1087
1088
1089
1090;; Some handy macros
1091;;
1092
1093;; define instructions
1094;;   Short (16 bit forms) must appear first so that instruction
1095;;   selection can reject them and match long forms when registers
1096;;   or immediates exceed the values in the 16 bit instructions
1097
1098
1099;; B<COND> SIMM8
1100;; B<COND> SIMM24
1101
1102(define-pmacro (br-insn name cond g-op)
1103  (begin
1104					; the 16-bit versions of branch
1105    (dni (.sym "b" name "16")
1106	 (.str "Conditional Branch - 16 bit" name)
1107	 (COND-CTI SHORT-INSN)
1108	 (.str "b" name ".s $simm8")
1109	 (+ OP4_BRANCH16 (.sym "OPC_" cond) simm8)
1110	 (if (g-op)
1111	     (set pc simm8)
1112	     )
1113	 ()
1114	 )
1115
1116    (dnmi (.sym "b" name "16r") "relaxable conditional branch"
1117	  (COND-CTI RELAXABLE)
1118	  (.str "b" name " $simm8")
1119	  (emit (.sym "b" name "16") simm8)
1120	  )
1121
1122    (dni (.sym "b" name)
1123	 (.str "Conditional Branch " name)
1124	 (COND-CTI)
1125	 (.str "b" name ".l $simm24")
1126	 (+ OP4_BRANCH (.sym "OPC_" cond) simm24)
1127	 (if (g-op)
1128	     (set pc simm24)
1129	     )
1130	 ()
1131	 )
1132
1133    (dnmi (.sym "b" name "32r") "relaxable conditional branch"
1134	  (COND-CTI RELAXED)
1135	  (.str "b" name " $simm24")
1136	  (emit (.sym "b" name) simm24)
1137	  )
1138    )
1139  )
1140
1141
1142					; basic conditional branches for integer arithmetic
1143(br-insn "eq"	 EQ	(.pmacro () (eq zbit #x1)))
1144(br-insn "ne"	 NE	(.pmacro () (eq zbit #x0)))
1145(br-insn "gtu"   GTU	(.pmacro () (and BI cbit (not BI zbit))))
1146(br-insn "gteu"  GTEU	(.pmacro () (eq cbit #x1)))
1147(br-insn "lteu"  LTEU	(.pmacro () (or BI (not BI cbit) zbit)))
1148(br-insn "ltu"   LTU	(.pmacro () (eq cbit #x0)))
1149(br-insn "gt"	 GT	(.pmacro () (and BI (not BI zbit) (eq vbit nbit))))
1150(br-insn "gte"   GTE	(.pmacro () (eq vbit nbit)))
1151(br-insn "lt"	 LT	(.pmacro () (xor BI vbit nbit)))
1152(br-insn "lte"   LTE	(.pmacro () (or BI zbit (xor vbit nbit))))
1153
1154
1155					; floating point condition codes (floating point instructions)
1156(br-insn "beq"   BEQ    (.pmacro () (or BI bzbit bzbit)))
1157(br-insn "bne"   BNE    (.pmacro () (not BI bzbit)))
1158(br-insn "blt"   BLT    (.pmacro () (and BI bnbit (not bzbit))))
1159(br-insn "blte"  BLTE   (.pmacro () (or BI bnbit bzbit)))
1160
1161					; unconditional branches
1162(dni b16 "short unconditional branch" (UNCOND-CTI SHORT-INSN)
1163     "b.s $simm8"
1164     (+ OP4_BRANCH16 OPC_B simm8)
1165     (set pc simm8)
1166     ()
1167     )
1168
1169(dnmi b16r "relaxable b16"
1170      (UNCOND-CTI RELAXABLE)
1171      "b $simm8"
1172      (emit b16 simm8)
1173      )
1174
1175(dni b "long unconditional branch" (UNCOND-CTI)
1176     "b.l $simm24"
1177     (+ OP4_BRANCH OPC_B simm24)
1178     (set pc simm24)
1179     ()
1180     )
1181
1182(dnmi b32r "relaxable b"
1183      (UNCOND-CTI RELAXED)
1184      "b $simm24"
1185      (emit b simm24))
1186
1187;; BL R,ADDR
1188
1189(dni bl16 "branch and link"
1190     (UNCOND-CTI SHORT-INSN)
1191     ("bl.s $simm8")
1192     (+ OP4_BRANCH16 OPC_BL simm8)
1193     (sequence ()
1194	       (set (reg h-registers 14) (add pc (const 2)))
1195	       (set pc simm8))
1196     ()
1197     )
1198
1199(dnmi bl16r "bl16 relaxable"
1200      (UNCOND-CTI RELAXABLE)
1201      "bl $simm8"
1202      (emit bl16 simm8))
1203
1204(dni bl "branch and link"
1205     (UNCOND-CTI)
1206     ("bl.l $simm24")
1207     (+ OP4_BRANCH OPC_BL simm24)
1208     (sequence ()
1209	       (set (reg h-registers 14) (add pc (const 4)))
1210	       (set pc simm24))
1211     ()
1212     )
1213
1214(dnmi blr "bl relaxable"
1215      (UNCOND-CTI RELAXED)
1216      "bl $simm24"
1217      (emit bl simm24))
1218
1219;; JUMP <RN>
1220(dni jr16 "unconditional jump 16"
1221     (UNCOND-CTI SHORT-INSN)
1222     ("jr $rn")
1223     (+ OP4_FLOW16 (f-opc-8-5 #x14) (f-dc-15-3 #x0) (f-dc-9-1 #x0) rn)
1224     (set pc rn)
1225     ()
1226     )
1227
1228;; RTS / JR
1229;; ??? Putting a constant into a multi-ifield does not work -
1230;; the constant gets inserted in full into each part.
1231					;(dnmi rts "return from subroutine"
1232					;     (UNCOND-CTI)
1233					;     ("rts")
1234					;     (emit jr (rn6 14)) ; jr lr  / jr r14
1235					;)
1236;; RTS / JR
1237(dni rts "return from subroutine"
1238     (ALIAS UNCOND-CTI)
1239     ("rts")
1240     (+ OP4_MISC (f-opc-8-5 #x14) (f-opc-19-4 #x2) (f-rn 6) (f-rn-x 1)
1241	(f-dc-9-1 #x0)
1242	(f-dc-15-3 #x0)
1243	(f-dc-25-6 #x0)
1244	(f-dc-31-3 #x0)
1245	)
1246     (set pc (reg h-registers 14))
1247     ()
1248     )
1249
1250(dni jr "unconditional jump"
1251     (UNCOND-CTI)
1252     ("jr $rn6")
1253     (+ OP4_MISC (f-opc-8-5 #x14) (f-opc-19-4 #x2) rn6
1254	(f-dc-9-1 #x0)
1255	(f-dc-15-3 #x0)
1256	(f-dc-25-6 #x0)
1257	(f-dc-31-3 #x0)
1258	)
1259     (set pc rn6)
1260     ()
1261     )
1262
1263
1264;; JALR <RN>
1265(dni jalr16 "jump and link register"
1266     (UNCOND-CTI SHORT-INSN)
1267     ("jalr $rn")
1268     (+ OP4_FLOW16  (f-opc-8-5 #x15) (f-dc-15-3 #x0) (f-dc-9-1 #x0)  rn)
1269     (sequence ()
1270	       (set (reg h-registers 14) (add pc (const 2)))
1271	       (set pc rn)
1272	       )
1273     ()
1274     )
1275
1276(dni jalr "jump and link register"
1277     (UNCOND-CTI)
1278     ("jalr $rn6")
1279     (+ OP4_MISC
1280	(f-opc-8-5 #x15)
1281	(f-opc-19-4 #x2)
1282	rn6
1283	(f-dc-9-1 #x0)
1284	(f-dc-15-3 #x0)
1285	(f-dc-25-6 #x0)
1286	(f-dc-31-3 #x0)
1287
1288	)
1289     (sequence ()
1290	       (set (reg h-registers 14) (add pc (const 4)))
1291	       (set pc rn6))
1292     ()
1293     )
1294
1295
1296;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1297					;  Load/Store Memory Instructions
1298;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1299
1300
1301(define-pmacro (callMisaligmentExceptionIfNeeded sel  addr isAligmentAccess)
1302  (sequence ((BI scale))
1303    (set isAligmentAccess
1304	 (case BI sel
1305	   ((OPW_BYTE)	(eq (and addr #x0) #x0))
1306	   ((OPW_SHORT)	(eq (and addr #x1) #x0))
1307	   ((OPW_WORD)	(eq (and addr #x3) #x0))
1308	   (else	(eq (and addr #x7) #x0))))
1309    (if (not BI isAligmentAccess)
1310	(call-exception #x4 #x2))
1311  )
1312)
1313
1314
1315
1316;; helper to convert size selector OPW_<mode> into a literal scale factor
1317(define-pmacro (ConvertSelectorToShift sel scale)
1318  (set scale
1319       (case SI sel
1320	 ((OPW_BYTE)	(const 0))
1321	 ((OPW_SHORT)	(const 1))
1322	 ((OPW_WORD)	(const 2))
1323	 (else	(const 3))))
1324)
1325
1326;; common load macros from effective address, handling 8/16/32/64 bits
1327(define-pmacro (load-double-from-ea regnum eff-addr mode sel)
1328  (sequence ((SI loadaddr) (BI isAligmentAccess))
1329	    (set loadaddr eff-addr)
1330	    (callMisaligmentExceptionIfNeeded sel  loadaddr isAligmentAccess)
1331
1332	    (if (not (not BI isAligmentAccess))
1333		(sequence ()
1334			  (set memaddr loadaddr)
1335			  (set regnum (mem SI loadaddr))
1336			  (set loadaddr (add loadaddr (const 4)))
1337			  (set memaddr loadaddr)
1338			  (set (reg h-registers
1339				    (add (index-of regnum)
1340					 (const 1)))
1341			       (mem SI loadaddr))
1342
1343			  )
1344		)
1345	    )
1346  )
1347
1348(define-pmacro (load-from-ea regnum eff-addr mode sel)
1349  (sequence ((BI isAligmentAccess))
1350
1351	    (callMisaligmentExceptionIfNeeded sel eff-addr   isAligmentAccess)
1352	    (if (not (not BI isAligmentAccess))
1353		(sequence ()
1354			  (set memaddr eff-addr)
1355			  (set regnum (zext SI (mem mode eff-addr)))
1356			  )
1357		)
1358	    )
1359  ) ;; 8/16/32 bit cases
1360
1361
1362;; common store to effective address, handling 8/16/32/64 bit data
1363(define-pmacro (store-double-to-ea eff-addr regnum mode sel)
1364  (sequence ((SI storeaddr) (BI isAligmentAccess))
1365	    (set storeaddr eff-addr)
1366	    (callMisaligmentExceptionIfNeeded sel storeaddr isAligmentAccess)
1367	    (if (not (not BI isAligmentAccess))
1368		(sequence ()
1369			  (set memaddr storeaddr)
1370			  (set (mem SI storeaddr) regnum)
1371			  (set storeaddr (add storeaddr (const 4)))
1372			  (set memaddr storeaddr)
1373			  (set (mem SI storeaddr)
1374			       (reg h-registers (add (index-of regnum) (const 1))))
1375			  )
1376		)
1377	    )
1378  )
1379
1380(define-pmacro (store-to-ea eff-addr regnum mode sel)
1381  (sequence ((BI isAligmentAccess))
1382	    (callMisaligmentExceptionIfNeeded sel eff-addr   isAligmentAccess)
1383	    (if (not (not BI isAligmentAccess))
1384		(sequence ()
1385			  (set memaddr eff-addr)
1386			  (set (mem mode eff-addr) regnum)
1387			  )
1388		)
1389	    )
1390  )	;8/16/32 bit cases
1391
1392
1393(define-pmacro (load-insn name mode sel sem-op)
1394  (begin
1395    (dni_wrapper (.sym name "x16.s")
1396		 (.str "load " mode " indexed")
1397		 (SHORT-INSN)
1398		 (.str name " $rd,[$rn,$rm]")
1399		 (+ OP4_LDSTR16X sel OP_LOAD rd rn rm)
1400		 (sequence ()
1401			   (sem-op rd (add rn rm) mode sel))
1402		 ()
1403		 )
1404
1405
1406    (dni_wrapper (.sym name "p16.s")
1407		 (.str "load " mode " postmodify")
1408		 (SHORT-INSN)
1409		 (.str name " $rd,[$rn],$rm")
1410		 (+ OP4_LDSTR16P sel OP_LOAD rd rn rm)
1411		 (sequence ((SI tmprm))
1412			   (set tmprm rm)
1413			   (sem-op rd rn mode sel)
1414			   (set rn (add rn tmprm)))
1415		 ()
1416		 )
1417
1418
1419    (dni_wrapper (.sym name "x.l")
1420		 (.str "load " mode " indexed")
1421		 ()
1422		 (.str name " $rd6,[$rn6,$direction$rm6]")
1423		 (+ OP4_LDSTRX sel OP_LOAD (f-opc-19-4 #x0) (f-dc-22-1 #x0) (f-dc-21-1 #x0) rd6 rn6 direction rm6)
1424		 (sequence ()
1425			   (if (ifield f-addsubx)
1426			       (sem-op rd6 (sub rn6 rm6) mode sel)
1427			       (sem-op rd6 (add rn6 rm6) mode sel)))
1428		 ()
1429		 )
1430
1431    (dnmi (.sym name "x")
1432	  (.str "load " mode " indexed")
1433	  (NO-DIS)
1434	  (.str name ".l $rd6,[$rn6,$direction$rm6]")
1435	  (emit  (.sym name "x.l") rd6 rn6 direction rm6)
1436	  )
1437
1438
1439
1440    (dni_wrapper (.sym name "p.l")
1441		 (.str "load " mode " postmodify")
1442		 ()
1443		 (.str name " $rd6,[$rn6],$direction$rm6")
1444		 (+ OP4_LDSTRP sel OP_LOAD (f-opc-19-4 #x0) (f-dc-22-2 #x0) rd6 rn6 direction rm6)
1445		 (sequence ((SI tmprm))
1446			   (set tmprm rm6)
1447			   (sem-op rd6 rn6 mode sel)
1448			   (if (ifield f-addsubx)
1449			       (set rn6 (sub rn6 tmprm))
1450			       (set rn6 (add rn6 tmprm)))
1451			   )
1452		 ()
1453		 )
1454
1455
1456    (dnmi (.sym name "p")
1457	  (.str "load " mode " postmodify")
1458	  (NO-DIS)
1459	  (.str name ".l $rd6,[$rn6],$direction$rm6")
1460	  (emit  (.sym name "p.l") rd6 rn6 direction rm6)
1461	  )
1462
1463
1464    ;;immediate modes last so reg forms found first.
1465    (dni_wrapper (.sym name "d16.s")
1466		 (.str "load " mode " displacement")
1467		 (SHORT-INSN IMM3)
1468		 (.str name " $rd,[$rn,$disp3]")
1469		 (+ OP4_LDSTR16D sel OP_LOAD rd rn disp3) ;; convert size to 'B'
1470		 (sequence ((SI effa)
1471			    (SI scale))
1472			   (ConvertSelectorToShift sel scale)
1473			   (set effa (add rn (sll disp3 scale)))
1474			   (sem-op rd effa mode sel)
1475			   )
1476		 ()
1477		 )
1478
1479
1480    (dni_wrapper (.sym name "d.l")
1481		 (.str "load " mode " displacement")
1482		 ()
1483		 (.str name " $rd6,[$rn6,$dpmi$disp11]")
1484		 (+ OP4_LDSTRD sel OP_LOAD PMOD_DISP rd6 rn6 dpmi disp11)
1485		 (sequence ((SI effa)
1486			    (SI scale))
1487			   (ConvertSelectorToShift sel scale)
1488			   (if dpmi
1489			       (set effa (sub rn6 (sll disp11 scale)))
1490			       (set effa (add rn6 (sll disp11 scale)))
1491			       )
1492			   (sem-op rd6 effa mode sel)
1493			   )
1494		 ()
1495		 )
1496
1497    (dnmi (.sym name "d")
1498	  (.str "load " mode " displacement")
1499	  (NO-DIS)
1500	  (.str name ".l $rd6,[$rn6,$dpmi$disp11]")
1501	  (emit  (.sym name "d.l") rd6 rn6  dpmi disp11)
1502	  )
1503
1504
1505
1506    (dni_wrapper (.sym name "dpm.l")
1507		 (.str "load " mode " displacement post-modify")
1508		 ()
1509		 (.str name " $rd6,[$rn6],$dpmi$disp11")
1510		 (+ OP4_LDSTRD sel OP_LOAD PMOD_POST rd6 rn6 dpmi disp11)
1511		 (sequence ((SI scale))
1512			   (ConvertSelectorToShift sel scale)
1513			   (sem-op rd6 rn6 mode sel)
1514			   (if dpmi
1515			       (set rn6 (sub rn6 (sll disp11 scale)))
1516			       (set rn6 (add rn6 (sll disp11 scale)))
1517			       )
1518			   )
1519		 ()
1520		 )
1521
1522    (dnmi (.sym name "dpm")
1523	  (.str "load " mode " displacement post-modify")
1524	  (NO-DIS)
1525	  (.str name ".l $rd6,[$rn6],$dpmi$disp11")
1526	  (emit  (.sym name "dpm.l") rd6 rn6  dpmi disp11)
1527	  )
1528
1529
1530    ;; ;; macro form with a zero displacement
1531    (dnmi (.sym name "ds0") "load with 0 disp"
1532	  (SHORT-INSN IMM3)
1533	  (.str name " $rd,[$rn]")
1534	  (emit (.sym name "d16.s") rd rn (disp3 0))
1535	  )
1536    (dnmi (.sym name "dl0") "load with 0 disp"
1537    	  (NO-DIS)
1538	  (.str name " $rd6,[$rn6]")
1539	  (emit (.sym name "d.l") rd6 rn6 (dpmi 0) (disp11 0))
1540	  )
1541    (dnmi (.sym name "dl0.l") "load with 0 disp"
1542    	  (NO-DIS)
1543	  (.str name ".l $rd6,[$rn6]")
1544	  (emit (.sym name "d.l") rd6 rn6 (dpmi 0) (disp11 0))
1545	  )
1546
1547
1548    )
1549  )
1550
1551(load-insn ldrb QI OPW_BYTE load-from-ea)
1552(load-insn ldrh HI OPW_SHORT load-from-ea)
1553(load-insn ldr  SI OPW_WORD  load-from-ea)
1554(load-insn ldrd DI OPW_DOUBLE load-double-from-ea)
1555
1556
1557
1558
1559;; TMP = MEM[RD+RM];    /* Copy content of memory to tmp.  */
1560;; if (~TMP)            /* Check if memory location is zero.  */
1561;;   MEM[RD+RM] = RD;   /* If zero, write RD to memory.  */
1562;; RD = TMP;            /* Always write tmp into RD (NOTE it's destructive).  */
1563
1564
1565(define-pmacro (testset-insn name mode sel)
1566  (begin
1567
1568
1569    (dni_wrapper (.sym name "t")
1570		 (.str "testset " mode " indexed")
1571		 ()
1572		 (.str name " $rd6,[$rn6,$direction$rm6]")
1573		 (+ OP4_LDSTRX sel OP_LOAD (f-opc-19-4 #x0) (f-dc-22-1 #x0) (f-dc-21-1 #x1)
1574		    rd6 rn6 direction rm6)
1575		 (sequence ((SI tmemaddr) (SI tmpValReg))
1576
1577			   ;;back up register
1578			   (set tmpValReg rd6)
1579
1580			   (if (ifield f-addsubx)
1581			       (set  tmemaddr  (sub rn6 rm6))
1582			       (set  tmemaddr  (add rn6 rm6))
1583			       )
1584			   ;;always update rd
1585			   (load-from-ea rd6 tmemaddr  mode sel)
1586			   ;;if zero
1587			   (if  rd6
1588				(nop)
1589				(set (mem mode tmemaddr) tmpValReg)
1590				)
1591
1592			   )
1593		 ()
1594		 )
1595
1596
1597    (dnmi  (.sym name "t.l")
1598	   (.str "testset " mode ".l indexed")
1599	   (NO-DIS)
1600	   (.str name ".l $rd6,[$rn6,$direction$rm6]")
1601	   (emit (.sym name "t") rd6 rn6 direction rm6)
1602	   )
1603
1604
1605    )
1606  )
1607
1608(testset-insn testsetb QI OPW_BYTE)
1609(testset-insn testseth HI OPW_SHORT)
1610(testset-insn testset  SI OPW_WORD)
1611;;no double mode support, since we have to send the src address, data
1612;;(testset-insn testsetd DI OPW_DOUBLE load-double-from-ea)
1613
1614
1615
1616;; need 16 bit forms too
1617(define-pmacro (store-insn name mode sel sem-op)
1618  (begin
1619    (dni_wrapper (.sym name "x16")
1620		 (.str "store" mode " indexed")
1621		 (SHORT-INSN)
1622		 (.str name " $rd,[$rn,$rm]")
1623		 (+ OP4_LDSTR16X sel OP_STORE rd rn rm)
1624		 (sequence ()
1625			   (sem-op (add rn rm) rd mode sel)
1626			   )
1627		 ()
1628		 )
1629
1630    (dni_wrapper (.sym name "x")
1631		 (.str "store" mode " indexed")
1632		 ()
1633		 (.str name " $rd6,[$rn6,$direction$rm6]")
1634		 (+ OP4_LDSTRX sel OP_STORE (f-opc-19-4 #x0)  (f-dc-22-1 #x0) (f-dc-21-1 #x0) rd6 rn6 direction rm6)
1635		 (sequence ()
1636			   (if (ifield f-addsubx)
1637			       (sem-op (sub rn6 rm6) rd6 mode sel)
1638			       (sem-op (add rn6 rm6) rd6 mode sel)
1639			       ))
1640		 ()
1641		 )
1642
1643    (dnmi (.sym name "x.l")
1644	  (.str "store" mode " indexed")
1645	  (NO-DIS)
1646	  (.str name ".l $rd6,[$rn6,$direction$rm6]")
1647	  (emit  (.sym name "x")  rd6 rn6 direction rm6)
1648	  )
1649
1650
1651
1652
1653
1654    (dni_wrapper (.sym name "p16")
1655		 (.str "store " mode " postmodify")
1656		 (SHORT-INSN)
1657		 (.str name " $rd,[$rn],$rm")
1658		 (+ OP4_LDSTR16P sel OP_STORE rd rn rm)
1659		 (sequence ()
1660			   (sem-op rn rd mode sel)
1661			   (set rn (add rn rm))
1662			   )
1663		 ()
1664		 )
1665
1666    (dni_wrapper (.sym name "p")
1667		 (.str "store " mode " postmodify")
1668		 ()
1669		 (.str name " $rd6,[$rn6],$direction$rm6")
1670		 (+ OP4_LDSTRP sel OP_STORE (f-opc-19-4 #x0) (f-dc-22-2 #x0) rd6 rn6 direction rm6)
1671		 (sequence ()
1672			   (sem-op rn6 rd6 mode sel)
1673			   (if (ifield f-addsubx)
1674			       (set rn6	(sub rn6 rm6))
1675			       (set rn6 (add rn6 rm6)))
1676			   )
1677		 ()
1678		 )
1679    (dnmi (.sym name "p.l")
1680	  (.str "store " mode " postmodify")
1681	  (NO-DIS)
1682	  (.str name ".l $rd6,[$rn6],$direction$rm6")
1683	  (emit (.sym name "p") rd6 rn6 direction rm6)
1684	  )
1685
1686    (dni_wrapper (.sym name "d16")
1687		 (.str "store " mode " displacement")
1688		 (SHORT-INSN IMM3)
1689		 (.str name " $rd,[$rn,$disp3]")
1690		 (+ OP4_LDSTR16D sel OP_STORE rd rn disp3) ;; convert size to 'B'
1691		 (sequence ((SI effa)
1692			    (SI scale))
1693			   (ConvertSelectorToShift sel scale)
1694			   (set effa (add rn (sll disp3 scale)))
1695			   (sem-op effa rd mode sel)
1696			   )
1697		 ()
1698		 )
1699
1700    (dni_wrapper (.sym name "d")
1701		 (.str "store " mode " displacement")
1702		 ()
1703		 (.str name " $rd6,[$rn6,$dpmi$disp11]")
1704		 (+ OP4_LDSTRD sel OP_STORE PMOD_DISP rd6 rn6 dpmi disp11)
1705		 (sequence ((SI effa)
1706			    (SI scale))
1707			   (ConvertSelectorToShift sel scale)
1708			   (if dpmi
1709			       (set effa (sub rn6 (sll disp11 scale)))
1710			       (set effa (add rn6 (sll disp11 scale)))
1711			       )
1712			   (sem-op effa rd6 mode sel)
1713			   )
1714		 ()
1715		 )
1716
1717    (dnmi (.sym name "d.l")
1718	  (.str "store " mode " displacement")
1719	  (NO-DIS)
1720	  (.str name ".l $rd6,[$rn6,$dpmi$disp11]")
1721	  (emit (.sym name "d") rd6 rn6 dpmi disp11)
1722	  )
1723
1724
1725    (dni_wrapper (.sym name "dpm")
1726		 (.str "store " mode " displacement post-modify")
1727		 ()
1728		 (.str name " $rd6,[$rn6],$dpmi$disp11")
1729		 (+ OP4_LDSTRD sel OP_STORE PMOD_POST rd6 rn6 dpmi disp11) ;; convert size to 'B'
1730		 (sequence ((SI scale))
1731			   (ConvertSelectorToShift sel scale)
1732			   (sem-op rn6 rd6 mode sel)
1733			   (if dpmi
1734			       (set rn6 (sub rn6 (sll disp11 scale)))
1735			       (set rn6 (add rn6 (sll disp11 scale)))
1736			       )
1737			   )
1738		 ()
1739		 )
1740    (dnmi (.sym name "dpm.l")
1741	  (.str "store " mode " displacement post-modify")
1742	  (NO-DIS)
1743	  (.str name ".l $rd6,[$rn6],$dpmi$disp11")
1744	  (emit (.sym name "dpm") rd6 rn6 dpmi disp11)
1745	  )
1746
1747    ;; macro form with a zero displacement
1748    (dnmi (.sym name "ds0") "store w 0 disp"
1749	  (SHORT-INSN IMM3)
1750	  (.str name " $rd,[$rn]")
1751	  (emit (.sym name "d16") rd rn (disp3 0))
1752	  )
1753
1754    (dnmi (.sym name "dl0")  "store w 0 disp"
1755	  ()
1756	  (.str name " $rd6,[$rn6]")
1757	  (emit (.sym name "d") rd6 rn6 (dpmi 0) (disp11 0))
1758	  )
1759
1760    (dnmi (.sym name "dl0.l")  "store w 0 disp"
1761	  (NO-DIS)
1762	  (.str name ".l $rd6,[$rn6]")
1763	  (emit (.sym name "d") rd6 rn6 (dpmi 0) (disp11 0))
1764	  )
1765
1766
1767
1768    )
1769  )
1770
1771(store-insn strb QI OPW_BYTE store-to-ea)
1772(store-insn strh HI OPW_SHORT store-to-ea)
1773(store-insn str  SI OPW_WORD store-to-ea)
1774(store-insn strd DI OPW_DOUBLE store-double-to-ea)
1775
1776;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1777;; MOV<COND> RD,RN
1778;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1779
1780(define-pmacro (move-insns name cond g-op)
1781  (begin
1782    (dni_wrapper (.sym "cmov16" cond)
1783		 (.str "move register " cond)
1784		 (SHORT-INSN)
1785		 (.str "mov" name " $rd,$rn")
1786		 (+ OP4_FLOW16 (.sym "OPC_" cond) (f-opc-8-1 #x0) (f-dc-9-1 #x0) rd rn)
1787		 (if (g-op)
1788		     (set rd rn))
1789		 ()
1790		 )
1791
1792    (dni_wrapper (.sym "cmov" cond)
1793		 (.str "move register " cond)
1794		 ()
1795		 (.str "mov" name " $rd6,$rn6")
1796		 (+ OP4_MISC (.sym "OPC_" cond) (f-opc-8-1 #x0) (f-dc-9-1 #x0) (f-opc-19-4 #x2) (f-dc-25-6 #x0) rd6 rn6)
1797		 (if (g-op)
1798		     (set rd6 rn6))
1799		 ()
1800		 )
1801    (dnmi (.sym "cmov.l" cond)
1802	  (.str "move register " cond)
1803	  (NO-DIS)
1804	  (.str "mov" name ".l $rd6,$rn6")
1805	  (emit (.sym "cmov" cond) rd6 rn6)
1806	  )
1807
1808
1809
1810    )
1811  )
1812
1813					; basic conditional moves
1814(move-insns "eq"    EQ	   (.pmacro () (eq zbit #x1)))
1815(move-insns "ne"    NE	   (.pmacro () (eq zbit #x0)))
1816(move-insns "gtu"   GTU	   (.pmacro () (and BI cbit (not BI zbit))))
1817(move-insns "gteu"  GTEU   (.pmacro () (eq cbit #x1)))
1818(move-insns "lteu"  LTEU   (.pmacro () (or BI (not BI cbit) zbit)))
1819(move-insns "ltu"   LTU	   (.pmacro () (eq cbit #x0)))
1820(move-insns "gt"    GT	   (.pmacro () (and BI (not BI zbit) (eq vbit nbit))))
1821(move-insns "gte"   GTE	   (.pmacro () (eq vbit nbit)))
1822(move-insns "lt"    LT	   (.pmacro () (xor BI vbit nbit)))
1823(move-insns "lte"   LTE	   (.pmacro () (or BI zbit (xor vbit nbit))))
1824
1825					; unconditional move
1826(move-insns ""      B      (.pmacro () #x1))
1827
1828
1829					; floating point condition codes (floating point instructions)
1830(move-insns "beq"   BEQ    (.pmacro () (or BI bzbit bzbit)))
1831(move-insns "bne"   BNE    (.pmacro () (not BI bzbit)))
1832(move-insns "blt"   BLT    (.pmacro () (and BI bnbit (not bzbit))))
1833(move-insns "blte"  BLTE   (.pmacro () (or BI bnbit bzbit)))
1834
1835;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1836;; MOVTS RD,RN
1837;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1838
1839;; 16 bits form exists for group zero ( M1 and M0 equals to zero ) only
1840
1841(dni_wrapper movts16
1842	     "move to special reg"
1843	     (SHORT-INSN)
1844	     "movts $sn,$rd"
1845	     (+ OP4_FLOW16 (f-opc-8-5 #x10) (f-dc-9-1 #x0) rd sn) ;; rd is source for movts
1846	     (set sn rd)
1847	     ()
1848	     )
1849
1850(define-pmacro (op-mmr-movts name sdreg code)
1851  (begin
1852
1853    (dni_wrapper (.sym "movts" name)
1854		 (.str "move to " name)
1855		 ()
1856		 (.str "movts $" sdreg ",$rd6")
1857		 (+ OP4_MISC (f-dc-7-4 #x0) (f-opc-8-1 #x1) (f-dc-9-1 #x0) (f-opc-19-4 #x2) (f-dc-25-4 #x0) (f-dc-21-2 code) sdreg rd6);; rd is source for movts
1858		 (set sdreg rd6)
1859		 ()
1860		 )
1861
1862    (dnmi (.sym "movts.l" name)
1863	  (.str "move to " name)
1864	  (NO-DIS)
1865	  (.str "movts.l $" sdreg ",$rd6")
1866	  (emit (.sym "movts" name) sdreg rd6)
1867	  )
1868
1869
1870
1871
1872    )
1873  )
1874
1875(op-mmr-movts  6    sn6    #x0)
1876(op-mmr-movts  dma  sndma  #x1)
1877(op-mmr-movts  mem  snmem  #x2)
1878(op-mmr-movts  mesh snmesh #x3)
1879
1880;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1881;; MOVFS
1882;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1883(dni_wrapper movfs16
1884	     "move from special register"
1885	     (SHORT-INSN)
1886	     "movfs $rd,$sn"
1887	     (+ OP4_FLOW16 (f-opc-8-5 #x11) (f-dc-9-1 #x0) rd sn)
1888	     (set rd sn)
1889	     ()
1890	     )
1891
1892
1893
1894(define-pmacro (op-mmr-movfs name snreg code)
1895  (begin
1896
1897    (dni_wrapper (.sym "movfs" name)
1898		 (.str "move from " name)
1899		 ()
1900		 (.str "movfs $rd6,$" snreg)
1901		 (+ OP4_MISC (f-dc-7-4 #x1) (f-opc-8-1 #x1) (f-dc-9-1 #x0) (f-opc-19-4 #x2) (f-dc-25-4 #x0) (f-dc-21-2 code) rd6 snreg)
1902		 (set rd6 snreg)
1903		 ()
1904		 )
1905
1906    (dnmi (.sym "movfs.l" name)
1907	  (.str "move from " name)
1908	  (NO-DIS)
1909	  (.str "movfs.l $rd6,$" snreg)
1910	  (emit (.sym "movfs" name) rd6 snreg)
1911	  )
1912
1913
1914
1915    )
1916  )
1917
1918(op-mmr-movfs  6    sn6    #x0)
1919(op-mmr-movfs  dma  sndma  #x1)
1920(op-mmr-movfs  mem  snmem  #x2)
1921(op-mmr-movfs  mesh snmesh #x3)
1922
1923
1924
1925
1926
1927;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1928;; NOP 0x1a2
1929;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1930(dni_wrapper nop
1931	     "no-operation"
1932	     (SHORT-INSN)
1933	     "nop"
1934	     (+ OP4_FLOW16 (f-opc-8-5 #x1a) (f-dc-15-7 #x0))
1935	     (nop)
1936	     ()
1937	     )
1938
1939
1940;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1941;; SNOP 0x3a2
1942;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1943(dni_wrapper snop
1944	     "no-operation"
1945	     (SHORT-INSN)
1946	     "snop"
1947	     (+ OP4_FLOW16 (f-opc-8-5 #x3a) (f-dc-15-7 #x0))
1948	     (nop)
1949	     ()
1950	     )
1951
1952
1953;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1954;; UNIMPL
1955;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1956(dni_wrapper unimpl
1957	     "not-implemented"
1958	     ()
1959	     "unimpl"
1960	     (+ (f-opc-31-32  #x000F000F))
1961	     (nop)
1962	     ()
1963	     )
1964
1965;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1966;; IDLE
1967;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1968
1969(dni idle "idle until interrupt" () "idle"
1970     (+ OP4_FLOW16 (f-opc-8-5 #x1b) (f-dc-15-7 #x0))
1971     ;;     (set pc pc)	;; should branch to self until interrupt, but not modeling interrupts
1972     (sequence ()
1973       (set caibit 0)
1974       (c-code "sim_engine_halt (CPU_STATE (current_cpu), current_cpu, NULL, \
1975		pc, sim_exited, 0);"))
1976     ()
1977     )
1978
1979;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1980;; BKPT
1981;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1982
1983(dni bkpt
1984     "breakpoint"
1985     (SHORT-INSN)
1986     "bkpt"
1987     (+ OP4_FLOW16 (f-opc-8-5 #x1c) (f-dc-15-7 #x0))
1988     (sequence ()
1989     	 (c-call  "epiphany_break" pc)
1990     	(set pc pc)
1991     	)
1992     ()
1993     )
1994
1995;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1996;; MBKPT
1997;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1998
1999(dni mbkpt
2000     "multicorebreakpoint"
2001     (SHORT-INSN)
2002     "mbkpt"
2003     (+ OP4_FLOW16 (f-opc-8-5 #x1c) (f-dc-15-7 #x1))
2004     ;;;(c-call "epiphany_break" pc)
2005     (nop) ;; ignore the multi core break point in the simulator
2006     ()
2007     )
2008
2009;;;;;;;;;;;;;;;;
2010;; RTI
2011;;;;;;;;;;;;;;;;
2012
2013(dni rti "return from interrupt" (SHORT-INSN UNCOND-CTI)
2014     "rti"
2015     (+ OP4_FLOW16 (f-opc-8-5 #x1d) (f-dc-15-7 #x0))
2016     (sequence ()
2017	       ;; 	(set (hcr-ipend)
2018	       ;; 	     (xor (hcr-ipend)
2019	       ;; 		  (sll (const 1)
2020	       ;; 		       (sub (c-raw-call SI "ffs" (and (hcr-ipend) (not (hcr-imask))))
2021	       ;; 			    (const 1)))))
2022
2023	       (set (hcr-ipend)
2024		    (c-call SI "epiphany_rti" (hcr-ipend) (hcr-imask)))
2025	       (set gidisablebit 0)
2026	       (set kmbit 0)
2027					;(set caibit 1)
2028	       (set pc (hcr-iret)))
2029     ()
2030     )
2031;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2032;; WAND is a wired flag that runs around the chip
2033;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2034(dni_wrapper wand     "wand"
2035	     (SHORT-INSN)
2036	     "wand"
2037	     (+ OP4_FLOW16 (f-opc-8-5 #x18) (f-dc-15-7 #x0))
2038	     (set sflagbit 1)
2039	     ()
2040	     )
2041
2042;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2043;; Sync likes wand, but wired OR
2044;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2045(dni_wrapper sync     "sync"
2046	     (SHORT-INSN)
2047	     "sync"
2048	     (+ OP4_FLOW16 (f-opc-8-5 #x1f) (f-dc-15-7 #x0))
2049	     (nop);;TODO
2050	     ()
2051	     )
2052
2053;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2054;; GIE
2055;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2056(dni_wrapper gien     "global interrupt enable"
2057	     (SHORT-INSN)
2058	     "gie"
2059	     (+ OP4_FLOW16 (f-gien-gidis-9-1 #x0) (f-opc-8-5 #x19) (f-dc-15-6 #x0))
2060	     (set gidisablebit 0)
2061	     ()
2062	     )
2063
2064;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2065;; GIDIS
2066;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2067(dni_wrapper gidis     "global interrupt disable"
2068	     (SHORT-INSN)
2069	     "gid"
2070	     (+ OP4_FLOW16 (f-gien-gidis-9-1 #x1) (f-opc-8-5 #x19) (f-dc-15-6 #x0))
2071	     (set gidisablebit 1)
2072	     ()
2073	     )
2074
2075
2076
2077;;;;;;;;;;;;;;;;
2078;; SWI
2079;;;;;;;;;;;;;;;;
2080
2081;; Model only immediate 'fire' exception, if gien cleared or masked don't fire and don't check later - no ilat like behavior
2082(dni swi_num "software interrupt" (SHORT-INSN UNCOND-CTI)
2083     "swi $swi_num"
2084     (+ OP4_FLOW16 (f-opc-8-5 #x1e) (f-trap-swi-9-1 #x0)  swi_num)
2085     (sequence ()  (call-exception #x24  #x80))
2086     ;;      (if (eq gie 1)
2087     ;; 	 (sequence ()
2088     ;; 		   (set kmbit 1)
2089     ;; 		   (set gie 0)
2090     ;; 		   (set (hcr-iret) (add pc (const 2)))
2091     ;; 		   (set (hcr-ipend) (or (hcr-ipend) (const #x80)))
2092     ;; 		   (set pc (const #x1c))
2093
2094     ;; 			   )
2095     ;; 	 ;; schedule interrupt
2096     ;; 	 (set (hcr-ilat) (or (hcr-ilat) (const #x80)))
2097     ;; 	 )
2098     ()
2099     )
2100(dni swi "software interrupt" (ALIAS SHORT-INSN UNCOND-CTI)
2101     "swi"
2102     (+ OP4_FLOW16 (f-opc-8-5 #x1e) (f-trap-swi-9-1 #x0) (f-dc-15-6 #x0))
2103     (sequence ()  (call-exception #x24  #x80))
2104     ()
2105     )
2106
2107
2108;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2109;; TRAP #disp3 - simulator only and chip as well - make the same grouop as swi
2110;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2111
2112;; Only defining 16-bit form of this instruction.  It exists to support the
2113;; simulator, by giving us a simple input/output mechanism beyond returning values
2114;; in registers or memory.
2115;; TRAP #N  - special sw trap for simulator support;  allows simple i/o using fixed arguments
2116;; TRAP #0  - write (r0=i/o channel, r1=addr, r2=len) returns status in r0
2117;; TRAP #1  - read  (r0=i/o channel, r1=addr, r2=len) returns length or -<code> on error
2118;; TRAP #2  - open  (r0=string path, r1=mode) returns channel# or -<code> on error
2119;; TRAP #3  - exit  (r0=status code) never returns.
2120;; TRAP #4  - print "pass\n" and exit
2121;; TRAP #5  - print "fail\n" and exit
2122;; TRAP #6  - close  (r0=i/o channel)
2123
2124(dni trap16 "trap to simulator"
2125     (SHORT-INSN UNCOND-CTI)
2126     "trap $trapnum6"
2127     (+ OP4_FLOW16 (f-opc-8-5 #x1e) (f-trap-swi-9-1 #x1)  trapnum6) ;;  (+ OP4_IMM16 OPI_TRAP (f-rd 0) (f-rn 0) disp3)
2128     (set (reg SI h-registers 0) (c-call SI "epiphany_trap" pc trapnum6))
2129     ()
2130     )
2131
2132
2133;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2134;; Integer arithmetic instructions 3 address forms
2135;;   both 16 and 32 bit forms
2136;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2137
2138(define-pmacro (op-rrr name sem-op cond-op)
2139  (begin
2140    (dni_wrapper (.sym name "16")
2141		 (.str name)
2142		 (SHORT-INSN)
2143		 (.str name " $rd,$rn,$rm")
2144		 (+ OP4_ALU16 (.sym "OPB_" (.upcase (.str name))) rd rn rm)
2145		 (sequence ()
2146			   (cond-op rn rm)
2147			   (set rd (sem-op SI rn rm))
2148			   (set zbit (zflag rd))
2149			   (set nbit (nflag rd))
2150			   )
2151		 ()
2152		 )
2153
2154    (dni_wrapper (.sym name)
2155		 (.str name)
2156		 ()
2157		 (.str name " $rd6,$rn6,$rm6")
2158		 (+ OP4_MISC (.sym "OPB_" (.upcase (.str name))) (f-opc-19-4 #xa) (f-dc-22-3 #x0) rd6 rn6 rm6)
2159		 (sequence ()
2160			   (cond-op rn6 rm6)
2161			   (set rd6 (sem-op SI rn6 rm6))
2162			   (set zbit (zflag rd6))
2163			   (set nbit (nflag rd6))
2164			   )
2165		 ()
2166		 )
2167
2168    (dnmi (.sym name ".l")
2169	  (.str name)
2170	  (NO-DIS)
2171	  (.str name ".l $rd6,$rn6,$rm6")
2172	  (emit (.sym name) rd6 rn6 rm6)
2173	  )
2174
2175
2176
2177    )
2178  )
2179
2180;; submacros to set condition codes
2181;;  NZ are always set to reflect the sign and value of the result
2182;;  CV are a function of the operator
2183(define-pmacro (add-vc a b) (sequence ()
2184				      (set cbit (add-cflag SI a b 0))
2185				      (set vbit (add-oflag SI a b 0))
2186				      (set vsbit (or BI vsbit vbit))
2187				      ))
2188
2189(define-pmacro (sub-vc a b) (sequence ()
2190				      (set cbit (not (sub-cflag SI a b 0)))
2191				      (set vbit (sub-oflag SI a b 0))
2192				      (set vsbit (or vsbit vbit))
2193				      ))
2194
2195(define-pmacro (logic-vc a b) (sequence ()
2196					(set cbit 0)
2197					(set vbit 0)
2198					))
2199
2200(op-rrr add add add-vc)
2201(op-rrr sub sub sub-vc)
2202(op-rrr and and logic-vc)
2203(op-rrr orr  or  logic-vc)
2204(op-rrr eor xor logic-vc)
2205
2206;; Integer arithmetic immediate forms
2207
2208(define-pmacro (op-rri name code cond-op)
2209  (begin
2210    (dni_wrapper (.sym name "i16")
2211		 (.str name)
2212		 (SHORT-INSN IMM3)
2213		 (.str name ".s $rd,$rn,$simm3")
2214		 (+ OP4_IMM16 code rd rn simm3)
2215		 (sequence ()
2216			   (cond-op rn simm3)
2217			   (set rd (name SI rn simm3))
2218			   (set zbit (zflag rd))
2219			   (set nbit (nflag rd))
2220			   )
2221		 ()
2222		 )
2223
2224
2225    (dni_wrapper (.sym name "i")
2226		 (.str name)
2227		 ()
2228		 (.str name ".l $rd6,$rn6,$simm11")
2229		 (+ OP4_IMM32 code OPI_25_2_MBZ rd6 rn6 simm11)
2230		 (sequence ()
2231			   (cond-op rn6 simm11)
2232			   (set rd6 (name SI rn6 simm11))
2233			   (set zbit (zflag rd6))
2234			   (set nbit (nflag rd6))
2235			   )
2236		 ()
2237		 )
2238
2239    ;;    (dnmi (.sym name "ri") "relaxed arithmetic immediate" (RELAXED)
2240    ;;	  (.str name " $rd6,$rn6,$simm11")
2241    ;;	  (emit (.sym name "i") rd6 rn6 simm11))
2242    )
2243  )
2244
2245(op-rri add OPI_ADD add-vc)
2246(op-rri sub OPI_SUB sub-vc)
2247
2248(dnmi addir "relaxable short immediate add" (RELAXABLE IMM3)
2249      "add $rd,$rn,$simm3"
2250      (emit addi16 rd rn simm3))
2251
2252(dnmi addi32r "relaxed long immediate add" (RELAXED)
2253      "add $rd6,$rn6,$simm11"
2254      (emit addi rd6 rn6 simm11))
2255
2256;; Again, but not relaxable so that full sized registers are handled
2257(dnmi addi32m "relaxed long immediate add" ()
2258      "add $rd6,$rn6,$simm11"
2259      (emit addi rd6 rn6 simm11))
2260
2261
2262(dnmi subir "relaxable short immediate sub" (RELAXABLE IMM3)
2263      "sub $rd,$rn,$simm3"
2264      (emit subi16 rd rn simm3))
2265
2266(dnmi subi32r "relaxed long immediate sub" (RELAXED)
2267      "sub $rd6,$rn6,$simm11"
2268      (emit subi rd6 rn6 simm11))
2269
2270(dnmi subi32m "relaxed long immediate sub" ()
2271      "sub $rd6,$rn6,$simm11"
2272      (emit subi rd6 rn6 simm11))
2273
2274
2275;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2276;; Shift instructions 3 address forms
2277;;   both 16 and 32 bit forms
2278;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2279
2280(define-pmacro (shift-rrr name sem-op)
2281  (begin
2282    (dni_wrapper (.sym name "16")
2283		 (.str name)
2284		 (SHORT-INSN)
2285		 (.str name " $rd,$rn,$rm")
2286		 (+ OP4_ALU16 (.sym "OPB_" (.upcase (.str name))) rd rn rm)
2287		 (sequence ()
2288			   (logic-vc rn rm)
2289			   (set rd (sem-op SI rn (and rm (const 31))))
2290			   (set zbit (zflag rd))
2291			   (set nbit (nflag rd))
2292			   )
2293		 ()
2294		 )
2295
2296    (dni_wrapper (.sym name)
2297		 (.str name)
2298		 ()
2299		 (.str name " $rd6,$rn6,$rm6")
2300		 (+ OP4_MISC (.sym "OPB_" (.upcase (.str name))) (f-opc-19-4 #xa) (f-dc-22-3 #x0) rd6 rn6 rm6)
2301		 (sequence ()
2302			   (logic-vc rn6 rm6)
2303			   (set rd6 (sem-op SI rn6 (and rm6 (const 31))))
2304			   (set zbit (zflag rd6))
2305			   (set nbit (nflag rd6))
2306			   )
2307		 ()
2308		 )
2309
2310    (dnmi (.sym name ".l")
2311	  (.str name)
2312	  (NO-DIS)
2313	  (.str name ".l $rd6,$rn6,$rm6")
2314	  (emit (.sym name) rd6 rn6 rm6)
2315	  )
2316    )
2317  )
2318
2319(shift-rrr asr sra)
2320(shift-rrr lsr srl)
2321(shift-rrr lsl sll)
2322
2323(define-pmacro (op-shift-rri name shortcode f5 longcode sem-op)
2324  (begin
2325    (dni_wrapper (.sym name "i16")
2326		 (.str name)
2327		 (SHORT-INSN)
2328		 (.str name " $rd,$rn,$shift")
2329		 (+ shortcode (f-opc-4-1 f5) rd rn shift)
2330		 (sequence ()
2331			   (logic-vc rn shift)
2332			   (set rd (sem-op SI rn shift))
2333			   (set zbit (zflag rd))
2334			   (set nbit (nflag rd))
2335			   )
2336		 ()
2337		 )
2338    (dni_wrapper (.sym name "i32")
2339		 (.str name)
2340		 ()
2341		 (.str name " $rd6,$rn6,$shift")
2342		 (+ OP4_MISC (f-opc-4-1 f5) (f-opc-19-4 longcode) (f-dc-25-6 0) rd6 rn6 shift)
2343		 (sequence ()
2344			   (logic-vc rn6 shift)
2345			   (set rd6 (sem-op SI rn6 shift))
2346			   (set zbit (zflag rd6))
2347			   (set nbit (nflag rd6))
2348			   )
2349		 ()
2350		 )
2351
2352    (dnmi (.sym name "i32.l")
2353	  (.str name)
2354	  (NO-DIS)
2355	  (.str name ".l $rd6,$rn6,$shift")
2356	  (emit (.sym name "i32") rd6  rn6 shift)
2357	  )
2358
2359
2360    )
2361  )
2362
2363(op-shift-rri lsr OP4_LSHIFT16 0 #x6 srl)
2364(op-shift-rri lsl OP4_LSHIFT16 1 #x6 sll)
2365(op-shift-rri asr OP4_ASHIFT16 0 #xe sra)
2366
2367;; BITR - bitreversal (FFT)
2368;;
2369;; From Dr Dobbs et al.
2370;;
2371;; unsigned int v;
2372;; v = ((v >> 1) & 0x55555555) | ((v & 0x55555555) << 1);  ;; swap odd-even bits
2373;; v = ((v >> 2) & 0x33333333) | ((v & 0x33333333) << 2);  ;; swap pairs
2374;; v = ((v >> 4) & 0x0f0f0f0f) | ((v & 0x0f0f0f0f) << 4);  ;; swap nibbles
2375;; v = ((v >> 8) & 0x00ff00ff) | ((v & 0x00ff00ff) << 8);  ;; swap bytes
2376;; v =  (v >> 16)              |  (v               << 16); ;; swap halves
2377(define-pmacro (bit-reversal dest src)
2378  (sequence ((SI v))
2379	    (set v src)
2380	    (set v (or (and (srl v 1) #x55555555) (sll (and v #x55555555) 1)))
2381	    (set v (or (and (srl v 2) #x33333333) (sll (and v #x33333333) 2)))
2382	    (set v (or (and (srl v 4) #x0f0f0f0f) (sll (and v #x0f0f0f0f) 4)))
2383	    (set v (or (and (srl v 8) #x00ff00ff) (sll (and v #x00ff00ff) 8)))
2384	    (set v (or      (srl v 16)            (sll      v            16)))
2385	    (set dest v)
2386	    ))
2387
2388(dni_wrapper bitr16 "bit reverse short"
2389	     (SHORT-INSN)
2390	     ("bitr $rd,$rn")
2391	     (+ OP4_ASHIFT16 (f-opc-4-1 1) rd rn (f-shift 0))
2392	     (sequence ()
2393		       (bit-reversal rd rn)
2394		       (set zbit (zflag rd))
2395		       (set nbit (nflag rd))
2396		       (set cbit 0)
2397		       (set vbit 0)
2398		       )
2399	     ()
2400	     )
2401
2402(dni_wrapper bitr "bit reverse"
2403	     ()
2404	     ("bitr $rd6,$rn6")
2405	     (+ OP4_MISC (f-opc-4-1 1) (f-opc-19-4 #xe) (f-dc-25-6 0) rd6 rn6 (f-shift 0))
2406	     (sequence ()
2407		       (bit-reversal rd6 rn6)
2408		       (set zbit (zflag rd6))
2409		       (set nbit (nflag rd6))
2410		       (set cbit 0)
2411		       (set vbit 0)
2412		       )
2413	     ()
2414	     )
2415(dnmi bitrl "bit reverse l"
2416      (NO-DIS)
2417      ("bitr.l $rd6,$rn6")
2418      (emit bitr rd6 rn6)
2419      )
2420
2421;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2422;; Integer arithmetic instructions
2423;; Extended operation
2424;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2425
2426(define-pmacro (op-iextrrr  name  cond-op)
2427  (begin
2428
2429    (dni_wrapper (.sym name)
2430		 (.str name)
2431		 ()
2432		 (.str name " $rd6,$rn6,$rm6")
2433		 (+ OP4_MISC (.sym "OPBE_" (.upcase (.str name))) (f-opc-19-4 #xa) (f-dc-22-2 #x0)  (f-dc-20-1 #x1)
2434		    rd6 rn6 rm6)
2435		 (sequence ()
2436			   ;;  TODO cond operation (cond-op rn6 rm6)
2437			   ;;(set rd6 (sem-op SI rn6 rm6))
2438			   (set zbit (zflag rd6))
2439			   (set nbit (nflag rd6))
2440			   )
2441		 ()
2442		 )
2443
2444    (dnmi (.sym name ".l")
2445	  (.str name)
2446	  (NO-DIS)
2447	  (.str name ".l $rd6,$rn6,$rm6")
2448	  (emit (.sym name) rd6  rn6 rm6)
2449	  )
2450    )
2451  )
2452
2453(op-iextrrr fext  sub-vc)
2454(op-iextrrr fdep  sub-vc)
2455(op-iextrrr lfsr  sub-vc)
2456
2457
2458
2459;; Immediate moves.  The 8 bit form is relaxed if it doesn't fit or is external
2460;; Move RD,#IMM
2461(dni_wrapper mov8
2462	     "mov imm8"
2463	     (SHORT-INSN)
2464	     "mov.b $rd,$imm8"
2465	     (+ OP4_IMM16 (f-opc-4-1 #x0) rd imm8)
2466	     (set rd (zext SI imm8))
2467	     ()
2468	     )
2469
2470(dnmi mov8r "mov imm8 relaxable"
2471      (RELAXABLE)
2472      "mov $rd,$imm8"
2473      (emit mov8 rd imm8))
2474
2475(dni_wrapper mov16
2476	     "mov imm16"
2477	     ()
2478	     "mov.l $rd6,$imm16"
2479	     (+ OP4_IMM32 (f-opc-4-1 #x0) (f-opc-19-4 #x2) (f-dc-28-1 #x0) rd6 imm16)
2480	     (set rd6 (zext SI imm16))
2481	     ()
2482	     )
2483
2484(dnmi mov16r "mov imm16 relaxable"
2485      ()
2486      "mov $rd6,$imm16"
2487      (emit mov16 rd6 imm16))
2488
2489;; MOVE TO HIGH WORD
2490(dni_wrapper movt
2491	     "movt imm16"
2492	     ()
2493	     "movt $rd6,$imm16"
2494	     (+ OP4_IMM32 (f-opc-4-1 #x0) (f-opc-19-4 #x2) (f-dc-28-1 #x1) rd6 imm16)
2495	     (set rd6 (or (and SI rd6 (const #xffff)) ; keep low bits of rd
2496			  (sll SI imm16 (const 16)))) ; replacing just high bits
2497	     ()
2498	     )
2499(dnmi movtl
2500      "movt imm16"
2501      (NO-DIS)
2502      "movt.l $rd6,$imm16"
2503      (emit movt rd6 imm16)
2504      )
2505
2506
2507
2508;; FLOATING POINT OPERATIONS
2509;; TWO operands
2510(define-pmacro (op-two_operands-float name code)
2511  (begin
2512    (dni_wrapper
2513      (.sym "f_" name "f16")
2514      (.str "f_" name)
2515      (SHORT-INSN)
2516      (.str "f" name " $rd,$rn,$rm")
2517      (+ OP4_DSP16 code rd rn rm)
2518      (sequence ()
2519	(if
2520	  (eq  arithmetic-modebit2 0)
2521	  (sequence ((SF fptemp) (SI sdtmp))
2522	    (set sdtmp  (c-call SI (.str "epiphany_f" name) rd rn rm))
2523
2524	    ;;All bits are calculated in C
2525	    (set bzbit  (c-call BI "get_epiphany_fzeroflag" sdtmp))
2526	    (set bnbit  (c-call BI "get_epiphany_fnegativeflag" sdtmp))
2527	    (set bvbit  (c-call BI "get_epiphany_foverflowflag" sdtmp))
2528	    (set bubit  (c-call BI "get_epiphany_funderflowflag" sdtmp))
2529	    (set bibit  (c-call BI "get_epiphany_finvalidflag" sdtmp))
2530	    (set bvsbit (or bvsbit bvbit))
2531	    (set busbit (or busbit bubit))
2532	    (set bisbit (or bisbit bibit))
2533	    (set rd sdtmp)
2534	    (if (or (and invExcEnbit bisbit)
2535		    (or (and ovfExcEnbit bvsbit) (and unExcEnbit busbit)))
2536		(sequence ()
2537		  (set expcause0bit (const 1))
2538		  (set expcause1bit (const 1))
2539		  (call-exception #x4 #x2)))
2540	    ))
2541	(if (eq arithmetic-modebit2 1)
2542	    (sequence ((SI sdtmp))
2543	      (set sdtmp  (c-call SI (.str "epiphany_i" name) rd rn rm))
2544	      ;; carry is not connected inb the design (set bcbit bcbit)
2545	      (set bzbit (zflag sdtmp))
2546	      (set bnbit (nflag sdtmp))
2547	      (set rd sdtmp)))
2548	)
2549
2550      ()
2551      )
2552    (dnmi (.sym "i_" name "f16")
2553	  (.str "i_" name)
2554	  (SHORT-INSN NO-DIS)
2555	  (.str "i" name " $rd,$rn,$rm")
2556	  (emit (.sym "f_" name "f16") rd rn rm)
2557    )
2558
2559
2560    (dni_wrapper
2561      (.sym "f_" name "f32")
2562      (.str "f_" name)
2563      ()
2564      (.str "f" name " $rd6,$rn6,$rm6")
2565      (+ OP4_MISC code (f-opc-19-4 #x7) (f-dc-22-3 #x0) rd6 rn6 rm6)
2566      (sequence ()
2567	(if
2568	  (eq arithmetic-modebit2 0)
2569	  (sequence ((SF fptemp) (SI sdtmp))
2570	    (set sdtmp  (c-call SI (.str "epiphany_f" name) rd6 rn6 rm6))
2571
2572	    ;;All bits are calculated in C
2573	    (set bzbit  (c-call BI "get_epiphany_fzeroflag" sdtmp))
2574	    (set bnbit  (c-call BI "get_epiphany_fnegativeflag" sdtmp))
2575	    (set bvbit  (c-call BI "get_epiphany_foverflowflag" sdtmp))
2576	    (set bubit  (c-call BI "get_epiphany_funderflowflag" sdtmp))
2577	    (set bibit  (c-call BI "get_epiphany_finvalidflag" sdtmp))
2578	    (set bvsbit (or bvsbit bvbit))
2579	    (set busbit (or busbit bubit))
2580	    (set bisbit (or bisbit bibit))
2581
2582	    (set rd6 sdtmp)
2583
2584	    (if (or (and invExcEnbit bisbit)
2585		    (or (and ovfExcEnbit bvsbit) (and unExcEnbit busbit)))
2586		(sequence ()
2587		  (set expcause0bit (const 1))
2588		  (set expcause1bit (const 1))
2589		  (call-exception #x4 #x2)))
2590	    )
2591	  )
2592	(if (eq arithmetic-modebit2 1)
2593	    (sequence ((SI sdtmp))
2594	      (set sdtmp (c-call SI (.str "epiphany_i" name) rd6 rn6 rm6))
2595	      ;; carry is not connected inb the design (set bcbit bcbit)
2596	      (set bzbit (zflag sdtmp))
2597	      (set bnbit (nflag sdtmp))
2598	      (set rd6 sdtmp)
2599	      )
2600	    )
2601	)
2602      ()
2603      )
2604
2605    (dnmi (.sym "f_" name "f32.l")
2606	  (.str "f_" name)
2607	  (NO-DIS)
2608	  (.str "f" name ".l $rd6,$rn6,$rm6")
2609	  (emit  (.sym "f_" name "f32") rd6  rn6 rm6)
2610	  )
2611    (dnmi (.sym "i_" name "f32")
2612	  (.str "i_" name)
2613	  (NO-DIS)
2614	  (.str "i" name " $rd6,$rn6,$rm6")
2615	  (emit  (.sym "f_" name "f32") rd6  rn6 rm6)
2616	  )
2617    (dnmi (.sym "i_" name "f32.l")
2618	  (.str "i_" name)
2619	  (NO-DIS)
2620	  (.str "i" name ".l $rd6,$rn6,$rm6")
2621	  (emit  (.sym "f_" name "f32") rd6  rn6 rm6)
2622	  )
2623
2624
2625
2626    )
2627  )
2628
2629(op-two_operands-float add OPF_ADD)
2630(op-two_operands-float sub OPF_SUB)
2631(op-two_operands-float mul OPF_MUL)
2632(op-two_operands-float madd OPF_MADD)
2633(op-two_operands-float msub OPF_MSUB)
2634
2635;; ONE operands
2636;; FABS
2637(define-pmacro (op-fabs-float name code)
2638  (begin
2639    (dni_wrapper (.sym "f_" name "f16")
2640		 (.str "f_" name)
2641		 (SHORT-INSN)
2642		 (.str "f" name " rd,rn")
2643		 (+ OP4_DSP16 code rd rn rn)
2644		 (sequence ((SF fptemp) (SI sdtmp))
2645
2646		   ;(set sdtmp  (and rn  #x7fffffff))
2647		   (set sdtmp  (c-call SI (.str "epiphany_fabs") rd rn rn))
2648
2649
2650		   (set bnbit  (const SI 0))
2651		   (set bzbit (eq SI sdtmp  (const SI 0)))
2652
2653		   ;;TODO subnormal ??
2654		   (set bvsbit (or bvsbit bvbit))
2655		   (set busbit (or busbit bubit))
2656		   (set bisbit (or bisbit bibit))
2657
2658		   (set rd sdtmp)
2659		   )
2660		 ()
2661		 )
2662
2663    (dni_wrapper (.sym "f_" name "f32")
2664		 (.str "f_" name)
2665		 ()
2666		 (.str "f" name " $rd6,$rn6")
2667		 (+ OP4_MISC code (f-opc-19-4 #x7) (f-dc-22-3 #x0) rd6 rn6 rn6)
2668		 (sequence ((SF fptemp) (SI sdtmp))
2669
2670
2671		   ;(set sdtmp   (and rn6  #x7fffffff))
2672
2673		   (set sdtmp  (c-call SI (.str "epiphany_fabs") rd6 rn6 rn6))
2674
2675
2676		   (set bnbit   (const SI 0))
2677		   (set bzbit (eq SI sdtmp  (const SI 0)))
2678
2679		   (set bvsbit (or bvsbit bvbit))
2680		   (set busbit (or busbit bubit))
2681		   (set bisbit (or bisbit bibit))
2682
2683		   (set rd6 sdtmp)
2684
2685		   )
2686		 ()
2687		 )
2688
2689    (dnmi  (.sym "f_" name "f32.l")
2690	   (.str "f_" name)
2691	   (NO-DIS)
2692	   (.str "f" name ".l $rd6,$rn6")
2693	   (emit (.sym "f_" name "f32") rd6  rn6)
2694	   )
2695
2696
2697    )
2698  )
2699
2700(op-fabs-float abs OPF_FABS)
2701
2702
2703(define-pmacro (op-fix2float-float name code)
2704  (begin
2705    (dni_wrapper (.sym "f_" name "f16")
2706		 (.str "f_" name)
2707		 (SHORT-INSN)
2708		 (.str "f" name " $rd,$rn")
2709		 (+ OP4_DSP16 code frd frn frn)
2710		 (sequence ((SF fptemp) (SI sdtmp))
2711
2712		   (set sdtmp  (c-call SI (.str "epiphany_f" name) rd rn rn))
2713
2714		   (set bnbit (lt SI sdtmp  (const SI 0)))
2715		   (set bzbit (eq SI sdtmp  (const SI 0)))
2716
2717		   (set bvsbit (or bvsbit bvbit))
2718		   (set busbit (or busbit bubit))
2719		   (set bisbit (or bisbit bibit))
2720
2721		   (set rd sdtmp)
2722		   )
2723		 ()
2724		 )
2725
2726
2727    (dni_wrapper (.sym "f_" name "f32")
2728		 (.str "f_" name)
2729		 ()
2730		 (.str "f" name " $rd6,$rn6")
2731		 (+ OP4_MISC code (f-opc-19-4 #x7) (f-dc-22-3 #x0) rd6 rn6 rn6)
2732		 (sequence ((SF fptemp) (SI sdtmp))
2733
2734		   (set sdtmp  (c-call SI (.str "epiphany_f" name) rd6 rn6 rn6))
2735
2736		   (set bnbit (lt SI sdtmp  (const SI 0)))
2737		   (set bzbit (eq SI sdtmp  (const SI 0)))
2738
2739		   (set bvsbit (or bvsbit bvbit))
2740		   (set busbit (or busbit bubit))
2741		   (set bisbit (or bisbit bibit))
2742
2743		   (set rd6 sdtmp)
2744
2745		   )
2746		 ()
2747		 )
2748
2749    (dnmi (.sym "f_" name "f32.l")
2750	  (.str "f_" name)
2751	  (NO-DIS)
2752	  (.str "f" name ".l $rd6,$rn6")
2753	  (emit (.sym "f_" name "f32")  rd6 rn6)
2754	  )
2755    )
2756  )
2757
2758(op-fix2float-float loat OPF_FLOAT)
2759
2760(define-pmacro (op-float2fix-float name code)
2761  (begin
2762    (dni_wrapper (.sym "f_" name "f16")
2763		 (.str "f_" name)
2764		 (SHORT-INSN)
2765		 (.str "f" name " $rd,$rn")
2766		 (+ OP4_DSP16 code rd rn rn)
2767		 (sequence ((SF fptemp) (SI sdtmp))
2768
2769		   (set sdtmp  (c-call SI (.str "epiphany_f" name) rd rn rn))
2770
2771		   (set bzbit (zflag sdtmp))
2772		   (set bnbit (nflag sdtmp))
2773
2774		   (set bvbit  (c-call BI "get_epiphany_foverflowflag" sdtmp))
2775		   (set bubit  (c-call BI "get_epiphany_funderflowflag" sdtmp))
2776		   (set bibit  (c-call BI "get_epiphany_finvalidflag" sdtmp))
2777
2778		   (set bvsbit (or bvsbit bvbit))
2779		   (set busbit (or busbit bubit))
2780		   (set bisbit (or bisbit bibit))
2781
2782		   (set rd6 sdtmp)
2783
2784		   (if (or (and invExcEnbit bisbit)
2785			   (or (and ovfExcEnbit busbit)
2786			       (and unExcEnbit bvsbit)))
2787		       (sequence ()
2788			 (set expcause0bit (const 1))
2789			 (set expcause1bit (const 1))
2790			 (call-exception #x4 #x2)))
2791		   (set rd sdtmp)
2792		   )
2793		 ()
2794		 )
2795
2796
2797
2798    (dni_wrapper (.sym "f_" name "f32")
2799		 (.str "f_" name)
2800		 ()
2801		 (.str "f" name " $rd6,$rn6")
2802		 (+ OP4_MISC code (f-opc-19-4 #x7) (f-dc-22-3 #x0) rd6 rn6 rn6)
2803		 (sequence ((SF fptemp) (SI sdtmp))
2804
2805		   (set sdtmp  (c-call SI (.str "epiphany_f" name) rd6 rn6 rm6))
2806
2807		   (set bzbit (zflag sdtmp))
2808		   (set bnbit (nflag sdtmp))
2809
2810		   (set bvbit  (c-call BI "get_epiphany_foverflowflag" sdtmp))
2811		   (set bubit  (c-call BI "get_epiphany_funderflowflag" sdtmp))
2812		   (set bibit  (c-call BI "get_epiphany_finvalidflag" sdtmp))
2813
2814		   (set bvsbit (or bvsbit bvbit))
2815		   (set busbit (or busbit bubit))
2816		   (set bisbit (or bisbit bibit))
2817
2818		   (set rd6 sdtmp)
2819
2820		   (if (or (and invExcEnbit bisbit)
2821			   (or (and ovfExcEnbit busbit)
2822			       (and unExcEnbit bvsbit)))
2823		       (sequence ()
2824			 (set expcause0bit (const 1))
2825			 (set expcause1bit (const 1))
2826			 (call-exception #x4 #x2))
2827		       )
2828
2829		   )
2830		 ()
2831		 )
2832
2833    (dnmi (.sym "f_" name "f32.l")
2834	  (.str "f_" name)
2835	  (NO-DIS)
2836	  (.str "f" name ".l $rd6,$rn6")
2837	  (emit (.sym "f_" name "f32") rd6  rn6)
2838	  )
2839
2840
2841    )
2842  )
2843
2844
2845
2846
2847
2848(op-float2fix-float ix OPF_FIX)
2849
2850;; MAC (Multiply and Accumulate Instructions
2851;; (define-pmacro (op-mac-float name code)
2852;;   (begin
2853;;     (dni_wrapper (.sym "fm" name "f16")
2854;; 	 (.str "fm" name)
2855;; 	 (SHORT-INSN)
2856;; 	 (.str "fm" name " $frd,$frn,$frm")
2857;; 	 (+ OP4_DSP16 code frd frn frm)
2858;; 	 (sequence ((SF fptemp))
2859;; 		   (set bvbit 0)
2860;; 		   (set busbit 0)
2861;;                    (set fptemp (c-call SF (.str "epiphany_fm" name) frd frm frn))
2862;; 		   (set bnbit (lt SF fptemp (const SF 0)))
2863;; 		   (set bzbit (eq SF fptemp (const SF 0)))
2864;; 		   (set bvsbit (or bvsbit bvbit))
2865;;                    (set frd fptemp)
2866;; ;		   (set rd (subword SI frd 0))
2867;; 		   )
2868;; 	 ()
2869;; 	 )
2870
2871;;     (dni_wrapper (.sym "fm" name "f32")
2872;; 	 (.str "fm" name)
2873;; 	 ()
2874;; 	 (.str "fm" name " $frd6,$frn6,$frm6")
2875;; 	 (+ OP4_MISC code (f-opc-19-4 #x7) (f-dc-22-3 #x0) frd6 frn6 frm6)
2876;; 	 (sequence ((SF fptemp))
2877;; 		   (set bvbit 0)
2878;; 		   (set busbit 0)
2879;;                    (set fptemp (c-call SF (.str "epiphany_fm" name) frd6 frm6 frn6))
2880;; 		   (set bnbit (lt SF fptemp (const SF 0)))
2881;; 		   (set bzbit (eq SF fptemp (const SF 0)))
2882;; 		   (set bvsbit (or bvsbit bvbit))
2883;;                    (set frd6 fptemp)
2884;; ;		   (set rd6 (subword SI frd6 0))
2885;; 		   )
2886;; 	 ()
2887;; 	 )
2888;;     )
2889;; )
2890
2891
2892
2893
2894
2895
2896
2897					; extended floating point operation
2898
2899
2900(define-pmacro (op-fextop-float name code)
2901  (begin
2902
2903    (dni_wrapper (.sym "f_" name "f32")
2904		 (.str "f_" name)
2905		 ()
2906		 (.str "f" name " $frd6,$frn6")
2907		 (+ OP4_MISC code (f-opc-19-4 #x7) (f-dc-22-2 #x0) (f-dc-20-1 #x1) frd6 frn6 frn6)
2908		 (sequence ((SF fptemp))
2909			   (set bvbit 0)
2910			   (set busbit 0)
2911			   (set fptemp (c-call SF (.str "epiphany_f" name) frn6))
2912			   (set bnbit (lt SF fptemp (const SF 0)))
2913			   (set bzbit (eq SF fptemp (const SF 0)))
2914			   (set bvsbit (or bvsbit bvbit))
2915			   (set frd6 fptemp)
2916
2917			   )
2918		 ()
2919		 )
2920
2921
2922    (dnmi (.sym "f_" name "f32.l")
2923	  (.str "f_" name)
2924	  (NO-DIS)
2925	  (.str "f" name ".l $frd6,$frn6")
2926	  (emit (.sym "f_" name "f32") frd6 frn6)
2927	  )
2928    )
2929  )
2930
2931(op-fextop-float recip OPF_FRECIP)
2932(op-fextop-float sqrt  OPF_FSQRT)
2933
2934
2935
2936
2937
2938