1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21#include <stdio.h>
22#include <string.h>
23
24#include "config.h"
25#include "cpu.h"
26#include "exec-all.h"
27#include "qemu-common.h"
28#include "gdbstub.h"
29
30#include "helpers.h"
31
32#define SIGNBIT (1u << 31)
33
34enum m68k_cpuid {
35 M68K_CPUID_M5206,
36 M68K_CPUID_M5208,
37 M68K_CPUID_CFV4E,
38 M68K_CPUID_ANY,
39};
40
41typedef struct m68k_def_t m68k_def_t;
42
43struct m68k_def_t {
44 const char * name;
45 enum m68k_cpuid id;
46};
47
48static m68k_def_t m68k_cpu_defs[] = {
49 {"m5206", M68K_CPUID_M5206},
50 {"m5208", M68K_CPUID_M5208},
51 {"cfv4e", M68K_CPUID_CFV4E},
52 {"any", M68K_CPUID_ANY},
53 {NULL, 0},
54};
55
56void m68k_cpu_list(FILE *f, int (*cpu_fprintf)(FILE *f, const char *fmt, ...))
57{
58 unsigned int i;
59
60 for (i = 0; m68k_cpu_defs[i].name; i++) {
61 (*cpu_fprintf)(f, "%s\n", m68k_cpu_defs[i].name);
62 }
63}
64
65static int fpu_gdb_get_reg(CPUState *env, uint8_t *mem_buf, int n)
66{
67 if (n < 8) {
68 stfq_p(mem_buf, env->fregs[n]);
69 return 8;
70 }
71 if (n < 11) {
72
73 memset(mem_buf, 0, 4);
74 return 4;
75 }
76 return 0;
77}
78
79static int fpu_gdb_set_reg(CPUState *env, uint8_t *mem_buf, int n)
80{
81 if (n < 8) {
82 env->fregs[n] = ldfq_p(mem_buf);
83 return 8;
84 }
85 if (n < 11) {
86
87 return 4;
88 }
89 return 0;
90}
91
92static void m68k_set_feature(CPUM68KState *env, int feature)
93{
94 env->features |= (1u << feature);
95}
96
97static int cpu_m68k_set_model(CPUM68KState *env, const char *name)
98{
99 m68k_def_t *def;
100
101 for (def = m68k_cpu_defs; def->name; def++) {
102 if (strcmp(def->name, name) == 0)
103 break;
104 }
105 if (!def->name)
106 return -1;
107
108 switch (def->id) {
109 case M68K_CPUID_M5206:
110 m68k_set_feature(env, M68K_FEATURE_CF_ISA_A);
111 break;
112 case M68K_CPUID_M5208:
113 m68k_set_feature(env, M68K_FEATURE_CF_ISA_A);
114 m68k_set_feature(env, M68K_FEATURE_CF_ISA_APLUSC);
115 m68k_set_feature(env, M68K_FEATURE_BRAL);
116 m68k_set_feature(env, M68K_FEATURE_CF_EMAC);
117 m68k_set_feature(env, M68K_FEATURE_USP);
118 break;
119 case M68K_CPUID_CFV4E:
120 m68k_set_feature(env, M68K_FEATURE_CF_ISA_A);
121 m68k_set_feature(env, M68K_FEATURE_CF_ISA_B);
122 m68k_set_feature(env, M68K_FEATURE_BRAL);
123 m68k_set_feature(env, M68K_FEATURE_CF_FPU);
124 m68k_set_feature(env, M68K_FEATURE_CF_EMAC);
125 m68k_set_feature(env, M68K_FEATURE_USP);
126 break;
127 case M68K_CPUID_ANY:
128 m68k_set_feature(env, M68K_FEATURE_CF_ISA_A);
129 m68k_set_feature(env, M68K_FEATURE_CF_ISA_B);
130 m68k_set_feature(env, M68K_FEATURE_CF_ISA_APLUSC);
131 m68k_set_feature(env, M68K_FEATURE_BRAL);
132 m68k_set_feature(env, M68K_FEATURE_CF_FPU);
133
134
135 m68k_set_feature(env, M68K_FEATURE_CF_EMAC);
136 m68k_set_feature(env, M68K_FEATURE_CF_EMAC_B);
137 m68k_set_feature(env, M68K_FEATURE_USP);
138 m68k_set_feature(env, M68K_FEATURE_EXT_FULL);
139 m68k_set_feature(env, M68K_FEATURE_WORD_INDEX);
140 break;
141 }
142
143 register_m68k_insns(env);
144 if (m68k_feature (env, M68K_FEATURE_CF_FPU)) {
145 gdb_register_coprocessor(env, fpu_gdb_get_reg, fpu_gdb_set_reg,
146 11, "cf-fp.xml", 18);
147 }
148
149 return 0;
150}
151
152void cpu_reset(CPUM68KState *env)
153{
154 if (qemu_loglevel_mask(CPU_LOG_RESET)) {
155 qemu_log("CPU Reset (CPU %d)\n", env->cpu_index);
156 log_cpu_state(env, 0);
157 }
158
159 memset(env, 0, offsetof(CPUM68KState, breakpoints));
160#if !defined (CONFIG_USER_ONLY)
161 env->sr = 0x2700;
162#endif
163 m68k_switch_sp(env);
164
165 env->cc_op = CC_OP_FLAGS;
166
167 env->pc = 0;
168 tlb_flush(env, 1);
169}
170
171CPUM68KState *cpu_m68k_init(const char *cpu_model)
172{
173 CPUM68KState *env;
174 static int inited;
175
176 env = qemu_mallocz(sizeof(CPUM68KState));
177 cpu_exec_init(env);
178 if (!inited) {
179 inited = 1;
180 m68k_tcg_init();
181 }
182
183 env->cpu_model_str = cpu_model;
184
185 if (cpu_m68k_set_model(env, cpu_model) < 0) {
186 cpu_m68k_close(env);
187 return NULL;
188 }
189
190 cpu_reset(env);
191 qemu_init_vcpu(env);
192 return env;
193}
194
195void cpu_m68k_close(CPUM68KState *env)
196{
197 qemu_free(env);
198}
199
200void cpu_m68k_flush_flags(CPUM68KState *env, int cc_op)
201{
202 int flags;
203 uint32_t src;
204 uint32_t dest;
205 uint32_t tmp;
206
207#define HIGHBIT 0x80000000u
208
209#define SET_NZ(x) do { \
210 if ((x) == 0) \
211 flags |= CCF_Z; \
212 else if ((int32_t)(x) < 0) \
213 flags |= CCF_N; \
214 } while (0)
215
216#define SET_FLAGS_SUB(type, utype) do { \
217 SET_NZ((type)dest); \
218 tmp = dest + src; \
219 if ((utype) tmp < (utype) src) \
220 flags |= CCF_C; \
221 if ((1u << (sizeof(type) * 8 - 1)) & (tmp ^ dest) & (tmp ^ src)) \
222 flags |= CCF_V; \
223 } while (0)
224
225 flags = 0;
226 src = env->cc_src;
227 dest = env->cc_dest;
228 switch (cc_op) {
229 case CC_OP_FLAGS:
230 flags = dest;
231 break;
232 case CC_OP_LOGIC:
233 SET_NZ(dest);
234 break;
235 case CC_OP_ADD:
236 SET_NZ(dest);
237 if (dest < src)
238 flags |= CCF_C;
239 tmp = dest - src;
240 if (HIGHBIT & (src ^ dest) & ~(tmp ^ src))
241 flags |= CCF_V;
242 break;
243 case CC_OP_SUB:
244 SET_FLAGS_SUB(int32_t, uint32_t);
245 break;
246 case CC_OP_CMPB:
247 SET_FLAGS_SUB(int8_t, uint8_t);
248 break;
249 case CC_OP_CMPW:
250 SET_FLAGS_SUB(int16_t, uint16_t);
251 break;
252 case CC_OP_ADDX:
253 SET_NZ(dest);
254 if (dest <= src)
255 flags |= CCF_C;
256 tmp = dest - src - 1;
257 if (HIGHBIT & (src ^ dest) & ~(tmp ^ src))
258 flags |= CCF_V;
259 break;
260 case CC_OP_SUBX:
261 SET_NZ(dest);
262 tmp = dest + src + 1;
263 if (tmp <= src)
264 flags |= CCF_C;
265 if (HIGHBIT & (tmp ^ dest) & (tmp ^ src))
266 flags |= CCF_V;
267 break;
268 case CC_OP_SHIFT:
269 SET_NZ(dest);
270 if (src)
271 flags |= CCF_C;
272 break;
273 default:
274 cpu_abort(env, "Bad CC_OP %d", cc_op);
275 }
276 env->cc_op = CC_OP_FLAGS;
277 env->cc_dest = flags;
278}
279
280void HELPER(movec)(CPUM68KState *env, uint32_t reg, uint32_t val)
281{
282 switch (reg) {
283 case 0x02:
284 env->cacr = val;
285 m68k_switch_sp(env);
286 break;
287 case 0x04: case 0x05: case 0x06: case 0x07:
288
289 break;
290 case 0x801:
291 env->vbr = val;
292 break;
293
294 default:
295 cpu_abort(env, "Unimplemented control register write 0x%x = 0x%x\n",
296 reg, val);
297 }
298}
299
300void HELPER(set_macsr)(CPUM68KState *env, uint32_t val)
301{
302 uint32_t acc;
303 int8_t exthigh;
304 uint8_t extlow;
305 uint64_t regval;
306 int i;
307 if ((env->macsr ^ val) & (MACSR_FI | MACSR_SU)) {
308 for (i = 0; i < 4; i++) {
309 regval = env->macc[i];
310 exthigh = regval >> 40;
311 if (env->macsr & MACSR_FI) {
312 acc = regval >> 8;
313 extlow = regval;
314 } else {
315 acc = regval;
316 extlow = regval >> 32;
317 }
318 if (env->macsr & MACSR_FI) {
319 regval = (((uint64_t)acc) << 8) | extlow;
320 regval |= ((int64_t)exthigh) << 40;
321 } else if (env->macsr & MACSR_SU) {
322 regval = acc | (((int64_t)extlow) << 32);
323 regval |= ((int64_t)exthigh) << 40;
324 } else {
325 regval = acc | (((uint64_t)extlow) << 32);
326 regval |= ((uint64_t)(uint8_t)exthigh) << 40;
327 }
328 env->macc[i] = regval;
329 }
330 }
331 env->macsr = val;
332}
333
334void m68k_switch_sp(CPUM68KState *env)
335{
336 int new_sp;
337
338 env->sp[env->current_sp] = env->aregs[7];
339 new_sp = (env->sr & SR_S && env->cacr & M68K_CACR_EUSP)
340 ? M68K_SSP : M68K_USP;
341 env->aregs[7] = env->sp[new_sp];
342 env->current_sp = new_sp;
343}
344
345#if defined(CONFIG_USER_ONLY)
346
347int cpu_m68k_handle_mmu_fault (CPUState *env, target_ulong address, int rw,
348 int mmu_idx, int is_softmmu)
349{
350 env->exception_index = EXCP_ACCESS;
351 env->mmu.ar = address;
352 return 1;
353}
354
355#else
356
357
358
359
360target_phys_addr_t cpu_get_phys_page_debug(CPUState *env, target_ulong addr)
361{
362 return addr;
363}
364
365int cpu_m68k_handle_mmu_fault (CPUState *env, target_ulong address, int rw,
366 int mmu_idx, int is_softmmu)
367{
368 int prot;
369
370 address &= TARGET_PAGE_MASK;
371 prot = PAGE_READ | PAGE_WRITE | PAGE_EXEC;
372 tlb_set_page(env, address, address, prot, mmu_idx, TARGET_PAGE_SIZE);
373 return 0;
374}
375
376
377
378
379
380void m68k_set_irq_level(CPUM68KState *env, int level, uint8_t vector)
381{
382 env->pending_level = level;
383 env->pending_vector = vector;
384 if (level)
385 cpu_interrupt(env, CPU_INTERRUPT_HARD);
386 else
387 cpu_reset_interrupt(env, CPU_INTERRUPT_HARD);
388}
389
390#endif
391
392uint32_t HELPER(bitrev)(uint32_t x)
393{
394 x = ((x >> 1) & 0x55555555u) | ((x << 1) & 0xaaaaaaaau);
395 x = ((x >> 2) & 0x33333333u) | ((x << 2) & 0xccccccccu);
396 x = ((x >> 4) & 0x0f0f0f0fu) | ((x << 4) & 0xf0f0f0f0u);
397 return bswap32(x);
398}
399
400uint32_t HELPER(ff1)(uint32_t x)
401{
402 int n;
403 for (n = 32; x; n--)
404 x >>= 1;
405 return n;
406}
407
408uint32_t HELPER(sats)(uint32_t val, uint32_t ccr)
409{
410
411 if (ccr & CCF_V)
412 val = (((int32_t)val) >> 31) ^ SIGNBIT;
413 return val;
414}
415
416uint32_t HELPER(subx_cc)(CPUState *env, uint32_t op1, uint32_t op2)
417{
418 uint32_t res;
419 uint32_t old_flags;
420
421 old_flags = env->cc_dest;
422 if (env->cc_x) {
423 env->cc_x = (op1 <= op2);
424 env->cc_op = CC_OP_SUBX;
425 res = op1 - (op2 + 1);
426 } else {
427 env->cc_x = (op1 < op2);
428 env->cc_op = CC_OP_SUB;
429 res = op1 - op2;
430 }
431 env->cc_dest = res;
432 env->cc_src = op2;
433 cpu_m68k_flush_flags(env, env->cc_op);
434
435 env->cc_dest &= (old_flags | ~CCF_Z);
436 return res;
437}
438
439uint32_t HELPER(addx_cc)(CPUState *env, uint32_t op1, uint32_t op2)
440{
441 uint32_t res;
442 uint32_t old_flags;
443
444 old_flags = env->cc_dest;
445 if (env->cc_x) {
446 res = op1 + op2 + 1;
447 env->cc_x = (res <= op2);
448 env->cc_op = CC_OP_ADDX;
449 } else {
450 res = op1 + op2;
451 env->cc_x = (res < op2);
452 env->cc_op = CC_OP_ADD;
453 }
454 env->cc_dest = res;
455 env->cc_src = op2;
456 cpu_m68k_flush_flags(env, env->cc_op);
457
458 env->cc_dest &= (old_flags | ~CCF_Z);
459 return res;
460}
461
462uint32_t HELPER(xflag_lt)(uint32_t a, uint32_t b)
463{
464 return a < b;
465}
466
467void HELPER(set_sr)(CPUState *env, uint32_t val)
468{
469 env->sr = val & 0xffff;
470 m68k_switch_sp(env);
471}
472
473uint32_t HELPER(shl_cc)(CPUState *env, uint32_t val, uint32_t shift)
474{
475 uint32_t result;
476 uint32_t cf;
477
478 shift &= 63;
479 if (shift == 0) {
480 result = val;
481 cf = env->cc_src & CCF_C;
482 } else if (shift < 32) {
483 result = val << shift;
484 cf = (val >> (32 - shift)) & 1;
485 } else if (shift == 32) {
486 result = 0;
487 cf = val & 1;
488 } else {
489 result = 0;
490 cf = 0;
491 }
492 env->cc_src = cf;
493 env->cc_x = (cf != 0);
494 env->cc_dest = result;
495 return result;
496}
497
498uint32_t HELPER(shr_cc)(CPUState *env, uint32_t val, uint32_t shift)
499{
500 uint32_t result;
501 uint32_t cf;
502
503 shift &= 63;
504 if (shift == 0) {
505 result = val;
506 cf = env->cc_src & CCF_C;
507 } else if (shift < 32) {
508 result = val >> shift;
509 cf = (val >> (shift - 1)) & 1;
510 } else if (shift == 32) {
511 result = 0;
512 cf = val >> 31;
513 } else {
514 result = 0;
515 cf = 0;
516 }
517 env->cc_src = cf;
518 env->cc_x = (cf != 0);
519 env->cc_dest = result;
520 return result;
521}
522
523uint32_t HELPER(sar_cc)(CPUState *env, uint32_t val, uint32_t shift)
524{
525 uint32_t result;
526 uint32_t cf;
527
528 shift &= 63;
529 if (shift == 0) {
530 result = val;
531 cf = (env->cc_src & CCF_C) != 0;
532 } else if (shift < 32) {
533 result = (int32_t)val >> shift;
534 cf = (val >> (shift - 1)) & 1;
535 } else {
536 result = (int32_t)val >> 31;
537 cf = val >> 31;
538 }
539 env->cc_src = cf;
540 env->cc_x = cf;
541 env->cc_dest = result;
542 return result;
543}
544
545
546uint32_t HELPER(f64_to_i32)(CPUState *env, float64 val)
547{
548 return float64_to_int32(val, &env->fp_status);
549}
550
551float32 HELPER(f64_to_f32)(CPUState *env, float64 val)
552{
553 return float64_to_float32(val, &env->fp_status);
554}
555
556float64 HELPER(i32_to_f64)(CPUState *env, uint32_t val)
557{
558 return int32_to_float64(val, &env->fp_status);
559}
560
561float64 HELPER(f32_to_f64)(CPUState *env, float32 val)
562{
563 return float32_to_float64(val, &env->fp_status);
564}
565
566float64 HELPER(iround_f64)(CPUState *env, float64 val)
567{
568 return float64_round_to_int(val, &env->fp_status);
569}
570
571float64 HELPER(itrunc_f64)(CPUState *env, float64 val)
572{
573 return float64_trunc_to_int(val, &env->fp_status);
574}
575
576float64 HELPER(sqrt_f64)(CPUState *env, float64 val)
577{
578 return float64_sqrt(val, &env->fp_status);
579}
580
581float64 HELPER(abs_f64)(float64 val)
582{
583 return float64_abs(val);
584}
585
586float64 HELPER(chs_f64)(float64 val)
587{
588 return float64_chs(val);
589}
590
591float64 HELPER(add_f64)(CPUState *env, float64 a, float64 b)
592{
593 return float64_add(a, b, &env->fp_status);
594}
595
596float64 HELPER(sub_f64)(CPUState *env, float64 a, float64 b)
597{
598 return float64_sub(a, b, &env->fp_status);
599}
600
601float64 HELPER(mul_f64)(CPUState *env, float64 a, float64 b)
602{
603 return float64_mul(a, b, &env->fp_status);
604}
605
606float64 HELPER(div_f64)(CPUState *env, float64 a, float64 b)
607{
608 return float64_div(a, b, &env->fp_status);
609}
610
611float64 HELPER(sub_cmp_f64)(CPUState *env, float64 a, float64 b)
612{
613
614
615 float64 res;
616 res = float64_sub(a, b, &env->fp_status);
617 if (float64_is_nan(res)) {
618
619 if (!float64_is_nan(a)
620 && !float64_is_nan(b)) {
621 res = float64_zero;
622 if (float64_lt_quiet(a, res, &env->fp_status))
623 res = float64_chs(res);
624 }
625 }
626 return res;
627}
628
629uint32_t HELPER(compare_f64)(CPUState *env, float64 val)
630{
631 return float64_compare_quiet(val, float64_zero, &env->fp_status);
632}
633
634
635
636
637
638void HELPER(mac_move)(CPUState *env, uint32_t dest, uint32_t src)
639{
640 uint32_t mask;
641 env->macc[dest] = env->macc[src];
642 mask = MACSR_PAV0 << dest;
643 if (env->macsr & (MACSR_PAV0 << src))
644 env->macsr |= mask;
645 else
646 env->macsr &= ~mask;
647}
648
649uint64_t HELPER(macmuls)(CPUState *env, uint32_t op1, uint32_t op2)
650{
651 int64_t product;
652 int64_t res;
653
654 product = (uint64_t)op1 * op2;
655 res = (product << 24) >> 24;
656 if (res != product) {
657 env->macsr |= MACSR_V;
658 if (env->macsr & MACSR_OMC) {
659
660 if (product < 0)
661 res = ~(1ll << 50);
662 else
663 res = 1ll << 50;
664 }
665 }
666 return res;
667}
668
669uint64_t HELPER(macmulu)(CPUState *env, uint32_t op1, uint32_t op2)
670{
671 uint64_t product;
672
673 product = (uint64_t)op1 * op2;
674 if (product & (0xffffffull << 40)) {
675 env->macsr |= MACSR_V;
676 if (env->macsr & MACSR_OMC) {
677
678 product = 1ll << 50;
679 } else {
680 product &= ((1ull << 40) - 1);
681 }
682 }
683 return product;
684}
685
686uint64_t HELPER(macmulf)(CPUState *env, uint32_t op1, uint32_t op2)
687{
688 uint64_t product;
689 uint32_t remainder;
690
691 product = (uint64_t)op1 * op2;
692 if (env->macsr & MACSR_RT) {
693 remainder = product & 0xffffff;
694 product >>= 24;
695 if (remainder > 0x800000)
696 product++;
697 else if (remainder == 0x800000)
698 product += (product & 1);
699 } else {
700 product >>= 24;
701 }
702 return product;
703}
704
705void HELPER(macsats)(CPUState *env, uint32_t acc)
706{
707 int64_t tmp;
708 int64_t result;
709 tmp = env->macc[acc];
710 result = ((tmp << 16) >> 16);
711 if (result != tmp) {
712 env->macsr |= MACSR_V;
713 }
714 if (env->macsr & MACSR_V) {
715 env->macsr |= MACSR_PAV0 << acc;
716 if (env->macsr & MACSR_OMC) {
717
718
719
720 result = (result >> 63) ^ 0x7fffffff;
721 }
722 }
723 env->macc[acc] = result;
724}
725
726void HELPER(macsatu)(CPUState *env, uint32_t acc)
727{
728 uint64_t val;
729
730 val = env->macc[acc];
731 if (val & (0xffffull << 48)) {
732 env->macsr |= MACSR_V;
733 }
734 if (env->macsr & MACSR_V) {
735 env->macsr |= MACSR_PAV0 << acc;
736 if (env->macsr & MACSR_OMC) {
737 if (val > (1ull << 53))
738 val = 0;
739 else
740 val = (1ull << 48) - 1;
741 } else {
742 val &= ((1ull << 48) - 1);
743 }
744 }
745 env->macc[acc] = val;
746}
747
748void HELPER(macsatf)(CPUState *env, uint32_t acc)
749{
750 int64_t sum;
751 int64_t result;
752
753 sum = env->macc[acc];
754 result = (sum << 16) >> 16;
755 if (result != sum) {
756 env->macsr |= MACSR_V;
757 }
758 if (env->macsr & MACSR_V) {
759 env->macsr |= MACSR_PAV0 << acc;
760 if (env->macsr & MACSR_OMC) {
761 result = (result >> 63) ^ 0x7fffffffffffll;
762 }
763 }
764 env->macc[acc] = result;
765}
766
767void HELPER(mac_set_flags)(CPUState *env, uint32_t acc)
768{
769 uint64_t val;
770 val = env->macc[acc];
771 if (val == 0) {
772 env->macsr |= MACSR_Z;
773 } else if (val & (1ull << 47)) {
774 env->macsr |= MACSR_N;
775 }
776 if (env->macsr & (MACSR_PAV0 << acc)) {
777 env->macsr |= MACSR_V;
778 }
779 if (env->macsr & MACSR_FI) {
780 val = ((int64_t)val) >> 40;
781 if (val != 0 && val != -1)
782 env->macsr |= MACSR_EV;
783 } else if (env->macsr & MACSR_SU) {
784 val = ((int64_t)val) >> 32;
785 if (val != 0 && val != -1)
786 env->macsr |= MACSR_EV;
787 } else {
788 if ((val >> 32) != 0)
789 env->macsr |= MACSR_EV;
790 }
791}
792
793void HELPER(flush_flags)(CPUState *env, uint32_t cc_op)
794{
795 cpu_m68k_flush_flags(env, cc_op);
796}
797
798uint32_t HELPER(get_macf)(CPUState *env, uint64_t val)
799{
800 int rem;
801 uint32_t result;
802
803 if (env->macsr & MACSR_SU) {
804
805 rem = val & 0xffffff;
806 val = (val >> 24) & 0xffffu;
807 if (rem > 0x800000)
808 val++;
809 else if (rem == 0x800000)
810 val += (val & 1);
811 } else if (env->macsr & MACSR_RT) {
812
813 rem = val & 0xff;
814 val >>= 8;
815 if (rem > 0x80)
816 val++;
817 else if (rem == 0x80)
818 val += (val & 1);
819 } else {
820
821 val >>= 8;
822 }
823 if (env->macsr & MACSR_OMC) {
824
825 if (env->macsr & MACSR_SU) {
826 if (val != (uint16_t) val) {
827 result = ((val >> 63) ^ 0x7fff) & 0xffff;
828 } else {
829 result = val & 0xffff;
830 }
831 } else {
832 if (val != (uint32_t)val) {
833 result = ((uint32_t)(val >> 63) & 0x7fffffff);
834 } else {
835 result = (uint32_t)val;
836 }
837 }
838 } else {
839
840 if (env->macsr & MACSR_SU) {
841 result = val & 0xffff;
842 } else {
843 result = (uint32_t)val;
844 }
845 }
846 return result;
847}
848
849uint32_t HELPER(get_macs)(uint64_t val)
850{
851 if (val == (int32_t)val) {
852 return (int32_t)val;
853 } else {
854 return (val >> 61) ^ ~SIGNBIT;
855 }
856}
857
858uint32_t HELPER(get_macu)(uint64_t val)
859{
860 if ((val >> 32) == 0) {
861 return (uint32_t)val;
862 } else {
863 return 0xffffffffu;
864 }
865}
866
867uint32_t HELPER(get_mac_extf)(CPUState *env, uint32_t acc)
868{
869 uint32_t val;
870 val = env->macc[acc] & 0x00ff;
871 val = (env->macc[acc] >> 32) & 0xff00;
872 val |= (env->macc[acc + 1] << 16) & 0x00ff0000;
873 val |= (env->macc[acc + 1] >> 16) & 0xff000000;
874 return val;
875}
876
877uint32_t HELPER(get_mac_exti)(CPUState *env, uint32_t acc)
878{
879 uint32_t val;
880 val = (env->macc[acc] >> 32) & 0xffff;
881 val |= (env->macc[acc + 1] >> 16) & 0xffff0000;
882 return val;
883}
884
885void HELPER(set_mac_extf)(CPUState *env, uint32_t val, uint32_t acc)
886{
887 int64_t res;
888 int32_t tmp;
889 res = env->macc[acc] & 0xffffffff00ull;
890 tmp = (int16_t)(val & 0xff00);
891 res |= ((int64_t)tmp) << 32;
892 res |= val & 0xff;
893 env->macc[acc] = res;
894 res = env->macc[acc + 1] & 0xffffffff00ull;
895 tmp = (val & 0xff000000);
896 res |= ((int64_t)tmp) << 16;
897 res |= (val >> 16) & 0xff;
898 env->macc[acc + 1] = res;
899}
900
901void HELPER(set_mac_exts)(CPUState *env, uint32_t val, uint32_t acc)
902{
903 int64_t res;
904 int32_t tmp;
905 res = (uint32_t)env->macc[acc];
906 tmp = (int16_t)val;
907 res |= ((int64_t)tmp) << 32;
908 env->macc[acc] = res;
909 res = (uint32_t)env->macc[acc + 1];
910 tmp = val & 0xffff0000;
911 res |= (int64_t)tmp << 16;
912 env->macc[acc + 1] = res;
913}
914
915void HELPER(set_mac_extu)(CPUState *env, uint32_t val, uint32_t acc)
916{
917 uint64_t res;
918 res = (uint32_t)env->macc[acc];
919 res |= ((uint64_t)(val & 0xffff)) << 32;
920 env->macc[acc] = res;
921 res = (uint32_t)env->macc[acc + 1];
922 res |= (uint64_t)(val & 0xffff0000) << 16;
923 env->macc[acc + 1] = res;
924}
925