cpu_alpha_instr_alu.cc Source File

Back to the index.

cpu_alpha_instr_alu.cc
Go to the documentation of this file.
1 /*
2  * Copyright (C) 2005-2011 Anders Gavare. All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions are met:
6  *
7  * 1. Redistributions of source code must retain the above copyright
8  * notice, this list of conditions and the following disclaimer.
9  * 2. Redistributions in binary form must reproduce the above copyright
10  * notice, this list of conditions and the following disclaimer in the
11  * documentation and/or other materials provided with the distribution.
12  * 3. The name of the author may not be used to endorse or promote products
13  * derived from this software without specific prior written permission.
14  *
15  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
16  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18  * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
19  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
20  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
21  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
22  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
23  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
24  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
25  * SUCH DAMAGE.
26  *
27  *
28  * Alpha ALU instructions. (Included from tmp_alpha_misc.c.)
29  *
30  *
31  * Most ALU instructions have the following arguments:
32  *
33  * arg[0] = pointer to destination uint64_t
34  * arg[1] = pointer to source uint64_t nr 1
35  * arg[2] = pointer to source uint64_t nr 2
36  *
37  * or, if ALU_IMM is set, arg[2] contains an 8-bit immediate value.
38  *
39  * The main function groups are:
40  *
41  * ALU_INS inserts
42  * ALU_EXT extracts
43  * ALU_MSK masks
44  * ALU_CMOV conditional moves
45  * ALU_CMP compares
46  * ALU_CMPBGE byte compare
47  * none of the above everything else (add, sub, ...)
48  */
49 
50 void ALU_N(struct cpu *cpu, struct alpha_instr_call *ic)
51 {
52 #ifdef ALU_INS
53 
54  uint64_t x = *((uint64_t *)ic->arg[1]);
55  int r = (
56 #ifdef ALU_IMM
57  ic->arg[2]
58 #else
59  (*((uint64_t *)ic->arg[2]))
60 #endif
61  & 7) * 8;
62 
63 #ifdef ALU_B
64  x &= 0xff;
65 #endif
66 #ifdef ALU_W
67  x &= 0xffff;
68 #endif
69 #ifdef ALU_L
70  x &= 0xffffffffULL;
71 #endif
72 
73 #ifdef ALU_LO
74  x <<= r;
75 #else
76  r = 64 - r;
77  if (r == 64)
78  x = 0;
79  else
80  x >>= r;
81 #endif
82  *((uint64_t *)ic->arg[0]) = x;
83 
84 #else /* ! INS */
85 
86 #ifdef ALU_EXT
87 
88  uint64_t x = *((uint64_t *)ic->arg[1]);
89  int r = (
90 #ifdef ALU_IMM
91  ic->arg[2]
92 #else
93  (*((uint64_t *)ic->arg[2]))
94 #endif
95  & 7) * 8;
96 #ifdef ALU_LO
97  x >>= r;
98 #else
99  r = 64 - r;
100  if (r != 64)
101  x <<= r;
102 #endif
103 #ifdef ALU_B
104  x &= 0xff;
105 #endif
106 #ifdef ALU_W
107  x &= 0xffff;
108 #endif
109 #ifdef ALU_L
110  x &= 0xffffffffULL;
111 #endif
112  *((uint64_t *)ic->arg[0]) = x;
113 
114 #else /* ! EXT */
115 
116 #ifdef ALU_MSK
117 
118  uint64_t x = *((uint64_t *)ic->arg[1]);
119 #ifdef ALU_B
120  uint64_t mask = 0x00000000000000ffULL;
121 #endif
122 #ifdef ALU_W
123  uint64_t mask = 0x000000000000ffffULL;
124 #endif
125 #ifdef ALU_L
126  uint64_t mask = 0x00000000ffffffffULL;
127 #endif
128 #ifdef ALU_Q
129  uint64_t mask = 0xffffffffffffffffULL;
130 #endif
131  int r = (
132 #ifdef ALU_IMM
133  ic->arg[2]
134 #else
135  (*((uint64_t *)ic->arg[2]))
136 #endif
137  & 7) * 8;
138 
139 #ifdef ALU_LO
140  mask <<= r;
141 #else
142  if (r == 0)
143  mask = 0;
144  else
145  mask >>= (64 - r);
146 #endif
147 
148  *((uint64_t *)ic->arg[0]) = x & ~mask;
149 
150 #else /* !MSK */
151 
152 #ifdef ALU_CMOV
153 
154  if (
155 #ifdef ALU_CMOV_lbc
156  !(
157 #endif
158  (*((int64_t *)ic->arg[1]))
159 #ifdef ALU_CMOV_eq
160  == 0
161 #endif
162 #ifdef ALU_CMOV_ne
163  != 0
164 #endif
165 #ifdef ALU_CMOV_le
166  <= 0
167 #endif
168 #ifdef ALU_CMOV_lt
169  < 0
170 #endif
171 #ifdef ALU_CMOV_ge
172  >= 0
173 #endif
174 #ifdef ALU_CMOV_gt
175  > 0
176 #endif
177 #ifdef ALU_CMOV_lbs
178  & 1
179 #endif
180 #ifdef ALU_CMOV_lbc
181  & 1)
182 #endif
183  )
184  *((uint64_t *)ic->arg[0]) =
185 #ifdef ALU_IMM
186  (uint64_t)ic->arg[2]
187 #else
188  (*((uint64_t *)ic->arg[2]))
189 #endif
190  ;
191 
192 #else /* ! CMOV */
193 
194 #ifdef ALU_CMPBGE
195 
196  uint64_t ra = *((uint64_t *)ic->arg[1]), rc = 0, rb =
197 #ifdef ALU_IMM
198  (uint64_t)ic->arg[2]
199 #else
200  (*((uint64_t *)ic->arg[2]))
201 #endif
202  ;
203  int i;
204  for (i=7; i>=0; i--) {
205  if ((uint8_t)ra >= (uint8_t)rb)
206  rc |= (1 << i);
207  rb >>= 8; ra >>= 8;
208  }
209 
210  *((uint64_t *)ic->arg[0]) = rc;
211 
212 #else /* ! CMPBGE */
213 
214 #ifdef ALU_CMP
215 
216  uint64_t x;
217 
218  x = (*((
219 #ifdef ALU_UNSIGNED
220  uint64_t
221 #else
222  int64_t
223 #endif
224  *)ic->arg[1]))
225 
226 #ifdef ALU_CMP_EQ
227  ==
228 #endif
229 #ifdef ALU_CMP_LE
230  <=
231 #endif
232 #ifdef ALU_CMP_LT
233  <
234 #endif
235 
236 #ifdef ALU_IMM
237 #ifdef ALU_UNSIGNED
238  (uint64_t)ic->arg[2]
239 #else
240  (int64_t)ic->arg[2]
241 #endif
242 #else
243 #ifdef ALU_UNSIGNED
244  (*((uint64_t *)ic->arg[2]))
245 #else
246  (*((int64_t *)ic->arg[2]))
247 #endif
248 #endif
249  ;
250 
251 #else /* !ALU_CMP */
252 
253 #ifdef ALU_LONG
254  /* Long */
255  int32_t x;
256 #else
257  /* Quad */
258  int64_t x;
259 #endif
260 
261 #ifdef ALU_ZAP
262  /* Prepare for zapping: */
263  uint64_t zapmask = 0xffffffffffffffffULL;
264  int zapbytes =
265 #ifdef ALU_NOT
266  ~
267 #endif
268 #ifdef ALU_IMM
269  (int64_t)ic->arg[2]
270 #else
271  (*((uint64_t *)ic->arg[2]))
272 #endif
273  ;
274  if (zapbytes & 0x80)
275  zapmask &= ~0xff00000000000000ULL;
276  if (zapbytes & 0x40)
277  zapmask &= ~0xff000000000000ULL;
278  if (zapbytes & 0x20)
279  zapmask &= ~0xff0000000000ULL;
280  if (zapbytes & 0x10)
281  zapmask &= ~0xff00000000ULL;
282  if (zapbytes & 0x08)
283  zapmask &= ~0xff000000ULL;
284  if (zapbytes & 0x04)
285  zapmask &= ~0xff0000ULL;
286  if (zapbytes & 0x02)
287  zapmask &= ~0xff00ULL;
288  if (zapbytes & 0x01)
289  zapmask &= ~0xffULL;
290 #endif /* ZAP */
291 
292  x = (
293 #ifdef ALU_SRA
294  (int64_t)
295 #endif
296  (*((uint64_t *)ic->arg[1]))
297 #ifdef ALU_S4
298  * 4
299 #endif
300 #ifdef ALU_S8
301  * 8
302 #endif
303  )
304 #ifdef ALU_ADD
305  +
306 #endif
307 #ifdef ALU_SUB
308  -
309 #endif
310 #ifdef ALU_OR
311  |
312 #endif
313 #ifdef ALU_XOR
314  ^
315 #endif
316 #ifdef ALU_AND
317  &
318 #endif
319 #ifdef ALU_SLL
320  <<
321 #endif
322 #if defined(ALU_SRA) || defined(ALU_SRL)
323  >>
324 #endif
325 
326 #ifdef ALU_ZAP
327  & zapmask
328 #else /* !ZAP */
329  (
330 #ifdef ALU_NOT
331  ~
332 #endif
333  (
334 #ifdef ALU_IMM
335  (int64_t)ic->arg[2]
336 #else
337  (*((uint64_t *)ic->arg[2]))
338 #endif
339 #if defined(ALU_SRA) || defined(ALU_SRL) || defined(ALU_SLL)
340  & 63
341 #endif
342  )
343  )
344 #endif /* !ZAP */
345 
346  ;
347 
348 #endif /* !ALU_CMP */
349 
350  *((uint64_t *)ic->arg[0]) = x;
351 #endif /* ! CMPBGE */
352 #endif /* ! CMOV */
353 #endif /* ! MSK */
354 #endif /* ! EXT */
355 #endif /* ! INS */
356 }
357 
#define ALU_OR
struct arm_instr_call * ic
#define ALU_CMP_LT
#define ALU_SRL
void ALU_N(struct cpu *cpu, struct alpha_instr_call *ic)
#define ALU_XOR
#define ALU_IMM
#define ALU_CMP_LE
#define ALU_AND
Definition: cpu.h:326
#define ALU_SUB
#define ALU_SRA
#define ALU_UNSIGNED
#define ALU_SLL
#define ALU_CMOV_lbc
#define ALU_ADD
#define ALU_CMP_EQ

Generated on Fri Dec 7 2018 19:52:23 for GXemul by doxygen 1.8.13