1 #ifndef INSN_H
2 #define INSN_H
3 /* insn.h: Instruction encoding definition
4  * $Id: insn.h,v 1.5 2002/10/01 22:25:18 rowan Exp $
5  */
6 
7 /* This file is part of `exhaust', a memory array redcode simulator.
8  * Copyright (C) 2002 M Joonas Pihlaja
9  * Public Domain.
10  */
11 
12 /*
13  * Instruction encoding:
14  *
15  * Instructions are held in a insn_t typed struct with three fields:
16  *   in:	instruction flags, opcode, modifier, a-mode, b-mode
17  *   a:		a-value
18  *   b: 	b-value
19  *
20  * The layout of the `in' field is as follows:
21  *
22  * bit         15 14 13 12 11 10  9  8  7  6  5  4  3  2  1  0
23  * field   | flags | |- op-code  -| |-.mod-| |b-mode| |a-mode|
24  *
25  * Currently there is only one flag, the fl_START flag, which
26  * the assembler uses to figure out the starting instruction
27  * of a warrior (i.e. the one given by the START label).
28  */
29 
30 #define mBITS 3			/* number of bits for mode */
31 #define opBITS 5		/* bits for opcode */
32 #define moBITS 3		/* bits for modifier */
33 #define flBITS 2		/* bits for flags */
34 
35 /* Positions of various fields
36  */
37 #define maPOS 0
38 #define mbPOS (maPOS + mBITS)
39 #define moPOS (mbPOS + mBITS)
40 #define opPOS (moPOS + moBITS)
41 #define flPOS (opPOS + opBITS)
42 
43 /* Various masks.  These extract a field once it has been
44  * shifted to the least significant bits of the word.
45  */
46 #define moMASK ((1<<moBITS)-1)
47 #define opMASK ((1<<opBITS)-1)
48 #define mMASK ((1<<mBITS)-1)
49 #define flMASK ((1<<flBITS)-1)
50 #define iMASK ( (1<<flPOS)-1 )
51 
52 /*
53  * Extract the flags of an instruction `in' field
54  */
55 #define get_flags(in) ( ((in)>>flPOS) & flMASK )
56 #define set_flags(in,flags) ( (in) |= ((flags)<<flPOS) )
57 #define clr_flags(in,flags) ( (in) &=~ ((flags)<<flPOS) )
58 
59 
60 /*
61  * OP(o,m,ma,mb): This macro encodes an instruction `in' field
62  *		  from its various components (not flags).
63  *
64  * 	o: opcode
65  *	m: modifier
66  *	ma: a-mode
67  *	mb: b-mode
68  *
69  *  e.g. OP(SPL, mF, DIRECT, BPREDEC )
70  *  is a
71  *       spl.f $  , <
72  */
73 #define _OP(o,m) ( ((o)<<moBITS) | (m) )
74 #define OP( o, m, ma, mb ) ((_OP((o),(m))<<moPOS) | ((mb) << mbPOS) | (ma))
75 
76 
77 /*
78  * Encodings for various fields of the `in' field.
79  *
80  */
81 enum {
82   DAT,				/* must be 0 */
83   SPL,
84   MOV,
85   DJN,
86   ADD,
87   JMZ,
88   SUB,
89   SEQ,
90   SNE,
91   SLT,
92   JMN,
93   JMP,
94   NOP,
95   MUL,
96   MODM,
97   DIV,
98   LDP,
99   STP				/* 18 */
100 };
101 
102 enum {
103   mF, mA, mB, mAB, mBA, mX, mI	/* 7 */
104 };
105 
106 enum {				/* must start from 0,
107 				   the ordering is important */
108   DIRECT,
109   IMMEDIATE,
110   BINDIRECT,
111   BPREDEC,
112   BPOSTINC,
113   AINDIRECT,
114   APREDEC,
115   APOSTINC		/* 8 */
116 };
117 
118 #define INDIRECT BINDIRECT
119 #define PREDEC   BPREDEC
120 #define POSTINC  BPOSTINC
121 
122 #define INDIR_A(mode) ((mode) >= AINDIRECT)
123 #define RAW_MODE(mode) ((mode) + (INDIRECT-AINDIRECT))
124 
125 /*
126  * flags
127  */
128 enum {
129   flB_START			/* start label */
130 };
131 
132 #define fl_START (1<<flB_START)
133 
134 
135 /* Macros to take things mod CORESIZE
136  *
137  * Mod here is the `mathematical' modulo, with non-negative
138  * results even with x negative.
139  *
140  * MOD(x,M):	x mod CORESIZE
141  * MODS(x,M):	x mod CORESIZE
142  */
143 #define MODS(x,M) ( (int)(x)%(int)(M) >= 0 \
144 		  ? (int)(x)%(int)(M) \
145 		  : (M) + ((int)(x)%(int)(M)) )
146 #define MOD(x,M) ( (x) % (M) )
147 
148 #endif /* INSN_H */
149