1use std::fmt;
5
6#[derive(Copy, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
8pub enum AluOp {
9 Add,
10 AddCarry,
11 Sub,
12 SubCarry,
13 And,
14 Xor,
15 Or,
16 Compare,
17}
18
19impl AluOp {
20 pub(super) fn from_ycode(code: u8) -> Self {
22 match code {
23 0 => Self::Add,
24 1 => Self::AddCarry,
25 2 => Self::Sub,
26 3 => Self::SubCarry,
27 4 => Self::And,
28 5 => Self::Xor,
29 6 => Self::Or,
30 7 => Self::Compare,
31 _ => panic!("Unrecognized ALU operation type (y code) {}", code),
32 }
33 }
34}
35
36impl fmt::Display for AluOp {
37 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
38 match *self {
39 Self::Add => f.write_str("ADD"),
40 Self::AddCarry => f.write_str("ADC"),
41 Self::Sub => f.write_str("SUB"),
42 Self::SubCarry => f.write_str("SBC"),
43 Self::And => f.write_str("AND"),
44 Self::Xor => f.write_str("XOR"),
45 Self::Or => f.write_str("OR"),
46 Self::Compare => f.write_str("CP"),
47 }
48 }
49}
50
51#[derive(Copy, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
53pub enum AluUnaryOp {
54 RotateLeft8,
56 RotateLeft9,
58 RotateRight8,
60 RotateRight9,
62 DecimalAdjust,
65 SetCarryFlag,
67 Compliment,
69 ComplimentCarryFlag,
71}
72
73impl AluUnaryOp {
74 pub(super) fn from_ycode(code: u8) -> Self {
76 match code {
77 0 => Self::RotateLeft8,
78 1 => Self::RotateRight8,
79 2 => Self::RotateLeft9,
80 3 => Self::RotateRight9,
81 4 => Self::DecimalAdjust,
82 5 => Self::Compliment,
83 6 => Self::SetCarryFlag,
84 7 => Self::ComplimentCarryFlag,
85 _ => panic!("Unrecognized ALU unary operation type (y code) {}", code),
86 }
87 }
88}
89
90impl fmt::Display for AluUnaryOp {
91 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
92 match *self {
93 Self::RotateLeft8 => f.write_str("RLCA"),
94 Self::RotateLeft9 => f.write_str("RLA"),
95 Self::RotateRight8 => f.write_str("RRCA"),
96 Self::RotateRight9 => f.write_str("RRA"),
97 Self::DecimalAdjust => f.write_str("DAA"),
98 Self::SetCarryFlag => f.write_str("SCF"),
99 Self::Compliment => f.write_str("CPL"),
100 Self::ComplimentCarryFlag => f.write_str("CCF"),
101 }
102 }
103}
104
105#[derive(Copy, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
107pub enum Operand8 {
108 B,
111 C,
113 D,
115 E,
117 H,
119 L,
121 A,
123
124 AddrHL,
127 AddrBC,
129 AddrDE,
131 AddrHLInc,
133 AddrHLDec,
135 Immediate,
139 AddrImmediate,
141
142 AddrRelC,
145 AddrRelImmediate,
147}
148
149impl Operand8 {
150 pub(super) fn from_regcode(code: u8) -> Self {
153 match code {
154 0 => Self::B,
155 1 => Self::C,
156 2 => Self::D,
157 3 => Self::E,
158 4 => Self::H,
159 5 => Self::L,
160 6 => Self::AddrHL,
161 7 => Self::A,
162 _ => panic!("Unrecognized Operand type {}", code),
163 }
164 }
165
166 pub(super) fn from_indirect(code: u8) -> Self {
168 match code {
169 0 => Self::AddrBC,
170 1 => Self::AddrDE,
171 2 => Self::AddrHLInc,
172 3 => Self::AddrHLDec,
173 _ => panic!("Unrecognized indirection code {}", code),
174 }
175 }
176}
177
178impl fmt::Display for Operand8 {
179 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
180 match *self {
181 Self::A => f.write_str("A"),
182 Self::B => f.write_str("B"),
183 Self::C => f.write_str("C"),
184 Self::D => f.write_str("D"),
185 Self::E => f.write_str("E"),
186 Self::H => f.write_str("H"),
187 Self::L => f.write_str("L"),
188 Self::AddrHL => f.write_str("(HL)"),
189 Self::AddrBC => f.write_str("(BC)"),
190 Self::AddrDE => f.write_str("(DE)"),
191 Self::AddrHLInc => f.write_str("(HL+)"),
192 Self::AddrHLDec => f.write_str("(HL-)"),
193 Self::Immediate => f.write_str("u8"),
194 Self::AddrImmediate => f.write_str("(u16)"),
195 Self::AddrRelC => f.write_str("(FF00+C)"),
196 Self::AddrRelImmediate => f.write_str("(FF00+u8)"),
197 }
198 }
199}
200
201#[derive(Copy, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
203pub enum Operand16 {
204 BC,
206 DE,
208 HL,
210 AF,
212 Sp,
214 Immediate,
217 AddrImmediate,
221}
222
223impl Operand16 {
224 pub(super) fn from_pair_code_sp(code: u8) -> Operand16 {
227 match code {
228 0 => Operand16::BC,
229 1 => Operand16::DE,
230 2 => Operand16::HL,
231 3 => Operand16::Sp,
232 _ => panic!("Unrecognized register pair code {}", code),
233 }
234 }
235
236 pub(super) fn from_pair_code_af(code: u8) -> Operand16 {
239 match code {
240 0 => Operand16::BC,
241 1 => Operand16::DE,
242 2 => Operand16::HL,
243 3 => Operand16::AF,
244 _ => panic!("Unrecognized register pair code {}", code),
245 }
246 }
247}
248
249impl fmt::Display for Operand16 {
250 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
251 match *self {
252 Operand16::BC => f.write_str("BC"),
253 Operand16::DE => f.write_str("DE"),
254 Operand16::HL => f.write_str("HL"),
255 Operand16::AF => f.write_str("AF"),
256 Operand16::Sp => f.write_str("SP"),
257 Operand16::Immediate => f.write_str("u16"),
258 Operand16::AddrImmediate => f.write_str("(u16)"),
259 }
260 }
261}
262
263#[derive(Copy, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
265pub enum ConditionCode {
266 Unconditional,
267 NonZero,
268 Zero,
269 NoCarry,
270 Carry,
271}
272
273impl ConditionCode {
274 pub(super) fn from_relative_cond_code(code: u8) -> Self {
278 match code {
279 3 => Self::Unconditional,
280 4..=7 => Self::from_absolute_cond_code(code - 4),
281 _ => panic!("Unrecognized Relative-Jump condtion code {}", code),
282 }
283 }
284
285 pub(super) fn from_absolute_cond_code(code: u8) -> Self {
288 match code {
289 0 => Self::NonZero,
290 1 => Self::Zero,
291 2 => Self::NoCarry,
292 3 => Self::Carry,
293 _ => panic!("Unrecognized Absolute-Jump condtion code {}", code),
294 }
295 }
296}
297
298impl fmt::Display for ConditionCode {
299 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
300 match *self {
301 Self::Unconditional => Ok(()),
302 Self::NonZero => f.write_str("NZ"),
303 Self::Zero => f.write_str("Z"),
304 Self::NoCarry => f.write_str("NC"),
305 Self::Carry => f.write_str("C"),
306 }
307 }
308}