/[gxemul]/trunk/src/cpu.c
This is repository of my old source code which isn't updated any more. Go to git.rot13.org for current projects!
ViewVC logotype

Annotation of /trunk/src/cpu.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 26 - (hide annotations)
Mon Oct 8 16:20:10 2007 UTC (16 years, 5 months ago) by dpavlin
File MIME type: text/plain
File size: 16702 byte(s)
++ trunk/HISTORY	(local)
$Id: HISTORY,v 1.1264 2006/06/25 11:08:04 debug Exp $
20060624	Replacing the error-prone machine type initialization stuff
		with something more reasonable.
		Finally removing the old "cpu_run" kludge; moving around stuff
		in machine.c and emul.c to better suit the dyntrans system.
		Various minor dyntrans cleanups (renaming translate_address to
		translate_v2p, and experimenting with template physpages).
20060625	Removing the speed hack which separated the vph entries into
		two halves (code vs data); things seem a lot more stable now.
		Minor performance hack: R2000/R3000 cache isolation now only
		clears address translations when going into isolation, not
		when going out of it.
		Fixing the MIPS interrupt problems by letting mtc0 immediately
		cause interrupts.

==============  RELEASE 0.4.0.1  ==============


1 dpavlin 2 /*
2 dpavlin 22 * Copyright (C) 2005-2006 Anders Gavare. All rights reserved.
3 dpavlin 2 *
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 dpavlin 26 * $Id: cpu.c,v 1.344 2006/06/24 21:47:22 debug Exp $
29 dpavlin 2 *
30     * Common routines for CPU emulation. (Not specific to any CPU type.)
31     */
32    
33     #include <stdio.h>
34     #include <stdlib.h>
35     #include <sys/types.h>
36 dpavlin 22 #include <sys/mman.h>
37 dpavlin 2 #include <string.h>
38    
39     #include "cpu.h"
40     #include "machine.h"
41 dpavlin 12 #include "memory.h"
42 dpavlin 2 #include "misc.h"
43    
44    
45     extern int quiet_mode;
46    
47     static struct cpu_family *first_cpu_family = NULL;
48    
49    
50     /*
51     * cpu_new():
52     *
53     * Create a new cpu object. Each family is tried in sequence until a
54     * CPU family recognizes the cpu_type_name.
55     */
56     struct cpu *cpu_new(struct memory *mem, struct machine *machine,
57     int cpu_id, char *name)
58     {
59 dpavlin 10 struct cpu *cpu;
60 dpavlin 2 struct cpu_family *fp;
61     char *cpu_type_name;
62    
63     if (name == NULL) {
64     fprintf(stderr, "cpu_new(): cpu name = NULL?\n");
65     exit(1);
66     }
67    
68     cpu_type_name = strdup(name);
69     if (cpu_type_name == NULL) {
70     fprintf(stderr, "cpu_new(): out of memory\n");
71     exit(1);
72     }
73    
74 dpavlin 12 cpu = zeroed_alloc(sizeof(struct cpu));
75 dpavlin 10
76     cpu->memory_rw = NULL;
77     cpu->name = cpu_type_name;
78     cpu->mem = mem;
79     cpu->machine = machine;
80     cpu->cpu_id = cpu_id;
81     cpu->byte_order = EMUL_LITTLE_ENDIAN;
82     cpu->bootstrap_cpu_flag = 0;
83     cpu->running = 0;
84    
85 dpavlin 12 cpu_create_or_reset_tc(cpu);
86    
87 dpavlin 2 fp = first_cpu_family;
88    
89     while (fp != NULL) {
90     if (fp->cpu_new != NULL) {
91 dpavlin 10 if (fp->cpu_new(cpu, mem, machine, cpu_id,
92     cpu_type_name)) {
93     /* Sanity check: */
94     if (cpu->memory_rw == NULL) {
95     fatal("\ncpu_new(): memory_rw == "
96     "NULL\n");
97 dpavlin 2 exit(1);
98     }
99 dpavlin 26 break;
100 dpavlin 2 }
101     }
102    
103     fp = fp->next;
104     }
105    
106 dpavlin 26 if (fp == NULL) {
107     fatal("\ncpu_new(): unknown cpu type '%s'\n", cpu_type_name);
108     return NULL;
109     }
110    
111     fp->init_tables(cpu);
112    
113     return cpu;
114 dpavlin 2 }
115    
116    
117     /*
118     * cpu_tlbdump():
119     *
120     * Called from the debugger to dump the TLB in a readable format.
121     * x is the cpu number to dump, or -1 to dump all CPUs.
122     *
123     * If rawflag is nonzero, then the TLB contents isn't formated nicely,
124     * just dumped.
125     */
126     void cpu_tlbdump(struct machine *m, int x, int rawflag)
127     {
128     if (m->cpu_family == NULL || m->cpu_family->tlbdump == NULL)
129     fatal("cpu_tlbdump(): NULL\n");
130     else
131     m->cpu_family->tlbdump(m, x, rawflag);
132     }
133    
134    
135     /*
136     * cpu_register_match():
137     *
138     * Used by the debugger.
139     */
140     void cpu_register_match(struct machine *m, char *name,
141     int writeflag, uint64_t *valuep, int *match_register)
142     {
143     if (m->cpu_family == NULL || m->cpu_family->register_match == NULL)
144     fatal("cpu_register_match(): NULL\n");
145     else
146     m->cpu_family->register_match(m, name, writeflag,
147     valuep, match_register);
148     }
149    
150    
151     /*
152     * cpu_disassemble_instr():
153     *
154     * Convert an instruction word into human readable format, for instruction
155     * tracing.
156     */
157     int cpu_disassemble_instr(struct machine *m, struct cpu *cpu,
158 dpavlin 24 unsigned char *instr, int running, uint64_t addr)
159 dpavlin 2 {
160     if (m->cpu_family == NULL || m->cpu_family->disassemble_instr == NULL) {
161     fatal("cpu_disassemble_instr(): NULL\n");
162     return 0;
163     } else
164     return m->cpu_family->disassemble_instr(cpu, instr,
165 dpavlin 24 running, addr);
166 dpavlin 2 }
167    
168    
169     /*
170     * cpu_register_dump():
171     *
172     * Dump cpu registers in a relatively readable format.
173     *
174 dpavlin 18 * gprs: set to non-zero to dump GPRs. (CPU dependent.)
175     * coprocs: set bit 0..x to dump registers in coproc 0..x. (CPU dependent.)
176 dpavlin 2 */
177     void cpu_register_dump(struct machine *m, struct cpu *cpu,
178     int gprs, int coprocs)
179     {
180     if (m->cpu_family == NULL || m->cpu_family->register_dump == NULL)
181     fatal("cpu_register_dump(): NULL\n");
182     else
183     m->cpu_family->register_dump(cpu, gprs, coprocs);
184     }
185    
186    
187     /*
188 dpavlin 24 * cpu_gdb_stub():
189     *
190     * Execute a "remote GDB" command. Return value is a pointer to a newly
191     * allocated response string, if the command was successfully executed. If
192     * there was an error, NULL is returned.
193     */
194     char *cpu_gdb_stub(struct cpu *cpu, char *cmd)
195     {
196     if (cpu->machine->cpu_family == NULL ||
197     cpu->machine->cpu_family->gdb_stub == NULL) {
198     fatal("cpu_gdb_stub(): NULL\n");
199     return NULL;
200     } else
201     return cpu->machine->cpu_family->gdb_stub(cpu, cmd);
202     }
203    
204    
205     /*
206 dpavlin 2 * cpu_interrupt():
207     *
208     * Assert an interrupt.
209     * Return value is 1 if the interrupt was asserted, 0 otherwise.
210     */
211     int cpu_interrupt(struct cpu *cpu, uint64_t irq_nr)
212     {
213     if (cpu->machine->cpu_family == NULL ||
214     cpu->machine->cpu_family->interrupt == NULL) {
215     fatal("cpu_interrupt(): NULL\n");
216     return 0;
217     } else
218     return cpu->machine->cpu_family->interrupt(cpu, irq_nr);
219     }
220    
221    
222     /*
223     * cpu_interrupt_ack():
224     *
225     * Acknowledge an interrupt.
226     * Return value is 1 if the interrupt was deasserted, 0 otherwise.
227     */
228     int cpu_interrupt_ack(struct cpu *cpu, uint64_t irq_nr)
229     {
230     if (cpu->machine->cpu_family == NULL ||
231     cpu->machine->cpu_family->interrupt_ack == NULL) {
232     /* debug("cpu_interrupt_ack(): NULL\n"); */
233     return 0;
234     } else
235     return cpu->machine->cpu_family->interrupt_ack(cpu, irq_nr);
236     }
237    
238    
239     /*
240 dpavlin 12 * cpu_functioncall_trace():
241     *
242     * This function should be called if machine->show_trace_tree is enabled, and
243     * a function call is being made. f contains the address of the function.
244     */
245     void cpu_functioncall_trace(struct cpu *cpu, uint64_t f)
246     {
247     int i, n_args = -1;
248     char *symbol;
249     uint64_t offset;
250    
251     if (cpu->machine->ncpus > 1)
252     fatal("cpu%i:\t", cpu->cpu_id);
253    
254     cpu->trace_tree_depth ++;
255 dpavlin 14 if (cpu->trace_tree_depth > 100)
256     cpu->trace_tree_depth = 100;
257 dpavlin 12 for (i=0; i<cpu->trace_tree_depth; i++)
258     fatal(" ");
259    
260     fatal("<");
261     symbol = get_symbol_name_and_n_args(&cpu->machine->symbol_context,
262     f, &offset, &n_args);
263     if (symbol != NULL)
264     fatal("%s", symbol);
265     else {
266     if (cpu->is_32bit)
267 dpavlin 24 fatal("0x%"PRIx32, (uint32_t) f);
268 dpavlin 12 else
269 dpavlin 24 fatal("0x%"PRIx64, (uint64_t) f);
270 dpavlin 12 }
271     fatal("(");
272    
273     if (cpu->machine->cpu_family->functioncall_trace != NULL)
274     cpu->machine->cpu_family->functioncall_trace(cpu, f, n_args);
275    
276     fatal(")>\n");
277 dpavlin 24
278     #ifdef PRINT_MEMORY_CHECKSUM
279     /* Temporary hack for finding bugs: */
280     fatal("call chksum=%016"PRIx64"\n", memory_checksum(cpu->mem));
281     #endif
282 dpavlin 12 }
283    
284    
285     /*
286     * cpu_functioncall_trace_return():
287     *
288     * This function should be called if machine->show_trace_tree is enabled, and
289     * a function is being returned from.
290     *
291     * TODO: Print return value? This could be implemented similar to the
292     * cpu->functioncall_trace function call above.
293     */
294     void cpu_functioncall_trace_return(struct cpu *cpu)
295     {
296     cpu->trace_tree_depth --;
297     if (cpu->trace_tree_depth < 0)
298     cpu->trace_tree_depth = 0;
299     }
300    
301    
302     /*
303     * cpu_create_or_reset_tc():
304     *
305     * Create the translation cache in memory (ie allocate memory for it), if
306     * necessary, and then reset it to an initial state.
307     */
308     void cpu_create_or_reset_tc(struct cpu *cpu)
309     {
310 dpavlin 22 size_t s = DYNTRANS_CACHE_SIZE + DYNTRANS_CACHE_MARGIN;
311 dpavlin 12
312 dpavlin 24 if (cpu->translation_cache == NULL)
313     cpu->translation_cache = zeroed_alloc(s);
314 dpavlin 22
315 dpavlin 12 /* Create an empty table at the beginning of the translation cache: */
316     memset(cpu->translation_cache, 0, sizeof(uint32_t)
317     * N_BASE_TABLE_ENTRIES);
318    
319     cpu->translation_cache_cur_ofs =
320     N_BASE_TABLE_ENTRIES * sizeof(uint32_t);
321    
322     /*
323     * There might be other translation pointers that still point to
324     * within the translation_cache region. Let's invalidate those too:
325     */
326 dpavlin 14 if (cpu->invalidate_code_translation != NULL)
327     cpu->invalidate_code_translation(cpu, 0, INVALIDATE_ALL);
328 dpavlin 12 }
329    
330    
331     /*
332 dpavlin 2 * cpu_dumpinfo():
333     *
334     * Dumps info about a CPU using debug(). "cpu0: CPUNAME, running" (or similar)
335 dpavlin 18 * is outputed, and it is up to CPU dependent code to complete the line.
336 dpavlin 2 */
337     void cpu_dumpinfo(struct machine *m, struct cpu *cpu)
338     {
339     debug("cpu%i: %s, %s", cpu->cpu_id, cpu->name,
340     cpu->running? "running" : "stopped");
341    
342     if (m->cpu_family == NULL || m->cpu_family->dumpinfo == NULL)
343     fatal("cpu_dumpinfo(): NULL\n");
344     else
345     m->cpu_family->dumpinfo(cpu);
346     }
347    
348    
349     /*
350     * cpu_list_available_types():
351     *
352     * Print a list of available CPU types for each cpu family.
353     */
354     void cpu_list_available_types(void)
355     {
356     struct cpu_family *fp;
357 dpavlin 22 int iadd = DEBUG_INDENTATION;
358 dpavlin 2
359     fp = first_cpu_family;
360    
361     if (fp == NULL) {
362     debug("No CPUs defined!\n");
363     return;
364     }
365    
366     while (fp != NULL) {
367     debug("%s:\n", fp->name);
368     debug_indentation(iadd);
369     if (fp->list_available_types != NULL)
370     fp->list_available_types();
371     else
372     debug("(internal error: list_available_types"
373     " = NULL)\n");
374     debug_indentation(-iadd);
375    
376     fp = fp->next;
377     }
378     }
379    
380    
381     /*
382     * cpu_run_deinit():
383     *
384     * Shuts down all CPUs in a machine when ending a simulation. (This function
385     * should only need to be called once for each machine.)
386     */
387 dpavlin 12 void cpu_run_deinit(struct machine *machine)
388 dpavlin 2 {
389     int te;
390    
391     /*
392     * Two last ticks of every hardware device. This will allow
393     * framebuffers to draw the last updates to the screen before
394     * halting.
395     */
396     for (te=0; te<machine->n_tick_entries; te++) {
397     machine->tick_func[te](machine->cpus[0],
398     machine->tick_extra[te]);
399     machine->tick_func[te](machine->cpus[0],
400     machine->tick_extra[te]);
401     }
402    
403     debug("cpu_run_deinit(): All CPUs halted.\n");
404    
405     if (machine->show_nr_of_instructions || !quiet_mode)
406 dpavlin 10 cpu_show_cycles(machine, 1);
407 dpavlin 2
408     fflush(stdout);
409     }
410    
411    
412     /*
413     * cpu_show_cycles():
414     *
415     * If automatic adjustment of clock interrupts is turned on, then recalculate
416     * emulated_hz. Also, if show_nr_of_instructions is on, then print a
417     * line to stdout about how many instructions/cycles have been executed so
418     * far.
419     */
420 dpavlin 10 void cpu_show_cycles(struct machine *machine, int forced)
421 dpavlin 2 {
422     uint64_t offset, pc;
423     char *symbol;
424 dpavlin 12 int64_t mseconds, ninstrs, is, avg;
425 dpavlin 2 struct timeval tv;
426 dpavlin 24 int h, m, s, ms, d;
427 dpavlin 2
428     static int64_t mseconds_last = 0;
429     static int64_t ninstrs_last = -1;
430    
431     pc = machine->cpus[machine->bootstrap_cpu]->pc;
432    
433     gettimeofday(&tv, NULL);
434 dpavlin 10 mseconds = (tv.tv_sec - machine->starttime.tv_sec) * 1000
435     + (tv.tv_usec - machine->starttime.tv_usec) / 1000;
436 dpavlin 2
437     if (mseconds == 0)
438     mseconds = 1;
439    
440     if (mseconds - mseconds_last == 0)
441     mseconds ++;
442    
443 dpavlin 24 ninstrs = machine->ncycles_since_gettimeofday;
444 dpavlin 2
445     if (machine->automatic_clock_adjustment) {
446     static int first_adjustment = 1;
447    
448     /* Current nr of cycles per second: */
449     int64_t cur_cycles_per_second = 1000 *
450 dpavlin 24 (ninstrs-ninstrs_last) / (mseconds-mseconds_last);
451 dpavlin 2
452 dpavlin 24 /* fatal("[ CYCLES PER SECOND = %"PRIi64" ]\n",
453     cur_cycles_per_second); */
454    
455 dpavlin 2 if (cur_cycles_per_second < 1000000)
456     cur_cycles_per_second = 1000000;
457    
458     if (first_adjustment) {
459     machine->emulated_hz = cur_cycles_per_second;
460     first_adjustment = 0;
461     } else {
462     machine->emulated_hz = (15 * machine->emulated_hz +
463     cur_cycles_per_second) / 16;
464     }
465    
466 dpavlin 24 /* fatal("[ updating emulated_hz to %"PRIi64" Hz ]\n",
467     machine->emulated_hz); */
468 dpavlin 2 }
469    
470    
471     /* RETURN here, unless show_nr_of_instructions (-N) is turned on: */
472     if (!machine->show_nr_of_instructions && !forced)
473     goto do_return;
474    
475 dpavlin 24 printf("[ %"PRIi64" instrs", (int64_t)machine->ncycles);
476 dpavlin 2
477     if (!machine->automatic_clock_adjustment) {
478     d = machine->emulated_hz / 1000;
479     if (d < 1)
480     d = 1;
481 dpavlin 10 ms = machine->ncycles / d;
482 dpavlin 2 h = ms / 3600000;
483     ms -= 3600000 * h;
484     m = ms / 60000;
485     ms -= 60000 * m;
486     s = ms / 1000;
487     ms -= 1000 * s;
488    
489 dpavlin 22 printf(", emulated time = %02i:%02i:%02i.%03i; ", h, m, s, ms);
490 dpavlin 2 }
491    
492     /* Instructions per second, and average so far: */
493 dpavlin 12 is = 1000 * (ninstrs-ninstrs_last) / (mseconds-mseconds_last);
494     avg = (long long)1000 * ninstrs / mseconds;
495     if (is < 0)
496     is = 0;
497     if (avg < 0)
498     avg = 0;
499 dpavlin 24 printf("; i/s=%"PRIi64" avg=%"PRIi64, is, avg);
500 dpavlin 2
501     symbol = get_symbol_name(&machine->symbol_context, pc, &offset);
502    
503 dpavlin 12 if (machine->ncpus == 1) {
504     if (machine->cpus[machine->bootstrap_cpu]->is_32bit)
505 dpavlin 24 printf("; pc=0x%08"PRIx32, (uint32_t) pc);
506 dpavlin 12 else
507 dpavlin 24 printf("; pc=0x%016"PRIx64, (uint64_t) pc);
508 dpavlin 12 }
509 dpavlin 2
510 dpavlin 10 if (symbol != NULL)
511     printf(" <%s>", symbol);
512     printf(" ]\n");
513 dpavlin 2
514     do_return:
515     ninstrs_last = ninstrs;
516     mseconds_last = mseconds;
517     }
518    
519    
520     /*
521     * cpu_run_init():
522     *
523     * Prepare to run instructions on all CPUs in this machine. (This function
524     * should only need to be called once for each machine.)
525     */
526 dpavlin 12 void cpu_run_init(struct machine *machine)
527 dpavlin 2 {
528     int ncpus = machine->ncpus;
529     int te;
530    
531     machine->a_few_cycles = 1048576;
532     machine->ncycles_flush = 0;
533     machine->ncycles = 0;
534     machine->ncycles_show = 0;
535    
536     /*
537     * Instead of doing { one cycle, check hardware ticks }, we
538     * can do { n cycles, check hardware ticks }, as long as
539     * n is at most as much as the lowest number of cycles/tick
540     * for any hardware device.
541     */
542     for (te=0; te<machine->n_tick_entries; te++) {
543     if (machine->ticks_reset_value[te] < machine->a_few_cycles)
544     machine->a_few_cycles = machine->ticks_reset_value[te];
545     }
546    
547     machine->a_few_cycles >>= 1;
548     if (machine->a_few_cycles < 1)
549     machine->a_few_cycles = 1;
550    
551 dpavlin 24 if (ncpus > 1)
552 dpavlin 2 machine->a_few_cycles = 1;
553    
554     /* debug("cpu_run_init(): a_few_cycles = %i\n",
555     machine->a_few_cycles); */
556    
557     /* For performance measurement: */
558     gettimeofday(&machine->starttime, NULL);
559 dpavlin 10 machine->ncycles_since_gettimeofday = 0;
560 dpavlin 2 }
561    
562    
563     /*
564     * add_cpu_family():
565     *
566     * Allocates a cpu_family struct and calls an init function for the
567     * family to fill in reasonable data and pointers.
568     */
569     static void add_cpu_family(int (*family_init)(struct cpu_family *), int arch)
570     {
571     struct cpu_family *fp, *tmp;
572     int res;
573    
574     fp = malloc(sizeof(struct cpu_family));
575     if (fp == NULL) {
576     fprintf(stderr, "add_cpu_family(): out of memory\n");
577     exit(1);
578     }
579     memset(fp, 0, sizeof(struct cpu_family));
580    
581     /*
582     * family_init() returns 1 if the struct has been filled with
583     * valid data, 0 if suppor for the cpu family isn't compiled
584     * into the emulator.
585     */
586     res = family_init(fp);
587     if (!res) {
588     free(fp);
589     return;
590     }
591     fp->arch = arch;
592     fp->next = NULL;
593    
594     /* Add last in family chain: */
595     tmp = first_cpu_family;
596     if (tmp == NULL) {
597     first_cpu_family = fp;
598     } else {
599     while (tmp->next != NULL)
600     tmp = tmp->next;
601     tmp->next = fp;
602     }
603     }
604    
605    
606     /*
607     * cpu_family_ptr_by_number():
608     *
609     * Returns a pointer to a CPU family based on the ARCH_* integers.
610     */
611     struct cpu_family *cpu_family_ptr_by_number(int arch)
612     {
613     struct cpu_family *fp;
614     fp = first_cpu_family;
615    
616     /* YUCK! This is too hardcoded! TODO */
617    
618     while (fp != NULL) {
619     if (arch == fp->arch)
620     return fp;
621     fp = fp->next;
622     }
623    
624     return NULL;
625     }
626    
627    
628     /*
629     * cpu_init():
630     *
631     * Should be called before any other cpu_*() function.
632     */
633     void cpu_init(void)
634     {
635     /* Note: These are registered in alphabetic order. */
636 dpavlin 12
637     #ifdef ENABLE_ALPHA
638     add_cpu_family(alpha_cpu_family_init, ARCH_ALPHA);
639     #endif
640    
641     #ifdef ENABLE_ARM
642 dpavlin 6 add_cpu_family(arm_cpu_family_init, ARCH_ARM);
643 dpavlin 12 #endif
644    
645 dpavlin 14 #ifdef ENABLE_AVR
646     add_cpu_family(avr_cpu_family_init, ARCH_AVR);
647     #endif
648    
649     #ifdef ENABLE_HPPA
650     add_cpu_family(hppa_cpu_family_init, ARCH_HPPA);
651     #endif
652    
653     #ifdef ENABLE_I960
654     add_cpu_family(i960_cpu_family_init, ARCH_I960);
655     #endif
656    
657 dpavlin 12 #ifdef ENABLE_IA64
658     add_cpu_family(ia64_cpu_family_init, ARCH_IA64);
659     #endif
660    
661     #ifdef ENABLE_M68K
662     add_cpu_family(m68k_cpu_family_init, ARCH_M68K);
663     #endif
664    
665     #ifdef ENABLE_MIPS
666 dpavlin 2 add_cpu_family(mips_cpu_family_init, ARCH_MIPS);
667 dpavlin 12 #endif
668    
669     #ifdef ENABLE_PPC
670 dpavlin 2 add_cpu_family(ppc_cpu_family_init, ARCH_PPC);
671 dpavlin 12 #endif
672    
673 dpavlin 14 #ifdef ENABLE_SH
674     add_cpu_family(sh_cpu_family_init, ARCH_SH);
675     #endif
676    
677 dpavlin 12 #ifdef ENABLE_SPARC
678     add_cpu_family(sparc_cpu_family_init, ARCH_SPARC);
679     #endif
680    
681     #ifdef ENABLE_X86
682 dpavlin 4 add_cpu_family(x86_cpu_family_init, ARCH_X86);
683 dpavlin 12 #endif
684 dpavlin 2 }
685    

  ViewVC Help
Powered by ViewVC 1.1.26