#define PHYS_RAM_MAX_SIZE (2047 * 1024 * 1024)
#endif
+#ifdef TARGET_PPC
+#define DEFAULT_RAM_SIZE 144
+#else
+#define DEFAULT_RAM_SIZE 32
+#endif
/* in ms */
#define GUI_REFRESH_INTERVAL 30
IOPortWriteFunc *ioport_write_table[3][MAX_IOPORTS];
BlockDriverState *bs_table[MAX_DISKS], *fd_table[MAX_FD];
int vga_ram_size;
+int bios_size;
static DisplayState display_state;
int nographic;
int64_t ticks_per_sec;
int boot_device = 'c';
-static int ram_size;
+int ram_size;
static char network_script[1024];
int pit_min_timer_count = 0;
int nb_nics;
QEMUTimer *gui_timer;
int vm_running;
int audio_enabled = 0;
-int pci_enabled = 0;
+int pci_enabled = 1;
+int prep_enabled = 0;
+int rtc_utc = 1;
+int cirrus_vga_enabled = 0;
+int graphic_width = 640;
+int graphic_height = 480;
+int graphic_depth = 15;
/***********************************************************/
/* x86 ISA bus support */
return buf;
}
+/* return the size or -1 if error */
+int get_image_size(const char *filename)
+{
+ int fd, size;
+ fd = open(filename, O_RDONLY | O_BINARY);
+ if (fd < 0)
+ return -1;
+ size = lseek(fd, 0, SEEK_END);
+ close(fd);
+ return size;
+}
+
/* return the size or -1 if error */
int load_image(const char *filename, uint8_t *addr)
{
abort();
}
+/***********************************************************/
+/* keyboard/mouse */
+
+static QEMUPutKBDEvent *qemu_put_kbd_event;
+static void *qemu_put_kbd_event_opaque;
+static QEMUPutMouseEvent *qemu_put_mouse_event;
+static void *qemu_put_mouse_event_opaque;
+
+void qemu_add_kbd_event_handler(QEMUPutKBDEvent *func, void *opaque)
+{
+ qemu_put_kbd_event_opaque = opaque;
+ qemu_put_kbd_event = func;
+}
+
+void qemu_add_mouse_event_handler(QEMUPutMouseEvent *func, void *opaque)
+{
+ qemu_put_mouse_event_opaque = opaque;
+ qemu_put_mouse_event = func;
+}
+
+void kbd_put_keycode(int keycode)
+{
+ if (qemu_put_kbd_event) {
+ qemu_put_kbd_event(qemu_put_kbd_event_opaque, keycode);
+ }
+}
+
+void kbd_mouse_event(int dx, int dy, int dz, int buttons_state)
+{
+ if (qemu_put_mouse_event) {
+ qemu_put_mouse_event(qemu_put_mouse_event_opaque,
+ dx, dy, dz, buttons_state);
+ }
+}
+
/***********************************************************/
/* timers */
#ifndef _WIN32
+#if defined(__linux__)
+
#define RTC_FREQ 1024
static int rtc_fd;
-
+
static int start_rtc_timer(void)
{
rtc_fd = open("/dev/rtc", O_RDONLY);
return 0;
}
-#endif
+#else
+
+static int start_rtc_timer(void)
+{
+ return -1;
+}
+
+#endif /* !defined(__linux__) */
+
+#endif /* !defined(_WIN32) */
static void init_timers(void)
{
/* use console for serial port */
return 0;
} else {
+#if 0
+ /* Not satisfying */
if (openpty(&master_fd, &slave_fd, slave_name, NULL, NULL) < 0) {
fprintf(stderr, "warning: could not create pseudo terminal for serial port\n");
return -1;
}
fprintf(stderr, "Serial port redirected to %s\n", slave_name);
return master_fd;
+#else
+ return -1;
+#endif
}
}
}
}
+/* reset/shutdown handler */
+
+typedef struct QEMUResetEntry {
+ QEMUResetHandler *func;
+ void *opaque;
+ struct QEMUResetEntry *next;
+} QEMUResetEntry;
+
+static QEMUResetEntry *first_reset_entry;
+static int reset_requested;
+static int shutdown_requested;
+
+void qemu_register_reset(QEMUResetHandler *func, void *opaque)
+{
+ QEMUResetEntry **pre, *re;
+
+ pre = &first_reset_entry;
+ while (*pre != NULL)
+ pre = &(*pre)->next;
+ re = qemu_mallocz(sizeof(QEMUResetEntry));
+ re->func = func;
+ re->opaque = opaque;
+ re->next = NULL;
+ *pre = re;
+}
+
+void qemu_system_reset(void)
+{
+ QEMUResetEntry *re;
+
+ /* reset all devices */
+ for(re = first_reset_entry; re != NULL; re = re->next) {
+ re->func(re->opaque);
+ }
+}
+
+void qemu_system_reset_request(void)
+{
+ reset_requested = 1;
+ cpu_interrupt(cpu_single_env, CPU_INTERRUPT_EXIT);
+}
+
+void qemu_system_shutdown_request(void)
+{
+ shutdown_requested = 1;
+ cpu_interrupt(cpu_single_env, CPU_INTERRUPT_EXIT);
+}
+
+static void main_cpu_reset(void *opaque)
+{
+#ifdef TARGET_I386
+ CPUState *env = opaque;
+ cpu_reset(env);
+#endif
+}
+
int main_loop(void)
{
#ifndef _WIN32
for(;;) {
if (vm_running) {
ret = cpu_exec(env);
- if (reset_requested) {
+ if (shutdown_requested) {
ret = EXCP_INTERRUPT;
break;
}
+ if (reset_requested) {
+ reset_requested = 0;
+ qemu_system_reset();
+ ret = EXCP_INTERRUPT;
+ }
if (ret == EXCP_DEBUG) {
vm_stop(EXCP_DEBUG);
}
"-cdrom file use 'file' as IDE cdrom image (cdrom is ide1 master)\n"
"-boot [a|b|c|d] boot on floppy (a, b), hard disk (c) or CD-ROM (d)\n"
"-snapshot write to temporary files instead of disk image files\n"
- "-m megs set virtual RAM size to megs MB\n"
+ "-m megs set virtual RAM size to megs MB [default=%d]\n"
"-nographic disable graphical output and redirect serial I/Os to console\n"
"-enable-audio enable audio support\n"
+ "-localtime set the real time clock to local time [default=utc]\n"
+#ifdef TARGET_PPC
+ "-prep Simulate a PREP system (default is PowerMAC)\n"
+ "-g WxH[xDEPTH] Set the initial VGA graphic mode\n"
+#endif
"\n"
"Network options:\n"
"-nics n simulate 'n' network cards [default=1]\n"
#ifdef USE_CODE_COPY
"-no-code-copy disable code copy acceleration\n"
#endif
-
+#ifdef TARGET_I386
+ "-isa simulate an ISA-only system (default is PCI system)\n"
+#endif
"\n"
"During emulation, use C-a h to get terminal commands:\n",
#ifdef CONFIG_SOFTMMU
#else
"qemu-fast",
#endif
- DEFAULT_NETWORK_SCRIPT,
+ DEFAULT_RAM_SIZE,
+ DEFAULT_NETWORK_SCRIPT,
DEFAULT_GDBSTUB_PORT,
"/tmp/qemu.log");
term_print_help();
QEMU_OPTION_L,
QEMU_OPTION_no_code_copy,
QEMU_OPTION_pci,
+ QEMU_OPTION_isa,
+ QEMU_OPTION_prep,
+ QEMU_OPTION_localtime,
+ QEMU_OPTION_cirrusvga,
+ QEMU_OPTION_g,
};
typedef struct QEMUOption {
{ "hdachs", HAS_ARG, QEMU_OPTION_hdachs },
{ "L", HAS_ARG, QEMU_OPTION_L },
{ "no-code-copy", 0, QEMU_OPTION_no_code_copy },
+#ifdef TARGET_PPC
+ { "prep", 0, QEMU_OPTION_prep },
+ { "g", 1, QEMU_OPTION_g },
+#endif
+ { "localtime", 0, QEMU_OPTION_localtime },
+ { "isa", 0, QEMU_OPTION_isa },
+
+ /* temporary options */
{ "pci", 0, QEMU_OPTION_pci },
+ { "cirrusvga", 0, QEMU_OPTION_cirrusvga },
{ NULL },
};
fd_filename[i] = NULL;
for(i = 0; i < MAX_DISKS; i++)
hd_filename[i] = NULL;
- ram_size = 32 * 1024 * 1024;
+ ram_size = DEFAULT_RAM_SIZE * 1024 * 1024;
vga_ram_size = VGA_RAM_SIZE;
+ bios_size = BIOS_SIZE;
pstrcpy(network_script, sizeof(network_script), DEFAULT_NETWORK_SCRIPT);
#ifdef CONFIG_GDBSTUB
use_gdbstub = 0;
case QEMU_OPTION_pci:
pci_enabled = 1;
break;
+ case QEMU_OPTION_isa:
+ pci_enabled = 0;
+ break;
+ case QEMU_OPTION_prep:
+ prep_enabled = 1;
+ break;
+ case QEMU_OPTION_localtime:
+ rtc_utc = 0;
+ break;
+ case QEMU_OPTION_cirrusvga:
+ cirrus_vga_enabled = 1;
+ break;
+ case QEMU_OPTION_g:
+ {
+ const char *p;
+ int w, h, depth;
+ p = optarg;
+ w = strtol(p, (char **)&p, 10);
+ if (w <= 0) {
+ graphic_error:
+ fprintf(stderr, "qemu: invalid resolution or depth\n");
+ exit(1);
+ }
+ if (*p != 'x')
+ goto graphic_error;
+ p++;
+ h = strtol(p, (char **)&p, 10);
+ if (h <= 0)
+ goto graphic_error;
+ if (*p == 'x') {
+ p++;
+ depth = strtol(p, (char **)&p, 10);
+ if (depth != 8 && depth != 15 && depth != 16 &&
+ depth != 24 && depth != 32)
+ goto graphic_error;
+ } else if (*p == '\0') {
+ depth = graphic_depth;
+ } else {
+ goto graphic_error;
+ }
+
+ graphic_width = w;
+ graphic_height = h;
+ graphic_depth = depth;
+ }
+ break;
}
}
}
}
/* init the memory */
- phys_ram_size = ram_size + vga_ram_size;
+ phys_ram_size = ram_size + vga_ram_size + bios_size;
#ifdef CONFIG_SOFTMMU
#ifdef _BSD
register_savevm("timer", 0, 1, timer_save, timer_load, env);
register_savevm("cpu", 0, 1, cpu_save, cpu_load, env);
register_savevm("ram", 0, 1, ram_save, ram_load, NULL);
+ qemu_register_reset(main_cpu_reset, global_env);
init_ioports();
cpu_calibrate_ticks();