blob: cb32eb2887601f79c82f3c9b0b888baeb2836db0 [file] [log] [blame]
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07001/*
2 * QEMU System Emulator
3 *
4 * Copyright (c) 2003-2008 Fabrice Bellard
5 *
6 * Permission is hereby granted, free of charge, to any person obtaining a copy
7 * of this software and associated documentation files (the "Software"), to deal
8 * in the Software without restriction, including without limitation the rights
9 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10 * copies of the Software, and to permit persons to whom the Software is
11 * furnished to do so, subject to the following conditions:
12 *
13 * The above copyright notice and this permission notice shall be included in
14 * all copies or substantial portions of the Software.
15 *
16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
19 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
22 * THE SOFTWARE.
23 */
24
25/* the following is needed on Linux to define ptsname() in stdlib.h */
26#if defined(__linux__)
27#define _GNU_SOURCE 1
28#endif
29
30#include "qemu-common.h"
31#include "hw/hw.h"
32#include "hw/boards.h"
33#include "hw/usb.h"
34#include "hw/pcmcia.h"
35#include "hw/pc.h"
36#include "hw/audiodev.h"
37#include "hw/isa.h"
38#include "hw/baum.h"
39#include "hw/goldfish_nand.h"
40#include "net.h"
41#include "console.h"
42#include "sysemu.h"
43#include "gdbstub.h"
44#include "qemu-timer.h"
45#include "qemu-char.h"
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +010046#include "blockdev.h"
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -070047#include "audio/audio.h"
48
49#include "qemu_file.h"
50#include "android/android.h"
51#include "charpipe.h"
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -070052#include "modem_driver.h"
53#include "android/gps.h"
54#include "android/hw-qemud.h"
55#include "android/hw-kmsg.h"
Vladimir Chtchetkineeb838252010-07-15 12:27:56 -070056#include "android/charmap.h"
Vladimir Chtchetkine074d1f92010-08-06 09:29:50 -070057#include "android/globals.h"
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -070058#include "android/utils/bufprint.h"
David 'Digit' Turner5f824112011-03-01 14:00:26 +010059#include "android/utils/debug.h"
David 'Digit' Turner48a3c662011-03-01 14:03:20 +010060#include "android/utils/filelock.h"
61#include "android/utils/path.h"
David 'Digit' Turner5f824112011-03-01 14:00:26 +010062#include "android/utils/stralloc.h"
David 'Digit' Turner40841b22011-03-01 14:04:00 +010063#include "android/utils/tempfile.h"
Vladimir Chtchetkine72d83df2010-12-14 09:24:02 -080064#include "android/display-core.h"
Vladimir Chtchetkine90c62352011-01-13 11:24:07 -080065#include "android/utils/timezone.h"
David 'Digit' Turnerbdb6f2d2011-02-23 15:57:25 +010066#include "android/snapshot.h"
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -070067#include "targphys.h"
Vladimir Chtchetkine318f17a2010-08-27 09:09:45 -070068#include "tcpdump.h"
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -070069
Vladimir Chtchetkineb5365f32010-08-09 13:33:57 -070070#ifdef CONFIG_MEMCHECK
71#include "memcheck/memcheck.h"
72#endif // CONFIG_MEMCHECK
73
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -070074#include <unistd.h>
75#include <fcntl.h>
76#include <signal.h>
77#include <time.h>
78#include <errno.h>
79#include <sys/time.h>
80#include <zlib.h>
81
David 'Digit' Turner2c538c82010-05-10 16:48:20 -070082/* Needed early for CONFIG_BSD etc. */
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -070083#include "config-host.h"
84
85#ifndef _WIN32
86#include <libgen.h>
87#include <pwd.h>
88#include <sys/times.h>
89#include <sys/wait.h>
90#include <termios.h>
91#include <sys/mman.h>
92#include <sys/ioctl.h>
93#include <sys/resource.h>
94#include <sys/socket.h>
95#include <netinet/in.h>
96#include <net/if.h>
97#if defined(__NetBSD__)
98#include <net/if_tap.h>
99#endif
100#ifdef __linux__
101#include <linux/if_tun.h>
102#endif
103#include <arpa/inet.h>
104#include <dirent.h>
105#include <netdb.h>
106#include <sys/select.h>
David 'Digit' Turner2c538c82010-05-10 16:48:20 -0700107#ifdef CONFIG_BSD
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700108#include <sys/stat.h>
109#if defined(__FreeBSD__) || defined(__DragonFly__)
110#include <libutil.h>
111#else
112#include <util.h>
113#endif
114#elif defined (__GLIBC__) && defined (__FreeBSD_kernel__)
115#include <freebsd/stdlib.h>
116#else
117#ifdef __linux__
118#include <pty.h>
119#include <malloc.h>
120#include <linux/rtc.h>
121
122/* For the benefit of older linux systems which don't supply it,
123 we use a local copy of hpet.h. */
124/* #include <linux/hpet.h> */
125#include "hpet.h"
126
127#include <linux/ppdev.h>
128#include <linux/parport.h>
129#endif
130#ifdef __sun__
131#include <sys/stat.h>
132#include <sys/ethernet.h>
133#include <sys/sockio.h>
134#include <netinet/arp.h>
135#include <netinet/in.h>
136#include <netinet/in_systm.h>
137#include <netinet/ip.h>
138#include <netinet/ip_icmp.h> // must come after ip.h
139#include <netinet/udp.h>
140#include <netinet/tcp.h>
141#include <net/if.h>
142#include <syslog.h>
143#include <stropts.h>
144#endif
145#endif
146#endif
147
148#if defined(__OpenBSD__)
149#include <util.h>
150#endif
151
152#if defined(CONFIG_VDE)
153#include <libvdeplug.h>
154#endif
155
156#ifdef _WIN32
157#include <windows.h>
158#include <malloc.h>
159#include <sys/timeb.h>
160#include <mmsystem.h>
161#define getopt_long_only getopt_long
162#define memalign(align, size) malloc(size)
163#endif
164
165
166#ifdef CONFIG_COCOA
167#undef main
168#define main qemu_main
169#endif /* CONFIG_COCOA */
170
171#include "hw/hw.h"
172#include "hw/boards.h"
173#include "hw/usb.h"
174#include "hw/pcmcia.h"
175#include "hw/pc.h"
176#include "hw/audiodev.h"
177#include "hw/isa.h"
178#include "hw/baum.h"
179#include "hw/bt.h"
180#include "hw/watchdog.h"
181#include "hw/smbios.h"
182#include "hw/xen.h"
183#include "bt-host.h"
184#include "net.h"
185#include "monitor.h"
186#include "console.h"
187#include "sysemu.h"
188#include "gdbstub.h"
189#include "qemu-timer.h"
190#include "qemu-char.h"
191#include "cache-utils.h"
192#include "block.h"
193#include "dma.h"
194#include "audio/audio.h"
195#include "migration.h"
196#include "kvm.h"
197#include "balloon.h"
Vladimir Chtchetkineb25bf2a2010-09-08 11:09:23 -0700198#include "android/hw-lcd.h"
199#include "android/boot-properties.h"
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -0700200#include "android/core-init-utils.h"
David 'Digit' Turnerca29fbb2011-01-02 13:17:22 +0100201#include "android/audio-test.h"
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700202
Vladimir Chtchetkineeb838252010-07-15 12:27:56 -0700203#ifdef CONFIG_STANDALONE_CORE
204/* Verbose value used by the standalone emulator core (without UI) */
205unsigned long android_verbose;
206#endif // CONFIG_STANDALONE_CORE
207
Vladimir Chtchetkine57584042011-01-20 16:15:30 -0800208#if !defined(CONFIG_STANDALONE_CORE)
209/* in android/qemulator.c */
210extern void android_emulator_set_base_port(int port);
211#endif
212
Vladimir Chtchetkine43552dc2010-07-22 11:23:19 -0700213#if defined(CONFIG_SKINS) && !defined(CONFIG_STANDALONE_CORE)
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700214#undef main
215#define main qemu_main
216#endif
217
218#include "disas.h"
219
220#include "exec-all.h"
221
222#ifdef CONFIG_TRACE
223#include "trace.h"
224#include "dcache.h"
225#endif
226
227#include "qemu_socket.h"
228
229#if defined(CONFIG_SLIRP)
230#include "libslirp.h"
231#endif
232
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700233
234
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700235#define DEFAULT_RAM_SIZE 128
236
237/* Max number of USB devices that can be specified on the commandline. */
238#define MAX_USB_CMDLINE 8
239
240/* Max number of bluetooth switches on the commandline. */
241#define MAX_BT_CMDLINE 10
242
243/* XXX: use a two level table to limit memory usage */
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700244
245static const char *data_dir;
246const char *bios_name = NULL;
247static void *ioport_opaque[MAX_IOPORTS];
248static IOPortReadFunc *ioport_read_table[3][MAX_IOPORTS];
249static IOPortWriteFunc *ioport_write_table[3][MAX_IOPORTS];
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +0100250#ifdef MAX_DRIVES
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700251/* Note: drives_table[MAX_DRIVES] is a dummy block driver if none available
252 to store the VM snapshots */
253DriveInfo drives_table[MAX_DRIVES+1];
254int nb_drives;
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +0100255#endif
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700256enum vga_retrace_method vga_retrace_method = VGA_RETRACE_DUMB;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700257DisplayType display_type = DT_DEFAULT;
258const char* keyboard_layout = NULL;
259int64_t ticks_per_sec;
260ram_addr_t ram_size;
261int nb_nics;
262NICInfo nd_table[MAX_NICS];
263int vm_running;
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +0100264int autostart;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700265static int rtc_utc = 1;
266static int rtc_date_offset = -1; /* -1 means no change */
267int cirrus_vga_enabled = 1;
268int std_vga_enabled = 0;
269int vmsvga_enabled = 0;
270int xenfb_enabled = 0;
David 'Digit' Turnera7fb77d2010-05-10 23:50:54 -0700271QEMUClock *rtc_clock;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700272#ifdef TARGET_SPARC
273int graphic_width = 1024;
274int graphic_height = 768;
275int graphic_depth = 8;
276#else
277int graphic_width = 800;
278int graphic_height = 600;
279int graphic_depth = 15;
280#endif
281static int full_screen = 0;
282#ifdef CONFIG_SDL
283static int no_frame = 0;
284#endif
285int no_quit = 0;
286CharDriverState *serial_hds[MAX_SERIAL_PORTS];
David 'Digit' Turner062dd6a2011-03-01 14:50:07 +0100287int serial_hds_count;
288
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700289CharDriverState *parallel_hds[MAX_PARALLEL_PORTS];
290CharDriverState *virtcon_hds[MAX_VIRTIO_CONSOLES];
291#ifdef TARGET_I386
292int win2k_install_hack = 0;
293int rtc_td_hack = 0;
294#endif
295int usb_enabled = 0;
296int singlestep = 0;
297int smp_cpus = 1;
298const char *vnc_display;
299int acpi_enabled = 1;
300int no_hpet = 0;
301int no_virtio_balloon = 0;
302int fd_bootchk = 1;
303int no_reboot = 0;
304int no_shutdown = 0;
305int cursor_hide = 1;
306int graphic_rotate = 0;
307#ifndef _WIN32
308int daemonize = 0;
309#endif
310WatchdogTimerModel *watchdog = NULL;
311int watchdog_action = WDT_RESET;
312const char *option_rom[MAX_OPTION_ROMS];
313int nb_option_roms;
314int semihosting_enabled = 0;
315#ifdef TARGET_ARM
316int old_param = 0;
317#endif
318const char *qemu_name;
319int alt_grab = 0;
320#if defined(TARGET_SPARC) || defined(TARGET_PPC)
321unsigned int nb_prom_envs = 0;
322const char *prom_envs[MAX_PROM_ENVS];
323#endif
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +0100324#ifdef MAX_DRIVES
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700325int nb_drives_opt;
326struct drive_opt drives_opt[MAX_DRIVES];
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +0100327#endif
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700328int nb_numa_nodes;
329uint64_t node_mem[MAX_NODES];
330uint64_t node_cpumask[MAX_NODES];
331
332static CPUState *cur_cpu;
333static CPUState *next_cpu;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700334static QEMUTimer *nographic_timer;
335
336uint8_t qemu_uuid[16];
337
338
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -0700339int qemu_cpu_delay;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700340extern char* audio_input_source;
341
Vladimir Chtchetkined81e6d12010-06-15 16:46:32 -0700342extern char* android_op_ports;
343extern char* android_op_port;
344extern char* android_op_report_console;
345extern char* op_http_proxy;
Vladimir Chtchetkine43552dc2010-07-22 11:23:19 -0700346// Path to the file containing specific key character map.
347char* op_charmap_file = NULL;
Vladimir Chtchetkined81e6d12010-06-15 16:46:32 -0700348
Vladimir Chtchetkine074d1f92010-08-06 09:29:50 -0700349/* Path to hardware initialization file passed with -android-hw option. */
350char* android_op_hwini = NULL;
351
Vladimir Chtchetkineb5365f32010-08-09 13:33:57 -0700352/* Memory checker options. */
353char* android_op_memcheck = NULL;
354
Vladimir Chtchetkine7fbf4972010-08-11 15:30:32 -0700355/* -dns-server option value. */
356char* android_op_dns_server = NULL;
357
Vladimir Chtchetkine13f3b6c2010-08-25 09:49:25 -0700358/* -radio option value. */
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -0700359char* android_op_radio = NULL;
360
361/* -gps option value. */
362char* android_op_gps = NULL;
363
364/* -audio option value. */
365char* android_op_audio = NULL;
366
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -0700367/* -cpu-delay option value. */
368char* android_op_cpu_delay = NULL;
369
Vladimir Chtchetkinee1316862010-08-26 09:03:54 -0700370#ifdef CONFIG_NAND_LIMITS
371/* -nand-limits option value. */
372char* android_op_nand_limits = NULL;
373#endif // CONFIG_NAND_LIMITS
374
375/* -netspeed option value. */
376char* android_op_netspeed = NULL;
377
378/* -netdelay option value. */
379char* android_op_netdelay = NULL;
380
381/* -netfast option value. */
382int android_op_netfast = 0;
383
Vladimir Chtchetkine318f17a2010-08-27 09:09:45 -0700384/* -tcpdump option value. */
385char* android_op_tcpdump = NULL;
386
Vladimir Chtchetkineb25bf2a2010-09-08 11:09:23 -0700387/* -lcd-density option value. */
388char* android_op_lcd_density = NULL;
389
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -0700390/* -ui-port option value. This port will be used to report the core
391 * initialization completion.
392 */
393char* android_op_ui_port = NULL;
394
395/* -ui-settings option value. This value will be passed to the UI when new UI
396 * process is attaching to the core.
397 */
398char* android_op_ui_settings = NULL;
399
Vladimir Chtchetkine90c62352011-01-13 11:24:07 -0800400/* -android-avdname option value. */
401char* android_op_avd_name = "unknown";
402
Vladimir Chtchetkinedd50f7d2010-07-30 09:16:41 -0700403extern int android_display_width;
404extern int android_display_height;
405extern int android_display_bpp;
406
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700407extern void dprint( const char* format, ... );
408
rich canningsd952f282011-03-01 15:40:09 -0800409const char* dns_log_filename = NULL;
410const char* drop_log_filename = NULL;
411static int rotate_logs_requested = 0;
412
Tim Baverstock24204cc2010-11-25 11:37:43 +0000413const char* savevm_on_exit = NULL;
Tim Baverstock24204cc2010-11-25 11:37:43 +0000414
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700415#define TFR(expr) do { if ((expr) != -1) break; } while (errno == EINTR)
416
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -0700417/* Reports the core initialization failure to the error stdout and to the UI
418 * socket before exiting the application.
419 * Parameters that are passed to this macro are used to format the error
420 * mesage using sprintf routine.
421 */
422#ifdef CONFIG_ANDROID
423#define PANIC(...) android_core_init_failure(__VA_ARGS__)
424#else
425#define PANIC(...) do { fprintf(stderr, __VA_ARGS__); \
426 exit(1); \
427 } while (0)
428#endif // CONFIG_ANDROID
429
430/* Exits the core during initialization. */
431#ifdef CONFIG_ANDROID
432#define QEMU_EXIT(exit_code) android_core_init_exit(exit_code)
433#else
434#define QEMU_EXIT(exit_code) exit(exit_code)
435#endif // CONFIG_ANDROID
436
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700437/***********************************************************/
438/* x86 ISA bus support */
439
440target_phys_addr_t isa_mem_base = 0;
441PicState2 *isa_pic;
442
443static IOPortReadFunc default_ioport_readb, default_ioport_readw, default_ioport_readl;
444static IOPortWriteFunc default_ioport_writeb, default_ioport_writew, default_ioport_writel;
445
446static uint32_t ioport_read(int index, uint32_t address)
447{
448 static IOPortReadFunc *default_func[3] = {
449 default_ioport_readb,
450 default_ioport_readw,
451 default_ioport_readl
452 };
453 IOPortReadFunc *func = ioport_read_table[index][address];
454 if (!func)
455 func = default_func[index];
456 return func(ioport_opaque[address], address);
457}
458
459static void ioport_write(int index, uint32_t address, uint32_t data)
460{
461 static IOPortWriteFunc *default_func[3] = {
462 default_ioport_writeb,
463 default_ioport_writew,
464 default_ioport_writel
465 };
466 IOPortWriteFunc *func = ioport_write_table[index][address];
467 if (!func)
468 func = default_func[index];
469 func(ioport_opaque[address], address, data);
470}
471
472static uint32_t default_ioport_readb(void *opaque, uint32_t address)
473{
474#ifdef DEBUG_UNUSED_IOPORT
475 fprintf(stderr, "unused inb: port=0x%04x\n", address);
476#endif
477 return 0xff;
478}
479
480static void default_ioport_writeb(void *opaque, uint32_t address, uint32_t data)
481{
482#ifdef DEBUG_UNUSED_IOPORT
483 fprintf(stderr, "unused outb: port=0x%04x data=0x%02x\n", address, data);
484#endif
485}
486
487/* default is to make two byte accesses */
488static uint32_t default_ioport_readw(void *opaque, uint32_t address)
489{
490 uint32_t data;
491 data = ioport_read(0, address);
492 address = (address + 1) & (MAX_IOPORTS - 1);
493 data |= ioport_read(0, address) << 8;
494 return data;
495}
496
497static void default_ioport_writew(void *opaque, uint32_t address, uint32_t data)
498{
499 ioport_write(0, address, data & 0xff);
500 address = (address + 1) & (MAX_IOPORTS - 1);
501 ioport_write(0, address, (data >> 8) & 0xff);
502}
503
504static uint32_t default_ioport_readl(void *opaque, uint32_t address)
505{
506#ifdef DEBUG_UNUSED_IOPORT
507 fprintf(stderr, "unused inl: port=0x%04x\n", address);
508#endif
509 return 0xffffffff;
510}
511
512static void default_ioport_writel(void *opaque, uint32_t address, uint32_t data)
513{
514#ifdef DEBUG_UNUSED_IOPORT
515 fprintf(stderr, "unused outl: port=0x%04x data=0x%02x\n", address, data);
516#endif
517}
518
rich canningsd952f282011-03-01 15:40:09 -0800519/*
520 * Sets a flag (rotate_logs_requested) to clear both the DNS and the
521 * drop logs upon receiving a SIGUSR1 signal. We need to clear the logs
522 * between the tasks that do not require restarting Qemu.
523 */
524void rotate_qemu_logs_handler(int signum) {
525 rotate_logs_requested = 1;
526}
527
528/*
529 * Resets the rotate_log_requested_flag. Normally called after qemu
530 * logs has been rotated.
531 */
532void reset_rotate_qemu_logs_request(void) {
533 rotate_logs_requested = 0;
534}
535
536/*
537 * Clears the passed qemu log when the rotate_logs_requested
538 * is set. We need to clear the logs between the tasks that do not
539 * require restarting Qemu.
540 */
541FILE* rotate_qemu_log(FILE* old_log_fd, const char* filename) {
542 FILE* new_log_fd = NULL;
543 if (old_log_fd) {
544 if (fclose(old_log_fd) == -1) {
545 fprintf(stderr, "Cannot close old_log fd\n");
546 exit(errno);
547 }
548 }
549
550 if (!filename) {
551 fprintf(stderr, "The log filename to be rotated is not provided");
552 exit(-1);
553 }
554
555 new_log_fd = fopen(filename , "wb+");
556 if (new_log_fd == NULL) {
557 fprintf(stderr, "Cannot open the log file: %s for write.\n",
558 filename);
559 exit(1);
560 }
561
562 return new_log_fd;
563}
564
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700565/***********************************************************/
566void hw_error(const char *fmt, ...)
567{
568 va_list ap;
569 CPUState *env;
570
571 va_start(ap, fmt);
572 fprintf(stderr, "qemu: hardware error: ");
573 vfprintf(stderr, fmt, ap);
574 fprintf(stderr, "\n");
575 for(env = first_cpu; env != NULL; env = env->next_cpu) {
576 fprintf(stderr, "CPU #%d:\n", env->cpu_index);
577#ifdef TARGET_I386
578 cpu_dump_state(env, stderr, fprintf, X86_DUMP_FPU);
579#else
580 cpu_dump_state(env, stderr, fprintf, 0);
581#endif
582 }
583 va_end(ap);
584 abort();
585}
David 'Digit' Turner4e024bb2010-09-22 14:19:28 +0200586
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700587/***************/
588/* ballooning */
589
590static QEMUBalloonEvent *qemu_balloon_event;
591void *qemu_balloon_event_opaque;
592
593void qemu_add_balloon_handler(QEMUBalloonEvent *func, void *opaque)
594{
595 qemu_balloon_event = func;
596 qemu_balloon_event_opaque = opaque;
597}
598
599void qemu_balloon(ram_addr_t target)
600{
601 if (qemu_balloon_event)
602 qemu_balloon_event(qemu_balloon_event_opaque, target);
603}
604
605ram_addr_t qemu_balloon_status(void)
606{
607 if (qemu_balloon_event)
608 return qemu_balloon_event(qemu_balloon_event_opaque, 0);
609 return 0;
610}
611
612/***********************************************************/
David Turner025c32f2010-09-10 14:52:42 +0200613/* real time host monotonic timer */
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700614
615/* compute with 96 bit intermediate result: (a*b)/c */
616uint64_t muldiv64(uint64_t a, uint32_t b, uint32_t c)
617{
618 union {
619 uint64_t ll;
620 struct {
David 'Digit' Turner20894ae2010-05-10 17:07:36 -0700621#ifdef HOST_WORDS_BIGENDIAN
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700622 uint32_t high, low;
623#else
624 uint32_t low, high;
625#endif
626 } l;
627 } u, res;
628 uint64_t rl, rh;
629
630 u.ll = a;
631 rl = (uint64_t)u.l.low * (uint64_t)b;
632 rh = (uint64_t)u.l.high * (uint64_t)b;
633 rh += (rl >> 32);
634 res.l.high = rh / c;
635 res.l.low = (((rh % c) << 32) + (rl & 0xffffffff)) / c;
636 return res.ll;
637}
638
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700639/***********************************************************/
640/* host time/date access */
641void qemu_get_timedate(struct tm *tm, int offset)
642{
643 time_t ti;
644 struct tm *ret;
645
646 time(&ti);
647 ti += offset;
648 if (rtc_date_offset == -1) {
649 if (rtc_utc)
650 ret = gmtime(&ti);
651 else
652 ret = localtime(&ti);
653 } else {
654 ti -= rtc_date_offset;
655 ret = gmtime(&ti);
656 }
657
658 memcpy(tm, ret, sizeof(struct tm));
659}
660
661int qemu_timedate_diff(struct tm *tm)
662{
663 time_t seconds;
664
665 if (rtc_date_offset == -1)
666 if (rtc_utc)
667 seconds = mktimegm(tm);
668 else
669 seconds = mktime(tm);
670 else
671 seconds = mktimegm(tm) + rtc_date_offset;
672
673 return seconds - time(NULL);
674}
675
676
677#ifdef CONFIG_TRACE
678static int tbflush_requested;
679static int exit_requested;
680
681void start_tracing()
682{
683 if (trace_filename == NULL)
684 return;
685 if (!tracing) {
686 fprintf(stderr,"-- start tracing --\n");
687 start_time = Now();
688 }
689 tracing = 1;
690 tbflush_requested = 1;
691 qemu_notify_event();
692}
693
694void stop_tracing()
695{
696 if (trace_filename == NULL)
697 return;
698 if (tracing) {
699 end_time = Now();
700 elapsed_usecs += end_time - start_time;
701 fprintf(stderr,"-- stop tracing --\n");
702 }
703 tracing = 0;
704 tbflush_requested = 1;
705 qemu_notify_event();
706}
707
708#ifndef _WIN32
709/* This is the handler for the SIGUSR1 and SIGUSR2 signals.
710 * SIGUSR1 turns tracing on. SIGUSR2 turns tracing off.
711 */
712void sigusr_handler(int sig)
713{
714 if (sig == SIGUSR1)
715 start_tracing();
716 else
717 stop_tracing();
718}
719#endif
720
721/* This is the handler to catch control-C so that we can exit cleanly.
722 * This is needed when tracing to flush the buffers to disk.
723 */
724void sigint_handler(int sig)
725{
726 exit_requested = 1;
727 qemu_notify_event();
728}
729#endif /* CONFIG_TRACE */
730
731
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700732/***********************************************************/
733/* Bluetooth support */
734static int nb_hcis;
735static int cur_hci;
736static struct HCIInfo *hci_table[MAX_NICS];
737
738static struct bt_vlan_s {
739 struct bt_scatternet_s net;
740 int id;
741 struct bt_vlan_s *next;
742} *first_bt_vlan;
743
744/* find or alloc a new bluetooth "VLAN" */
745static struct bt_scatternet_s *qemu_find_bt_vlan(int id)
746{
747 struct bt_vlan_s **pvlan, *vlan;
748 for (vlan = first_bt_vlan; vlan != NULL; vlan = vlan->next) {
749 if (vlan->id == id)
750 return &vlan->net;
751 }
752 vlan = qemu_mallocz(sizeof(struct bt_vlan_s));
753 vlan->id = id;
754 pvlan = &first_bt_vlan;
755 while (*pvlan != NULL)
756 pvlan = &(*pvlan)->next;
757 *pvlan = vlan;
758 return &vlan->net;
759}
760
761static void null_hci_send(struct HCIInfo *hci, const uint8_t *data, int len)
762{
763}
764
765static int null_hci_addr_set(struct HCIInfo *hci, const uint8_t *bd_addr)
766{
767 return -ENOTSUP;
768}
769
770static struct HCIInfo null_hci = {
771 .cmd_send = null_hci_send,
772 .sco_send = null_hci_send,
773 .acl_send = null_hci_send,
774 .bdaddr_set = null_hci_addr_set,
775};
776
777struct HCIInfo *qemu_next_hci(void)
778{
779 if (cur_hci == nb_hcis)
780 return &null_hci;
781
782 return hci_table[cur_hci++];
783}
784
785static struct HCIInfo *hci_init(const char *str)
786{
787 char *endp;
788 struct bt_scatternet_s *vlan = 0;
789
790 if (!strcmp(str, "null"))
791 /* null */
792 return &null_hci;
793 else if (!strncmp(str, "host", 4) && (str[4] == '\0' || str[4] == ':'))
794 /* host[:hciN] */
795 return bt_host_hci(str[4] ? str + 5 : "hci0");
796 else if (!strncmp(str, "hci", 3)) {
797 /* hci[,vlan=n] */
798 if (str[3]) {
799 if (!strncmp(str + 3, ",vlan=", 6)) {
800 vlan = qemu_find_bt_vlan(strtol(str + 9, &endp, 0));
801 if (*endp)
802 vlan = 0;
803 }
804 } else
805 vlan = qemu_find_bt_vlan(0);
806 if (vlan)
807 return bt_new_hci(vlan);
808 }
809
810 fprintf(stderr, "qemu: Unknown bluetooth HCI `%s'.\n", str);
811
812 return 0;
813}
814
815static int bt_hci_parse(const char *str)
816{
817 struct HCIInfo *hci;
818 bdaddr_t bdaddr;
819
820 if (nb_hcis >= MAX_NICS) {
821 fprintf(stderr, "qemu: Too many bluetooth HCIs (max %i).\n", MAX_NICS);
822 return -1;
823 }
824
825 hci = hci_init(str);
826 if (!hci)
827 return -1;
828
829 bdaddr.b[0] = 0x52;
830 bdaddr.b[1] = 0x54;
831 bdaddr.b[2] = 0x00;
832 bdaddr.b[3] = 0x12;
833 bdaddr.b[4] = 0x34;
834 bdaddr.b[5] = 0x56 + nb_hcis;
835 hci->bdaddr_set(hci, bdaddr.b);
836
837 hci_table[nb_hcis++] = hci;
838
839 return 0;
840}
841
842static void bt_vhci_add(int vlan_id)
843{
844 struct bt_scatternet_s *vlan = qemu_find_bt_vlan(vlan_id);
845
846 if (!vlan->slave)
847 fprintf(stderr, "qemu: warning: adding a VHCI to "
848 "an empty scatternet %i\n", vlan_id);
849
850 bt_vhci_init(bt_new_hci(vlan));
851}
852
853static struct bt_device_s *bt_device_add(const char *opt)
854{
855 struct bt_scatternet_s *vlan;
856 int vlan_id = 0;
857 char *endp = strstr(opt, ",vlan=");
858 int len = (endp ? endp - opt : strlen(opt)) + 1;
859 char devname[10];
860
861 pstrcpy(devname, MIN(sizeof(devname), len), opt);
862
863 if (endp) {
864 vlan_id = strtol(endp + 6, &endp, 0);
865 if (*endp) {
866 fprintf(stderr, "qemu: unrecognised bluetooth vlan Id\n");
867 return 0;
868 }
869 }
870
871 vlan = qemu_find_bt_vlan(vlan_id);
872
873 if (!vlan->slave)
874 fprintf(stderr, "qemu: warning: adding a slave device to "
875 "an empty scatternet %i\n", vlan_id);
876
877 if (!strcmp(devname, "keyboard"))
878 return bt_keyboard_init(vlan);
879
880 fprintf(stderr, "qemu: unsupported bluetooth device `%s'\n", devname);
881 return 0;
882}
883
884static int bt_parse(const char *opt)
885{
886 const char *endp, *p;
887 int vlan;
888
889 if (strstart(opt, "hci", &endp)) {
890 if (!*endp || *endp == ',') {
891 if (*endp)
892 if (!strstart(endp, ",vlan=", 0))
893 opt = endp + 1;
894
895 return bt_hci_parse(opt);
896 }
897 } else if (strstart(opt, "vhci", &endp)) {
898 if (!*endp || *endp == ',') {
899 if (*endp) {
900 if (strstart(endp, ",vlan=", &p)) {
901 vlan = strtol(p, (char **) &endp, 0);
902 if (*endp) {
903 fprintf(stderr, "qemu: bad scatternet '%s'\n", p);
904 return 1;
905 }
906 } else {
907 fprintf(stderr, "qemu: bad parameter '%s'\n", endp + 1);
908 return 1;
909 }
910 } else
911 vlan = 0;
912
913 bt_vhci_add(vlan);
914 return 0;
915 }
916 } else if (strstart(opt, "device:", &endp))
917 return !bt_device_add(endp);
918
919 fprintf(stderr, "qemu: bad bluetooth parameter '%s'\n", opt);
920 return 1;
921}
922
923/***********************************************************/
924/* QEMU Block devices */
925
926#define HD_ALIAS "index=%d,media=disk"
927#define CDROM_ALIAS "index=2,media=cdrom"
928#define FD_ALIAS "index=%d,if=floppy"
929#define PFLASH_ALIAS "if=pflash"
930#define MTD_ALIAS "if=mtd"
931#define SD_ALIAS "index=0,if=sd"
932
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +0100933static int drive_init_func(QemuOpts *opts, void *opaque)
934{
935 int *use_scsi = opaque;
936 int fatal_error = 0;
937
938 if (drive_init(opts, *use_scsi, &fatal_error) == NULL) {
939 if (fatal_error)
940 return 1;
941 }
942 return 0;
943}
944
945static int drive_enable_snapshot(QemuOpts *opts, void *opaque)
946{
947 if (NULL == qemu_opt_get(opts, "snapshot")) {
948 qemu_opt_set(opts, "snapshot", "on");
949 }
950 return 0;
951}
952
953#ifdef MAX_DRIVES
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700954static int drive_opt_get_free_idx(void)
955{
956 int index;
957
958 for (index = 0; index < MAX_DRIVES; index++)
959 if (!drives_opt[index].used) {
960 drives_opt[index].used = 1;
961 return index;
962 }
963
964 return -1;
965}
966
967static int drive_get_free_idx(void)
968{
969 int index;
970
971 for (index = 0; index < MAX_DRIVES; index++)
972 if (!drives_table[index].used) {
973 drives_table[index].used = 1;
974 return index;
975 }
976
977 return -1;
978}
979
980int drive_add(const char *file, const char *fmt, ...)
981{
982 va_list ap;
983 int index = drive_opt_get_free_idx();
984
985 if (nb_drives_opt >= MAX_DRIVES || index == -1) {
986 fprintf(stderr, "qemu: too many drives\n");
987 return -1;
988 }
989
990 drives_opt[index].file = file;
991 va_start(ap, fmt);
992 vsnprintf(drives_opt[index].opt,
993 sizeof(drives_opt[0].opt), fmt, ap);
994 va_end(ap);
David 'Digit' Turner92568952010-04-15 15:04:16 -0700995
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -0700996 nb_drives_opt++;
997 return index;
998}
999
1000void drive_remove(int index)
1001{
1002 drives_opt[index].used = 0;
1003 nb_drives_opt--;
1004}
1005
1006int drive_get_index(BlockInterfaceType type, int bus, int unit)
1007{
1008 int index;
1009
1010 /* seek interface, bus and unit */
1011
1012 for (index = 0; index < MAX_DRIVES; index++)
1013 if (drives_table[index].type == type &&
1014 drives_table[index].bus == bus &&
1015 drives_table[index].unit == unit &&
1016 drives_table[index].used)
1017 return index;
1018
1019 return -1;
1020}
1021
1022int drive_get_max_bus(BlockInterfaceType type)
1023{
1024 int max_bus;
1025 int index;
1026
1027 max_bus = -1;
1028 for (index = 0; index < nb_drives; index++) {
1029 if(drives_table[index].type == type &&
1030 drives_table[index].bus > max_bus)
1031 max_bus = drives_table[index].bus;
1032 }
1033 return max_bus;
1034}
1035
1036const char *drive_get_serial(BlockDriverState *bdrv)
1037{
1038 int index;
1039
1040 for (index = 0; index < nb_drives; index++)
1041 if (drives_table[index].bdrv == bdrv)
1042 return drives_table[index].serial;
1043
1044 return "\0";
1045}
1046
1047BlockInterfaceErrorAction drive_get_onerror(BlockDriverState *bdrv)
1048{
1049 int index;
1050
1051 for (index = 0; index < nb_drives; index++)
1052 if (drives_table[index].bdrv == bdrv)
1053 return drives_table[index].onerror;
1054
1055 return BLOCK_ERR_STOP_ENOSPC;
1056}
1057
1058static void bdrv_format_print(void *opaque, const char *name)
1059{
1060 fprintf(stderr, " %s", name);
1061}
1062
1063void drive_uninit(BlockDriverState *bdrv)
1064{
1065 int i;
1066
1067 for (i = 0; i < MAX_DRIVES; i++)
1068 if (drives_table[i].bdrv == bdrv) {
1069 drives_table[i].bdrv = NULL;
1070 drives_table[i].used = 0;
1071 drive_remove(drives_table[i].drive_opt_idx);
1072 nb_drives--;
1073 break;
1074 }
1075}
1076
1077int drive_init(struct drive_opt *arg, int snapshot, void *opaque)
1078{
1079 char buf[128];
1080 char file[1024];
1081 char devname[128];
1082 char serial[21];
1083 const char *mediastr = "";
1084 BlockInterfaceType type;
1085 enum { MEDIA_DISK, MEDIA_CDROM } media;
1086 int bus_id, unit_id;
1087 int cyls, heads, secs, translation;
1088 BlockDriverState *bdrv;
1089 BlockDriver *drv = NULL;
1090 QEMUMachine *machine = opaque;
1091 int max_devs;
1092 int index;
1093 int cache;
1094 int bdrv_flags, onerror;
1095 int drives_table_idx;
1096 char *str = arg->opt;
1097 static const char * const params[] = { "bus", "unit", "if", "index",
1098 "cyls", "heads", "secs", "trans",
1099 "media", "snapshot", "file",
1100 "cache", "format", "serial", "werror",
1101 NULL };
1102
1103 if (check_params(buf, sizeof(buf), params, str) < 0) {
1104 fprintf(stderr, "qemu: unknown parameter '%s' in '%s'\n",
1105 buf, str);
1106 return -1;
1107 }
1108
1109 file[0] = 0;
1110 cyls = heads = secs = 0;
1111 bus_id = 0;
1112 unit_id = -1;
1113 translation = BIOS_ATA_TRANSLATION_AUTO;
1114 index = -1;
1115 cache = 3;
1116
1117 if (machine->use_scsi) {
1118 type = IF_SCSI;
1119 max_devs = MAX_SCSI_DEVS;
1120 pstrcpy(devname, sizeof(devname), "scsi");
1121 } else {
1122 type = IF_IDE;
1123 max_devs = MAX_IDE_DEVS;
1124 pstrcpy(devname, sizeof(devname), "ide");
1125 }
1126 media = MEDIA_DISK;
1127
1128 /* extract parameters */
1129
1130 if (get_param_value(buf, sizeof(buf), "bus", str)) {
1131 bus_id = strtol(buf, NULL, 0);
1132 if (bus_id < 0) {
1133 fprintf(stderr, "qemu: '%s' invalid bus id\n", str);
1134 return -1;
1135 }
1136 }
1137
1138 if (get_param_value(buf, sizeof(buf), "unit", str)) {
1139 unit_id = strtol(buf, NULL, 0);
1140 if (unit_id < 0) {
1141 fprintf(stderr, "qemu: '%s' invalid unit id\n", str);
1142 return -1;
1143 }
1144 }
1145
1146 if (get_param_value(buf, sizeof(buf), "if", str)) {
1147 pstrcpy(devname, sizeof(devname), buf);
1148 if (!strcmp(buf, "ide")) {
1149 type = IF_IDE;
1150 max_devs = MAX_IDE_DEVS;
1151 } else if (!strcmp(buf, "scsi")) {
1152 type = IF_SCSI;
1153 max_devs = MAX_SCSI_DEVS;
1154 } else if (!strcmp(buf, "floppy")) {
1155 type = IF_FLOPPY;
1156 max_devs = 0;
1157 } else if (!strcmp(buf, "pflash")) {
1158 type = IF_PFLASH;
1159 max_devs = 0;
1160 } else if (!strcmp(buf, "mtd")) {
1161 type = IF_MTD;
1162 max_devs = 0;
1163 } else if (!strcmp(buf, "sd")) {
1164 type = IF_SD;
1165 max_devs = 0;
1166 } else if (!strcmp(buf, "virtio")) {
1167 type = IF_VIRTIO;
1168 max_devs = 0;
1169 } else if (!strcmp(buf, "xen")) {
1170 type = IF_XEN;
1171 max_devs = 0;
1172 } else {
1173 fprintf(stderr, "qemu: '%s' unsupported bus type '%s'\n", str, buf);
1174 return -1;
1175 }
1176 }
1177
1178 if (get_param_value(buf, sizeof(buf), "index", str)) {
1179 index = strtol(buf, NULL, 0);
1180 if (index < 0) {
1181 fprintf(stderr, "qemu: '%s' invalid index\n", str);
1182 return -1;
1183 }
1184 }
1185
1186 if (get_param_value(buf, sizeof(buf), "cyls", str)) {
1187 cyls = strtol(buf, NULL, 0);
1188 }
1189
1190 if (get_param_value(buf, sizeof(buf), "heads", str)) {
1191 heads = strtol(buf, NULL, 0);
1192 }
1193
1194 if (get_param_value(buf, sizeof(buf), "secs", str)) {
1195 secs = strtol(buf, NULL, 0);
1196 }
1197
1198 if (cyls || heads || secs) {
1199 if (cyls < 1 || cyls > 16383) {
1200 fprintf(stderr, "qemu: '%s' invalid physical cyls number\n", str);
1201 return -1;
1202 }
1203 if (heads < 1 || heads > 16) {
1204 fprintf(stderr, "qemu: '%s' invalid physical heads number\n", str);
1205 return -1;
1206 }
1207 if (secs < 1 || secs > 63) {
1208 fprintf(stderr, "qemu: '%s' invalid physical secs number\n", str);
1209 return -1;
1210 }
1211 }
1212
1213 if (get_param_value(buf, sizeof(buf), "trans", str)) {
1214 if (!cyls) {
1215 fprintf(stderr,
1216 "qemu: '%s' trans must be used with cyls,heads and secs\n",
1217 str);
1218 return -1;
1219 }
1220 if (!strcmp(buf, "none"))
1221 translation = BIOS_ATA_TRANSLATION_NONE;
1222 else if (!strcmp(buf, "lba"))
1223 translation = BIOS_ATA_TRANSLATION_LBA;
1224 else if (!strcmp(buf, "auto"))
1225 translation = BIOS_ATA_TRANSLATION_AUTO;
1226 else {
1227 fprintf(stderr, "qemu: '%s' invalid translation type\n", str);
1228 return -1;
1229 }
1230 }
1231
1232 if (get_param_value(buf, sizeof(buf), "media", str)) {
1233 if (!strcmp(buf, "disk")) {
1234 media = MEDIA_DISK;
1235 } else if (!strcmp(buf, "cdrom")) {
1236 if (cyls || secs || heads) {
1237 fprintf(stderr,
1238 "qemu: '%s' invalid physical CHS format\n", str);
1239 return -1;
1240 }
1241 media = MEDIA_CDROM;
1242 } else {
1243 fprintf(stderr, "qemu: '%s' invalid media\n", str);
1244 return -1;
1245 }
1246 }
1247
1248 if (get_param_value(buf, sizeof(buf), "snapshot", str)) {
1249 if (!strcmp(buf, "on"))
1250 snapshot = 1;
1251 else if (!strcmp(buf, "off"))
1252 snapshot = 0;
1253 else {
1254 fprintf(stderr, "qemu: '%s' invalid snapshot option\n", str);
1255 return -1;
1256 }
1257 }
1258
1259 if (get_param_value(buf, sizeof(buf), "cache", str)) {
1260 if (!strcmp(buf, "off") || !strcmp(buf, "none"))
1261 cache = 0;
1262 else if (!strcmp(buf, "writethrough"))
1263 cache = 1;
1264 else if (!strcmp(buf, "writeback"))
1265 cache = 2;
1266 else {
1267 fprintf(stderr, "qemu: invalid cache option\n");
1268 return -1;
1269 }
1270 }
1271
1272 if (get_param_value(buf, sizeof(buf), "format", str)) {
1273 if (strcmp(buf, "?") == 0) {
1274 fprintf(stderr, "qemu: Supported formats:");
1275 bdrv_iterate_format(bdrv_format_print, NULL);
1276 fprintf(stderr, "\n");
1277 return -1;
1278 }
1279 drv = bdrv_find_format(buf);
1280 if (!drv) {
1281 fprintf(stderr, "qemu: '%s' invalid format\n", buf);
1282 return -1;
1283 }
1284 }
1285
1286 if (arg->file == NULL)
1287 get_param_value(file, sizeof(file), "file", str);
1288 else
1289 pstrcpy(file, sizeof(file), arg->file);
1290
1291 if (!get_param_value(serial, sizeof(serial), "serial", str))
1292 memset(serial, 0, sizeof(serial));
1293
1294 onerror = BLOCK_ERR_STOP_ENOSPC;
1295 if (get_param_value(buf, sizeof(serial), "werror", str)) {
1296 if (type != IF_IDE && type != IF_SCSI && type != IF_VIRTIO) {
1297 fprintf(stderr, "werror is no supported by this format\n");
1298 return -1;
1299 }
1300 if (!strcmp(buf, "ignore"))
1301 onerror = BLOCK_ERR_IGNORE;
1302 else if (!strcmp(buf, "enospc"))
1303 onerror = BLOCK_ERR_STOP_ENOSPC;
1304 else if (!strcmp(buf, "stop"))
1305 onerror = BLOCK_ERR_STOP_ANY;
1306 else if (!strcmp(buf, "report"))
1307 onerror = BLOCK_ERR_REPORT;
1308 else {
1309 fprintf(stderr, "qemu: '%s' invalid write error action\n", buf);
1310 return -1;
1311 }
1312 }
1313
1314 /* compute bus and unit according index */
1315
1316 if (index != -1) {
1317 if (bus_id != 0 || unit_id != -1) {
1318 fprintf(stderr,
1319 "qemu: '%s' index cannot be used with bus and unit\n", str);
1320 return -1;
1321 }
1322 if (max_devs == 0)
1323 {
1324 unit_id = index;
1325 bus_id = 0;
1326 } else {
1327 unit_id = index % max_devs;
1328 bus_id = index / max_devs;
1329 }
1330 }
1331
1332 /* if user doesn't specify a unit_id,
1333 * try to find the first free
1334 */
1335
1336 if (unit_id == -1) {
1337 unit_id = 0;
1338 while (drive_get_index(type, bus_id, unit_id) != -1) {
1339 unit_id++;
1340 if (max_devs && unit_id >= max_devs) {
1341 unit_id -= max_devs;
1342 bus_id++;
1343 }
1344 }
1345 }
1346
1347 /* check unit id */
1348
1349 if (max_devs && unit_id >= max_devs) {
1350 fprintf(stderr, "qemu: '%s' unit %d too big (max is %d)\n",
1351 str, unit_id, max_devs - 1);
1352 return -1;
1353 }
1354
1355 /*
1356 * ignore multiple definitions
1357 */
1358
1359 if (drive_get_index(type, bus_id, unit_id) != -1)
1360 return -2;
1361
1362 /* init */
1363
1364 if (type == IF_IDE || type == IF_SCSI)
1365 mediastr = (media == MEDIA_CDROM) ? "-cd" : "-hd";
1366 if (max_devs)
1367 snprintf(buf, sizeof(buf), "%s%i%s%i",
1368 devname, bus_id, mediastr, unit_id);
1369 else
1370 snprintf(buf, sizeof(buf), "%s%s%i",
1371 devname, mediastr, unit_id);
1372 bdrv = bdrv_new(buf);
1373 drives_table_idx = drive_get_free_idx();
1374 drives_table[drives_table_idx].bdrv = bdrv;
1375 drives_table[drives_table_idx].type = type;
1376 drives_table[drives_table_idx].bus = bus_id;
1377 drives_table[drives_table_idx].unit = unit_id;
1378 drives_table[drives_table_idx].onerror = onerror;
1379 drives_table[drives_table_idx].drive_opt_idx = arg - drives_opt;
1380 strncpy(drives_table[drives_table_idx].serial, serial, sizeof(serial));
1381 nb_drives++;
1382
1383 switch(type) {
1384 case IF_IDE:
1385 case IF_SCSI:
1386 case IF_XEN:
1387 switch(media) {
1388 case MEDIA_DISK:
1389 if (cyls != 0) {
1390 bdrv_set_geometry_hint(bdrv, cyls, heads, secs);
1391 bdrv_set_translation_hint(bdrv, translation);
1392 }
1393 break;
1394 case MEDIA_CDROM:
1395 bdrv_set_type_hint(bdrv, BDRV_TYPE_CDROM);
1396 break;
1397 }
1398 break;
1399 case IF_SD:
1400 /* FIXME: This isn't really a floppy, but it's a reasonable
1401 approximation. */
1402 case IF_FLOPPY:
1403 bdrv_set_type_hint(bdrv, BDRV_TYPE_FLOPPY);
1404 break;
1405 case IF_PFLASH:
1406 case IF_MTD:
1407 case IF_VIRTIO:
1408 break;
1409 case IF_COUNT:
David 'Digit' Turnerc34e8dc2010-09-13 02:47:01 -07001410 case IF_NONE:
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07001411 abort();
1412 }
1413 if (!file[0])
1414 return -2;
1415 bdrv_flags = 0;
1416 if (snapshot) {
1417 bdrv_flags |= BDRV_O_SNAPSHOT;
1418 cache = 2; /* always use write-back with snapshot */
1419 }
1420 if (cache == 0) /* no caching */
1421 bdrv_flags |= BDRV_O_NOCACHE;
1422 else if (cache == 2) /* write-back */
1423 bdrv_flags |= BDRV_O_CACHE_WB;
1424 else if (cache == 3) /* not specified */
1425 bdrv_flags |= BDRV_O_CACHE_DEF;
1426 if (bdrv_open2(bdrv, file, bdrv_flags, drv) < 0) {
1427 fprintf(stderr, "qemu: could not open disk image %s\n",
1428 file);
1429 return -1;
1430 }
1431 if (bdrv_key_required(bdrv))
1432 autostart = 0;
1433 return drives_table_idx;
1434}
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +01001435#endif /* MAX_DRIVES */
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07001436
1437static void numa_add(const char *optarg)
1438{
1439 char option[128];
1440 char *endptr;
1441 unsigned long long value, endvalue;
1442 int nodenr;
1443
1444 optarg = get_opt_name(option, 128, optarg, ',') + 1;
1445 if (!strcmp(option, "node")) {
1446 if (get_param_value(option, 128, "nodeid", optarg) == 0) {
1447 nodenr = nb_numa_nodes;
1448 } else {
1449 nodenr = strtoull(option, NULL, 10);
1450 }
1451
1452 if (get_param_value(option, 128, "mem", optarg) == 0) {
1453 node_mem[nodenr] = 0;
1454 } else {
1455 value = strtoull(option, &endptr, 0);
1456 switch (*endptr) {
1457 case 0: case 'M': case 'm':
1458 value <<= 20;
1459 break;
1460 case 'G': case 'g':
1461 value <<= 30;
1462 break;
1463 }
1464 node_mem[nodenr] = value;
1465 }
1466 if (get_param_value(option, 128, "cpus", optarg) == 0) {
1467 node_cpumask[nodenr] = 0;
1468 } else {
1469 value = strtoull(option, &endptr, 10);
1470 if (value >= 64) {
1471 value = 63;
1472 fprintf(stderr, "only 64 CPUs in NUMA mode supported.\n");
1473 } else {
1474 if (*endptr == '-') {
1475 endvalue = strtoull(endptr+1, &endptr, 10);
1476 if (endvalue >= 63) {
1477 endvalue = 62;
1478 fprintf(stderr,
1479 "only 63 CPUs in NUMA mode supported.\n");
1480 }
1481 value = (1 << (endvalue + 1)) - (1 << value);
1482 } else {
1483 value = 1 << value;
1484 }
1485 }
1486 node_cpumask[nodenr] = value;
1487 }
1488 nb_numa_nodes++;
1489 }
1490 return;
1491}
1492
1493/***********************************************************/
1494/* USB devices */
1495
1496static USBPort *used_usb_ports;
1497static USBPort *free_usb_ports;
1498
1499/* ??? Maybe change this to register a hub to keep track of the topology. */
1500void qemu_register_usb_port(USBPort *port, void *opaque, int index,
1501 usb_attachfn attach)
1502{
1503 port->opaque = opaque;
1504 port->index = index;
1505 port->attach = attach;
1506 port->next = free_usb_ports;
1507 free_usb_ports = port;
1508}
1509
1510int usb_device_add_dev(USBDevice *dev)
1511{
1512 USBPort *port;
1513
1514 /* Find a USB port to add the device to. */
1515 port = free_usb_ports;
1516 if (!port->next) {
1517 USBDevice *hub;
1518
1519 /* Create a new hub and chain it on. */
1520 free_usb_ports = NULL;
1521 port->next = used_usb_ports;
1522 used_usb_ports = port;
1523
1524 hub = usb_hub_init(VM_USB_HUB_SIZE);
1525 usb_attach(port, hub);
1526 port = free_usb_ports;
1527 }
1528
1529 free_usb_ports = port->next;
1530 port->next = used_usb_ports;
1531 used_usb_ports = port;
1532 usb_attach(port, dev);
1533 return 0;
1534}
1535
David 'Digit' Turner3266b512010-05-10 18:44:56 -07001536#if 0
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07001537static void usb_msd_password_cb(void *opaque, int err)
1538{
1539 USBDevice *dev = opaque;
1540
1541 if (!err)
1542 usb_device_add_dev(dev);
1543 else
1544 dev->handle_destroy(dev);
1545}
David 'Digit' Turner3266b512010-05-10 18:44:56 -07001546#endif
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07001547
1548static int usb_device_add(const char *devname, int is_hotplug)
1549{
1550 const char *p;
1551 USBDevice *dev;
1552
1553 if (!free_usb_ports)
1554 return -1;
1555
1556 if (strstart(devname, "host:", &p)) {
1557 dev = usb_host_device_open(p);
1558 } else if (!strcmp(devname, "mouse")) {
1559 dev = usb_mouse_init();
1560 } else if (!strcmp(devname, "tablet")) {
1561 dev = usb_tablet_init();
1562 } else if (!strcmp(devname, "keyboard")) {
1563 dev = usb_keyboard_init();
1564 } else if (strstart(devname, "disk:", &p)) {
1565#if 0
1566 BlockDriverState *bs;
1567#endif
1568 dev = usb_msd_init(p);
1569 if (!dev)
1570 return -1;
1571#if 0
1572 bs = usb_msd_get_bdrv(dev);
1573 if (bdrv_key_required(bs)) {
1574 autostart = 0;
1575 if (is_hotplug) {
1576 monitor_read_bdrv_key_start(cur_mon, bs, usb_msd_password_cb,
1577 dev);
1578 return 0;
1579 }
1580 }
1581 } else if (!strcmp(devname, "wacom-tablet")) {
1582 dev = usb_wacom_init();
1583 } else if (strstart(devname, "serial:", &p)) {
1584 dev = usb_serial_init(p);
1585#ifdef CONFIG_BRLAPI
1586 } else if (!strcmp(devname, "braille")) {
1587 dev = usb_baum_init();
1588#endif
1589 } else if (strstart(devname, "net:", &p)) {
1590 int nic = nb_nics;
1591
1592 if (net_client_init("nic", p) < 0)
1593 return -1;
1594 nd_table[nic].model = "usb";
1595 dev = usb_net_init(&nd_table[nic]);
1596 } else if (!strcmp(devname, "bt") || strstart(devname, "bt:", &p)) {
1597 dev = usb_bt_init(devname[2] ? hci_init(p) :
1598 bt_new_hci(qemu_find_bt_vlan(0)));
1599#endif
1600 } else {
1601 return -1;
1602 }
1603 if (!dev)
1604 return -1;
1605
1606 return usb_device_add_dev(dev);
1607}
1608
1609int usb_device_del_addr(int bus_num, int addr)
1610{
1611 USBPort *port;
1612 USBPort **lastp;
1613 USBDevice *dev;
1614
1615 if (!used_usb_ports)
1616 return -1;
1617
1618 if (bus_num != 0)
1619 return -1;
1620
1621 lastp = &used_usb_ports;
1622 port = used_usb_ports;
1623 while (port && port->dev->addr != addr) {
1624 lastp = &port->next;
1625 port = port->next;
1626 }
1627
1628 if (!port)
1629 return -1;
1630
1631 dev = port->dev;
1632 *lastp = port->next;
1633 usb_attach(port, NULL);
1634 dev->handle_destroy(dev);
1635 port->next = free_usb_ports;
1636 free_usb_ports = port;
1637 return 0;
1638}
1639
1640static int usb_device_del(const char *devname)
1641{
1642 int bus_num, addr;
1643 const char *p;
1644
1645 if (strstart(devname, "host:", &p))
1646 return usb_host_device_close(p);
1647
1648 if (!used_usb_ports)
1649 return -1;
1650
1651 p = strchr(devname, '.');
1652 if (!p)
1653 return -1;
1654 bus_num = strtoul(devname, NULL, 0);
1655 addr = strtoul(p + 1, NULL, 0);
1656
1657 return usb_device_del_addr(bus_num, addr);
1658}
1659
1660void do_usb_add(Monitor *mon, const char *devname)
1661{
1662 usb_device_add(devname, 1);
1663}
1664
1665void do_usb_del(Monitor *mon, const char *devname)
1666{
1667 usb_device_del(devname);
1668}
1669
1670void usb_info(Monitor *mon)
1671{
1672 USBDevice *dev;
1673 USBPort *port;
1674 const char *speed_str;
1675
1676 if (!usb_enabled) {
1677 monitor_printf(mon, "USB support not enabled\n");
1678 return;
1679 }
1680
1681 for (port = used_usb_ports; port; port = port->next) {
1682 dev = port->dev;
1683 if (!dev)
1684 continue;
1685 switch(dev->speed) {
1686 case USB_SPEED_LOW:
1687 speed_str = "1.5";
1688 break;
1689 case USB_SPEED_FULL:
1690 speed_str = "12";
1691 break;
1692 case USB_SPEED_HIGH:
1693 speed_str = "480";
1694 break;
1695 default:
1696 speed_str = "?";
1697 break;
1698 }
1699 monitor_printf(mon, " Device %d.%d, Speed %s Mb/s, Product %s\n",
1700 0, dev->addr, speed_str, dev->devname);
1701 }
1702}
1703
1704/***********************************************************/
1705/* PCMCIA/Cardbus */
1706
1707static struct pcmcia_socket_entry_s {
1708 PCMCIASocket *socket;
1709 struct pcmcia_socket_entry_s *next;
1710} *pcmcia_sockets = 0;
1711
1712void pcmcia_socket_register(PCMCIASocket *socket)
1713{
1714 struct pcmcia_socket_entry_s *entry;
1715
1716 entry = qemu_malloc(sizeof(struct pcmcia_socket_entry_s));
1717 entry->socket = socket;
1718 entry->next = pcmcia_sockets;
1719 pcmcia_sockets = entry;
1720}
1721
1722void pcmcia_socket_unregister(PCMCIASocket *socket)
1723{
1724 struct pcmcia_socket_entry_s *entry, **ptr;
1725
1726 ptr = &pcmcia_sockets;
1727 for (entry = *ptr; entry; ptr = &entry->next, entry = *ptr)
1728 if (entry->socket == socket) {
1729 *ptr = entry->next;
1730 qemu_free(entry);
1731 }
1732}
1733
1734void pcmcia_info(Monitor *mon)
1735{
1736 struct pcmcia_socket_entry_s *iter;
1737
1738 if (!pcmcia_sockets)
1739 monitor_printf(mon, "No PCMCIA sockets\n");
1740
1741 for (iter = pcmcia_sockets; iter; iter = iter->next)
1742 monitor_printf(mon, "%s: %s\n", iter->socket->slot_string,
1743 iter->socket->attached ? iter->socket->card_string :
1744 "Empty");
1745}
1746
1747/***********************************************************/
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07001748/* I/O handling */
1749
1750typedef struct IOHandlerRecord {
1751 int fd;
David Turner4143d8f2010-09-10 11:05:02 +02001752 IOCanReadHandler *fd_read_poll;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07001753 IOHandler *fd_read;
1754 IOHandler *fd_write;
1755 int deleted;
1756 void *opaque;
1757 /* temporary data */
1758 struct pollfd *ufd;
1759 struct IOHandlerRecord *next;
1760} IOHandlerRecord;
1761
1762static IOHandlerRecord *first_io_handler;
1763
1764/* XXX: fd_read_poll should be suppressed, but an API change is
1765 necessary in the character devices to suppress fd_can_read(). */
1766int qemu_set_fd_handler2(int fd,
David Turner4143d8f2010-09-10 11:05:02 +02001767 IOCanReadHandler *fd_read_poll,
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07001768 IOHandler *fd_read,
1769 IOHandler *fd_write,
1770 void *opaque)
1771{
1772 IOHandlerRecord **pioh, *ioh;
1773
1774 if (!fd_read && !fd_write) {
1775 pioh = &first_io_handler;
1776 for(;;) {
1777 ioh = *pioh;
1778 if (ioh == NULL)
1779 break;
1780 if (ioh->fd == fd) {
1781 ioh->deleted = 1;
1782 break;
1783 }
1784 pioh = &ioh->next;
1785 }
1786 } else {
1787 for(ioh = first_io_handler; ioh != NULL; ioh = ioh->next) {
1788 if (ioh->fd == fd)
1789 goto found;
1790 }
1791 ioh = qemu_mallocz(sizeof(IOHandlerRecord));
1792 ioh->next = first_io_handler;
1793 first_io_handler = ioh;
1794 found:
1795 ioh->fd = fd;
1796 ioh->fd_read_poll = fd_read_poll;
1797 ioh->fd_read = fd_read;
1798 ioh->fd_write = fd_write;
1799 ioh->opaque = opaque;
1800 ioh->deleted = 0;
1801 }
1802 return 0;
1803}
1804
1805int qemu_set_fd_handler(int fd,
1806 IOHandler *fd_read,
1807 IOHandler *fd_write,
1808 void *opaque)
1809{
1810 return qemu_set_fd_handler2(fd, NULL, fd_read, fd_write, opaque);
1811}
1812
1813#ifdef _WIN32
1814/***********************************************************/
1815/* Polling handling */
1816
1817typedef struct PollingEntry {
1818 PollingFunc *func;
1819 void *opaque;
1820 struct PollingEntry *next;
1821} PollingEntry;
1822
1823static PollingEntry *first_polling_entry;
1824
1825int qemu_add_polling_cb(PollingFunc *func, void *opaque)
1826{
1827 PollingEntry **ppe, *pe;
1828 pe = qemu_mallocz(sizeof(PollingEntry));
1829 pe->func = func;
1830 pe->opaque = opaque;
1831 for(ppe = &first_polling_entry; *ppe != NULL; ppe = &(*ppe)->next);
1832 *ppe = pe;
1833 return 0;
1834}
1835
1836void qemu_del_polling_cb(PollingFunc *func, void *opaque)
1837{
1838 PollingEntry **ppe, *pe;
1839 for(ppe = &first_polling_entry; *ppe != NULL; ppe = &(*ppe)->next) {
1840 pe = *ppe;
1841 if (pe->func == func && pe->opaque == opaque) {
1842 *ppe = pe->next;
1843 qemu_free(pe);
1844 break;
1845 }
1846 }
1847}
1848
1849/***********************************************************/
1850/* Wait objects support */
1851typedef struct WaitObjects {
1852 int num;
1853 HANDLE events[MAXIMUM_WAIT_OBJECTS + 1];
1854 WaitObjectFunc *func[MAXIMUM_WAIT_OBJECTS + 1];
1855 void *opaque[MAXIMUM_WAIT_OBJECTS + 1];
1856} WaitObjects;
1857
1858static WaitObjects wait_objects = {0};
1859
1860int qemu_add_wait_object(HANDLE handle, WaitObjectFunc *func, void *opaque)
1861{
1862 WaitObjects *w = &wait_objects;
1863
1864 if (w->num >= MAXIMUM_WAIT_OBJECTS)
1865 return -1;
1866 w->events[w->num] = handle;
1867 w->func[w->num] = func;
1868 w->opaque[w->num] = opaque;
1869 w->num++;
1870 return 0;
1871}
1872
1873void qemu_del_wait_object(HANDLE handle, WaitObjectFunc *func, void *opaque)
1874{
1875 int i, found;
1876 WaitObjects *w = &wait_objects;
1877
1878 found = 0;
1879 for (i = 0; i < w->num; i++) {
1880 if (w->events[i] == handle)
1881 found = 1;
1882 if (found) {
1883 w->events[i] = w->events[i + 1];
1884 w->func[i] = w->func[i + 1];
1885 w->opaque[i] = w->opaque[i + 1];
1886 }
1887 }
1888 if (found)
1889 w->num--;
1890}
1891#endif
1892
1893/***********************************************************/
1894/* ram save/restore */
1895
1896static int ram_get_page(QEMUFile *f, uint8_t *buf, int len)
1897{
1898 int v;
1899
1900 v = qemu_get_byte(f);
1901 switch(v) {
1902 case 0:
1903 if (qemu_get_buffer(f, buf, len) != len)
1904 return -EIO;
1905 break;
1906 case 1:
1907 v = qemu_get_byte(f);
1908 memset(buf, v, len);
1909 break;
1910 default:
1911 return -EINVAL;
1912 }
1913
1914 if (qemu_file_has_error(f))
1915 return -EIO;
1916
1917 return 0;
1918}
1919
1920static int ram_load_v1(QEMUFile *f, void *opaque)
1921{
1922 int ret;
1923 ram_addr_t i;
1924
1925 if (qemu_get_be32(f) != last_ram_offset)
1926 return -EINVAL;
1927 for(i = 0; i < last_ram_offset; i+= TARGET_PAGE_SIZE) {
1928 ret = ram_get_page(f, qemu_get_ram_ptr(i), TARGET_PAGE_SIZE);
1929 if (ret)
1930 return ret;
1931 }
1932 return 0;
1933}
1934
1935#define BDRV_HASH_BLOCK_SIZE 1024
1936#define IOBUF_SIZE 4096
1937#define RAM_CBLOCK_MAGIC 0xfabe
1938
1939typedef struct RamDecompressState {
1940 z_stream zstream;
1941 QEMUFile *f;
1942 uint8_t buf[IOBUF_SIZE];
1943} RamDecompressState;
1944
1945static int ram_decompress_open(RamDecompressState *s, QEMUFile *f)
1946{
1947 int ret;
1948 memset(s, 0, sizeof(*s));
1949 s->f = f;
1950 ret = inflateInit(&s->zstream);
1951 if (ret != Z_OK)
1952 return -1;
1953 return 0;
1954}
1955
1956static int ram_decompress_buf(RamDecompressState *s, uint8_t *buf, int len)
1957{
1958 int ret, clen;
1959
1960 s->zstream.avail_out = len;
1961 s->zstream.next_out = buf;
1962 while (s->zstream.avail_out > 0) {
1963 if (s->zstream.avail_in == 0) {
1964 if (qemu_get_be16(s->f) != RAM_CBLOCK_MAGIC)
1965 return -1;
1966 clen = qemu_get_be16(s->f);
1967 if (clen > IOBUF_SIZE)
1968 return -1;
1969 qemu_get_buffer(s->f, s->buf, clen);
1970 s->zstream.avail_in = clen;
1971 s->zstream.next_in = s->buf;
1972 }
1973 ret = inflate(&s->zstream, Z_PARTIAL_FLUSH);
1974 if (ret != Z_OK && ret != Z_STREAM_END) {
1975 return -1;
1976 }
1977 }
1978 return 0;
1979}
1980
1981static void ram_decompress_close(RamDecompressState *s)
1982{
1983 inflateEnd(&s->zstream);
1984}
1985
1986#define RAM_SAVE_FLAG_FULL 0x01
1987#define RAM_SAVE_FLAG_COMPRESS 0x02
1988#define RAM_SAVE_FLAG_MEM_SIZE 0x04
1989#define RAM_SAVE_FLAG_PAGE 0x08
1990#define RAM_SAVE_FLAG_EOS 0x10
1991
1992static int is_dup_page(uint8_t *page, uint8_t ch)
1993{
1994 uint32_t val = ch << 24 | ch << 16 | ch << 8 | ch;
1995 uint32_t *array = (uint32_t *)page;
1996 int i;
1997
1998 for (i = 0; i < (TARGET_PAGE_SIZE / 4); i++) {
1999 if (array[i] != val)
2000 return 0;
2001 }
2002
2003 return 1;
2004}
2005
2006static int ram_save_block(QEMUFile *f)
2007{
2008 static ram_addr_t current_addr = 0;
2009 ram_addr_t saved_addr = current_addr;
2010 ram_addr_t addr = 0;
2011 int found = 0;
2012
2013 while (addr < last_ram_offset) {
2014 if (cpu_physical_memory_get_dirty(current_addr, MIGRATION_DIRTY_FLAG)) {
2015 uint8_t *p;
2016
2017 cpu_physical_memory_reset_dirty(current_addr,
2018 current_addr + TARGET_PAGE_SIZE,
2019 MIGRATION_DIRTY_FLAG);
2020
2021 p = qemu_get_ram_ptr(current_addr);
2022
2023 if (is_dup_page(p, *p)) {
2024 qemu_put_be64(f, current_addr | RAM_SAVE_FLAG_COMPRESS);
2025 qemu_put_byte(f, *p);
2026 } else {
2027 qemu_put_be64(f, current_addr | RAM_SAVE_FLAG_PAGE);
2028 qemu_put_buffer(f, p, TARGET_PAGE_SIZE);
2029 }
2030
2031 found = 1;
2032 break;
2033 }
2034 addr += TARGET_PAGE_SIZE;
2035 current_addr = (saved_addr + addr) % last_ram_offset;
2036 }
2037
2038 return found;
2039}
2040
2041static uint64_t bytes_transferred = 0;
2042
2043static ram_addr_t ram_save_remaining(void)
2044{
2045 ram_addr_t addr;
2046 ram_addr_t count = 0;
2047
2048 for (addr = 0; addr < last_ram_offset; addr += TARGET_PAGE_SIZE) {
2049 if (cpu_physical_memory_get_dirty(addr, MIGRATION_DIRTY_FLAG))
2050 count++;
2051 }
2052
2053 return count;
2054}
2055
2056uint64_t ram_bytes_remaining(void)
2057{
2058 return ram_save_remaining() * TARGET_PAGE_SIZE;
2059}
2060
2061uint64_t ram_bytes_transferred(void)
2062{
2063 return bytes_transferred;
2064}
2065
2066uint64_t ram_bytes_total(void)
2067{
2068 return last_ram_offset;
2069}
2070
2071static int ram_save_live(QEMUFile *f, int stage, void *opaque)
2072{
2073 ram_addr_t addr;
2074 uint64_t bytes_transferred_last;
2075 double bwidth = 0;
2076 uint64_t expected_time = 0;
2077
2078 cpu_physical_sync_dirty_bitmap(0, TARGET_PHYS_ADDR_MAX);
2079
2080 if (stage == 1) {
2081 /* Make sure all dirty bits are set */
2082 for (addr = 0; addr < last_ram_offset; addr += TARGET_PAGE_SIZE) {
2083 if (!cpu_physical_memory_get_dirty(addr, MIGRATION_DIRTY_FLAG))
2084 cpu_physical_memory_set_dirty(addr);
2085 }
2086
2087 /* Enable dirty memory tracking */
2088 cpu_physical_memory_set_dirty_tracking(1);
2089
2090 qemu_put_be64(f, last_ram_offset | RAM_SAVE_FLAG_MEM_SIZE);
2091 }
2092
2093 bytes_transferred_last = bytes_transferred;
David Turner6a9ef172010-09-09 22:54:36 +02002094 bwidth = qemu_get_clock_ns(rt_clock);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07002095
2096 while (!qemu_file_rate_limit(f)) {
2097 int ret;
2098
2099 ret = ram_save_block(f);
2100 bytes_transferred += ret * TARGET_PAGE_SIZE;
2101 if (ret == 0) /* no more blocks */
2102 break;
2103 }
2104
David Turner6a9ef172010-09-09 22:54:36 +02002105 bwidth = qemu_get_clock_ns(rt_clock) - bwidth;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07002106 bwidth = (bytes_transferred - bytes_transferred_last) / bwidth;
2107
2108 /* if we haven't transferred anything this round, force expected_time to a
2109 * a very high value, but without crashing */
2110 if (bwidth == 0)
2111 bwidth = 0.000001;
2112
2113 /* try transferring iterative blocks of memory */
2114
2115 if (stage == 3) {
2116
2117 /* flush all remaining blocks regardless of rate limiting */
2118 while (ram_save_block(f) != 0) {
2119 bytes_transferred += TARGET_PAGE_SIZE;
2120 }
2121 cpu_physical_memory_set_dirty_tracking(0);
2122 }
2123
2124 qemu_put_be64(f, RAM_SAVE_FLAG_EOS);
2125
2126 expected_time = ram_save_remaining() * TARGET_PAGE_SIZE / bwidth;
2127
2128 return (stage == 2) && (expected_time <= migrate_max_downtime());
2129}
2130
2131static int ram_load_dead(QEMUFile *f, void *opaque)
2132{
2133 RamDecompressState s1, *s = &s1;
2134 uint8_t buf[10];
2135 ram_addr_t i;
2136
2137 if (ram_decompress_open(s, f) < 0)
2138 return -EINVAL;
2139 for(i = 0; i < last_ram_offset; i+= BDRV_HASH_BLOCK_SIZE) {
2140 if (ram_decompress_buf(s, buf, 1) < 0) {
2141 fprintf(stderr, "Error while reading ram block header\n");
2142 goto error;
2143 }
2144 if (buf[0] == 0) {
2145 if (ram_decompress_buf(s, qemu_get_ram_ptr(i),
2146 BDRV_HASH_BLOCK_SIZE) < 0) {
2147 fprintf(stderr, "Error while reading ram block address=0x%08" PRIx64, (uint64_t)i);
2148 goto error;
2149 }
2150 } else {
2151 error:
2152 printf("Error block header\n");
2153 return -EINVAL;
2154 }
2155 }
2156 ram_decompress_close(s);
2157
2158 return 0;
2159}
2160
2161static int ram_load(QEMUFile *f, void *opaque, int version_id)
2162{
2163 ram_addr_t addr;
2164 int flags;
2165
2166 if (version_id == 1)
2167 return ram_load_v1(f, opaque);
2168
2169 if (version_id == 2) {
2170 if (qemu_get_be32(f) != last_ram_offset)
2171 return -EINVAL;
2172 return ram_load_dead(f, opaque);
2173 }
2174
2175 if (version_id != 3)
2176 return -EINVAL;
2177
2178 do {
2179 addr = qemu_get_be64(f);
2180
2181 flags = addr & ~TARGET_PAGE_MASK;
2182 addr &= TARGET_PAGE_MASK;
2183
2184 if (flags & RAM_SAVE_FLAG_MEM_SIZE) {
2185 if (addr != last_ram_offset)
2186 return -EINVAL;
2187 }
2188
2189 if (flags & RAM_SAVE_FLAG_FULL) {
2190 if (ram_load_dead(f, opaque) < 0)
2191 return -EINVAL;
2192 }
Vladimir Chtchetkined81e6d12010-06-15 16:46:32 -07002193
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07002194 if (flags & RAM_SAVE_FLAG_COMPRESS) {
2195 uint8_t ch = qemu_get_byte(f);
2196 memset(qemu_get_ram_ptr(addr), ch, TARGET_PAGE_SIZE);
2197 } else if (flags & RAM_SAVE_FLAG_PAGE)
2198 qemu_get_buffer(f, qemu_get_ram_ptr(addr), TARGET_PAGE_SIZE);
2199 } while (!(flags & RAM_SAVE_FLAG_EOS));
2200
2201 return 0;
2202}
2203
2204void qemu_service_io(void)
2205{
2206 qemu_notify_event();
2207}
2208
2209/***********************************************************/
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07002210/* machine registration */
2211
2212static QEMUMachine *first_machine = NULL;
2213QEMUMachine *current_machine = NULL;
2214
2215int qemu_register_machine(QEMUMachine *m)
2216{
2217 QEMUMachine **pm;
2218 pm = &first_machine;
2219 while (*pm != NULL)
2220 pm = &(*pm)->next;
2221 m->next = NULL;
2222 *pm = m;
2223 return 0;
2224}
2225
2226static QEMUMachine *find_machine(const char *name)
2227{
2228 QEMUMachine *m;
2229
2230 for(m = first_machine; m != NULL; m = m->next) {
2231 if (!strcmp(m->name, name))
2232 return m;
2233 }
2234 return NULL;
2235}
2236
2237static QEMUMachine *find_default_machine(void)
2238{
2239 QEMUMachine *m;
2240
2241 for(m = first_machine; m != NULL; m = m->next) {
2242 if (m->is_default) {
2243 return m;
2244 }
2245 }
2246 return NULL;
2247}
2248
2249/***********************************************************/
2250/* main execution loop */
2251
2252static void gui_update(void *opaque)
2253{
2254 uint64_t interval = GUI_REFRESH_INTERVAL;
2255 DisplayState *ds = opaque;
2256 DisplayChangeListener *dcl = ds->listeners;
2257
2258 dpy_refresh(ds);
2259
2260 while (dcl != NULL) {
2261 if (dcl->gui_timer_interval &&
2262 dcl->gui_timer_interval < interval)
2263 interval = dcl->gui_timer_interval;
2264 dcl = dcl->next;
2265 }
2266 qemu_mod_timer(ds->gui_timer, interval + qemu_get_clock(rt_clock));
2267}
2268
2269static void nographic_update(void *opaque)
2270{
2271 uint64_t interval = GUI_REFRESH_INTERVAL;
2272
2273 qemu_mod_timer(nographic_timer, interval + qemu_get_clock(rt_clock));
2274}
2275
2276struct vm_change_state_entry {
2277 VMChangeStateHandler *cb;
2278 void *opaque;
David 'Digit' Turnera5d41202010-05-10 18:37:10 -07002279 QLIST_ENTRY (vm_change_state_entry) entries;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07002280};
2281
David 'Digit' Turnera5d41202010-05-10 18:37:10 -07002282static QLIST_HEAD(vm_change_state_head, vm_change_state_entry) vm_change_state_head;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07002283
2284VMChangeStateEntry *qemu_add_vm_change_state_handler(VMChangeStateHandler *cb,
2285 void *opaque)
2286{
2287 VMChangeStateEntry *e;
2288
2289 e = qemu_mallocz(sizeof (*e));
2290
2291 e->cb = cb;
2292 e->opaque = opaque;
David 'Digit' Turnera5d41202010-05-10 18:37:10 -07002293 QLIST_INSERT_HEAD(&vm_change_state_head, e, entries);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07002294 return e;
2295}
2296
2297void qemu_del_vm_change_state_handler(VMChangeStateEntry *e)
2298{
David 'Digit' Turnera5d41202010-05-10 18:37:10 -07002299 QLIST_REMOVE (e, entries);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07002300 qemu_free (e);
2301}
2302
2303static void vm_state_notify(int running, int reason)
2304{
2305 VMChangeStateEntry *e;
2306
2307 for (e = vm_change_state_head.lh_first; e; e = e->entries.le_next) {
2308 e->cb(e->opaque, running, reason);
2309 }
2310}
2311
2312static void resume_all_vcpus(void);
2313static void pause_all_vcpus(void);
2314
2315void vm_start(void)
2316{
2317 if (!vm_running) {
2318 cpu_enable_ticks();
2319 vm_running = 1;
2320 vm_state_notify(1, 0);
David Turner6a9ef172010-09-09 22:54:36 +02002321 //qemu_rearm_alarm_timer(alarm_timer);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07002322 resume_all_vcpus();
2323 }
2324}
2325
2326/* reset/shutdown handler */
2327
2328typedef struct QEMUResetEntry {
2329 QEMUResetHandler *func;
2330 void *opaque;
2331 int order;
2332 struct QEMUResetEntry *next;
2333} QEMUResetEntry;
2334
2335static QEMUResetEntry *first_reset_entry;
2336static int reset_requested;
2337static int shutdown_requested;
2338static int powerdown_requested;
2339static int debug_requested;
2340static int vmstop_requested;
2341
2342int qemu_shutdown_requested(void)
2343{
2344 int r = shutdown_requested;
2345 shutdown_requested = 0;
2346 return r;
2347}
2348
2349int qemu_reset_requested(void)
2350{
2351 int r = reset_requested;
2352 reset_requested = 0;
2353 return r;
2354}
2355
2356int qemu_powerdown_requested(void)
2357{
2358 int r = powerdown_requested;
2359 powerdown_requested = 0;
2360 return r;
2361}
2362
2363static int qemu_debug_requested(void)
2364{
2365 int r = debug_requested;
2366 debug_requested = 0;
2367 return r;
2368}
2369
2370static int qemu_vmstop_requested(void)
2371{
2372 int r = vmstop_requested;
2373 vmstop_requested = 0;
2374 return r;
2375}
2376
2377static void do_vm_stop(int reason)
2378{
2379 if (vm_running) {
2380 cpu_disable_ticks();
2381 vm_running = 0;
2382 pause_all_vcpus();
2383 vm_state_notify(0, reason);
2384 }
2385}
2386
2387void qemu_register_reset(QEMUResetHandler *func, int order, void *opaque)
2388{
2389 QEMUResetEntry **pre, *re;
2390
2391 pre = &first_reset_entry;
2392 while (*pre != NULL && (*pre)->order >= order) {
2393 pre = &(*pre)->next;
2394 }
2395 re = qemu_mallocz(sizeof(QEMUResetEntry));
2396 re->func = func;
2397 re->opaque = opaque;
2398 re->order = order;
2399 re->next = NULL;
2400 *pre = re;
2401}
2402
2403void qemu_system_reset(void)
2404{
2405 QEMUResetEntry *re;
2406
2407 /* reset all devices */
2408 for(re = first_reset_entry; re != NULL; re = re->next) {
2409 re->func(re->opaque);
2410 }
2411}
2412
2413void qemu_system_reset_request(void)
2414{
2415 if (no_reboot) {
2416 shutdown_requested = 1;
2417 } else {
2418 reset_requested = 1;
2419 }
2420 qemu_notify_event();
2421}
2422
2423void qemu_system_shutdown_request(void)
2424{
2425 shutdown_requested = 1;
2426 qemu_notify_event();
2427}
2428
2429void qemu_system_powerdown_request(void)
2430{
2431 powerdown_requested = 1;
2432 qemu_notify_event();
2433}
2434
2435#ifdef CONFIG_IOTHREAD
2436static void qemu_system_vmstop_request(int reason)
2437{
2438 vmstop_requested = reason;
2439 qemu_notify_event();
2440}
2441#endif
2442
2443#ifndef _WIN32
2444static int io_thread_fd = -1;
2445
David 'Digit' Turnerc34e8dc2010-09-13 02:47:01 -07002446#if 0
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07002447static void qemu_event_increment(void)
2448{
2449 static const char byte = 0;
2450
2451 if (io_thread_fd == -1)
2452 return;
2453
2454 write(io_thread_fd, &byte, sizeof(byte));
2455}
David 'Digit' Turnerc34e8dc2010-09-13 02:47:01 -07002456#endif
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07002457
2458static void qemu_event_read(void *opaque)
2459{
2460 int fd = (unsigned long)opaque;
2461 ssize_t len;
2462
2463 /* Drain the notify pipe */
2464 do {
2465 char buffer[512];
2466 len = read(fd, buffer, sizeof(buffer));
2467 } while ((len == -1 && errno == EINTR) || len > 0);
2468}
2469
2470static int qemu_event_init(void)
2471{
2472 int err;
2473 int fds[2];
2474
2475 err = pipe(fds);
2476 if (err == -1)
2477 return -errno;
2478
2479 err = fcntl_setfl(fds[0], O_NONBLOCK);
2480 if (err < 0)
2481 goto fail;
2482
2483 err = fcntl_setfl(fds[1], O_NONBLOCK);
2484 if (err < 0)
2485 goto fail;
2486
2487 qemu_set_fd_handler2(fds[0], NULL, qemu_event_read, NULL,
2488 (void *)(unsigned long)fds[0]);
2489
2490 io_thread_fd = fds[1];
2491 return 0;
2492
2493fail:
2494 close(fds[0]);
2495 close(fds[1]);
2496 return err;
2497}
2498#else
2499HANDLE qemu_event_handle;
2500
2501static void dummy_event_handler(void *opaque)
2502{
2503}
2504
2505static int qemu_event_init(void)
2506{
2507 qemu_event_handle = CreateEvent(NULL, FALSE, FALSE, NULL);
2508 if (!qemu_event_handle) {
2509 perror("Failed CreateEvent");
2510 return -1;
2511 }
2512 qemu_add_wait_object(qemu_event_handle, dummy_event_handler, NULL);
2513 return 0;
2514}
2515
David 'Digit' Turner4e024bb2010-09-22 14:19:28 +02002516#if 0
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07002517static void qemu_event_increment(void)
2518{
2519 SetEvent(qemu_event_handle);
2520}
2521#endif
David 'Digit' Turner4e024bb2010-09-22 14:19:28 +02002522#endif
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07002523
2524static int cpu_can_run(CPUState *env)
2525{
2526 if (env->stop)
2527 return 0;
2528 if (env->stopped)
2529 return 0;
2530 return 1;
2531}
2532
2533#ifndef CONFIG_IOTHREAD
2534static int qemu_init_main_loop(void)
2535{
2536 return qemu_event_init();
2537}
2538
2539void qemu_init_vcpu(void *_env)
2540{
2541 CPUState *env = _env;
2542
2543 if (kvm_enabled())
2544 kvm_init_vcpu(env);
2545 return;
2546}
2547
2548int qemu_cpu_self(void *env)
2549{
2550 return 1;
2551}
2552
2553static void resume_all_vcpus(void)
2554{
2555}
2556
2557static void pause_all_vcpus(void)
2558{
2559}
2560
2561void qemu_cpu_kick(void *env)
2562{
2563 return;
2564}
2565
2566void qemu_notify_event(void)
2567{
2568 CPUState *env = cpu_single_env;
2569
2570 if (env) {
2571 cpu_exit(env);
2572#ifdef USE_KQEMU
2573 if (env->kqemu_enabled)
2574 kqemu_cpu_interrupt(env);
2575#endif
2576 }
2577}
2578
2579#define qemu_mutex_lock_iothread() do { } while (0)
2580#define qemu_mutex_unlock_iothread() do { } while (0)
2581
2582void vm_stop(int reason)
2583{
2584 do_vm_stop(reason);
2585}
2586
2587#else /* CONFIG_IOTHREAD */
2588
2589#include "qemu-thread.h"
2590
2591QemuMutex qemu_global_mutex;
2592static QemuMutex qemu_fair_mutex;
2593
2594static QemuThread io_thread;
2595
2596static QemuThread *tcg_cpu_thread;
2597static QemuCond *tcg_halt_cond;
2598
2599static int qemu_system_ready;
2600/* cpu creation */
2601static QemuCond qemu_cpu_cond;
2602/* system init */
2603static QemuCond qemu_system_cond;
2604static QemuCond qemu_pause_cond;
2605
2606static void block_io_signals(void);
2607static void unblock_io_signals(void);
2608static int tcg_has_work(void);
2609
2610static int qemu_init_main_loop(void)
2611{
2612 int ret;
2613
2614 ret = qemu_event_init();
2615 if (ret)
2616 return ret;
2617
2618 qemu_cond_init(&qemu_pause_cond);
2619 qemu_mutex_init(&qemu_fair_mutex);
2620 qemu_mutex_init(&qemu_global_mutex);
2621 qemu_mutex_lock(&qemu_global_mutex);
2622
2623 unblock_io_signals();
2624 qemu_thread_self(&io_thread);
2625
2626 return 0;
2627}
2628
2629static void qemu_wait_io_event(CPUState *env)
2630{
2631 while (!tcg_has_work())
2632 qemu_cond_timedwait(env->halt_cond, &qemu_global_mutex, 1000);
2633
2634 qemu_mutex_unlock(&qemu_global_mutex);
2635
2636 /*
2637 * Users of qemu_global_mutex can be starved, having no chance
2638 * to acquire it since this path will get to it first.
2639 * So use another lock to provide fairness.
2640 */
2641 qemu_mutex_lock(&qemu_fair_mutex);
2642 qemu_mutex_unlock(&qemu_fair_mutex);
2643
2644 qemu_mutex_lock(&qemu_global_mutex);
2645 if (env->stop) {
2646 env->stop = 0;
2647 env->stopped = 1;
2648 qemu_cond_signal(&qemu_pause_cond);
2649 }
2650}
2651
2652static int qemu_cpu_exec(CPUState *env);
2653
2654static void *kvm_cpu_thread_fn(void *arg)
2655{
2656 CPUState *env = arg;
2657
2658 block_io_signals();
2659 qemu_thread_self(env->thread);
2660
2661 /* signal CPU creation */
2662 qemu_mutex_lock(&qemu_global_mutex);
2663 env->created = 1;
2664 qemu_cond_signal(&qemu_cpu_cond);
2665
2666 /* and wait for machine initialization */
2667 while (!qemu_system_ready)
2668 qemu_cond_timedwait(&qemu_system_cond, &qemu_global_mutex, 100);
2669
2670 while (1) {
2671 if (cpu_can_run(env))
2672 qemu_cpu_exec(env);
2673 qemu_wait_io_event(env);
2674 }
2675
2676 return NULL;
2677}
2678
2679static void tcg_cpu_exec(void);
2680
2681static void *tcg_cpu_thread_fn(void *arg)
2682{
2683 CPUState *env = arg;
2684
2685 block_io_signals();
2686 qemu_thread_self(env->thread);
2687
2688 /* signal CPU creation */
2689 qemu_mutex_lock(&qemu_global_mutex);
2690 for (env = first_cpu; env != NULL; env = env->next_cpu)
2691 env->created = 1;
2692 qemu_cond_signal(&qemu_cpu_cond);
2693
2694 /* and wait for machine initialization */
2695 while (!qemu_system_ready)
2696 qemu_cond_timedwait(&qemu_system_cond, &qemu_global_mutex, 100);
2697
2698 while (1) {
2699 tcg_cpu_exec();
2700 qemu_wait_io_event(cur_cpu);
2701 }
2702
2703 return NULL;
2704}
2705
2706void qemu_cpu_kick(void *_env)
2707{
2708 CPUState *env = _env;
2709 qemu_cond_broadcast(env->halt_cond);
2710 if (kvm_enabled())
2711 qemu_thread_signal(env->thread, SIGUSR1);
2712}
2713
2714int qemu_cpu_self(void *env)
2715{
2716 return (cpu_single_env != NULL);
2717}
2718
2719static void cpu_signal(int sig)
2720{
2721 if (cpu_single_env)
2722 cpu_exit(cpu_single_env);
2723}
2724
2725static void block_io_signals(void)
2726{
2727 sigset_t set;
2728 struct sigaction sigact;
2729
2730 sigemptyset(&set);
2731 sigaddset(&set, SIGUSR2);
2732 sigaddset(&set, SIGIO);
2733 sigaddset(&set, SIGALRM);
2734 pthread_sigmask(SIG_BLOCK, &set, NULL);
2735
2736 sigemptyset(&set);
2737 sigaddset(&set, SIGUSR1);
2738 pthread_sigmask(SIG_UNBLOCK, &set, NULL);
2739
2740 memset(&sigact, 0, sizeof(sigact));
2741 sigact.sa_handler = cpu_signal;
2742 sigaction(SIGUSR1, &sigact, NULL);
2743}
2744
2745static void unblock_io_signals(void)
2746{
2747 sigset_t set;
2748
2749 sigemptyset(&set);
2750 sigaddset(&set, SIGUSR2);
2751 sigaddset(&set, SIGIO);
2752 sigaddset(&set, SIGALRM);
2753 pthread_sigmask(SIG_UNBLOCK, &set, NULL);
2754
2755 sigemptyset(&set);
2756 sigaddset(&set, SIGUSR1);
2757 pthread_sigmask(SIG_BLOCK, &set, NULL);
2758}
2759
2760static void qemu_signal_lock(unsigned int msecs)
2761{
2762 qemu_mutex_lock(&qemu_fair_mutex);
2763
2764 while (qemu_mutex_trylock(&qemu_global_mutex)) {
2765 qemu_thread_signal(tcg_cpu_thread, SIGUSR1);
2766 if (!qemu_mutex_timedlock(&qemu_global_mutex, msecs))
2767 break;
2768 }
2769 qemu_mutex_unlock(&qemu_fair_mutex);
2770}
2771
David 'Digit' Turnerc34e8dc2010-09-13 02:47:01 -07002772void qemu_mutex_lock_iothread(void)
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07002773{
2774 if (kvm_enabled()) {
2775 qemu_mutex_lock(&qemu_fair_mutex);
2776 qemu_mutex_lock(&qemu_global_mutex);
2777 qemu_mutex_unlock(&qemu_fair_mutex);
2778 } else
2779 qemu_signal_lock(100);
2780}
2781
David 'Digit' Turnerc34e8dc2010-09-13 02:47:01 -07002782void qemu_mutex_unlock_iothread(void)
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07002783{
2784 qemu_mutex_unlock(&qemu_global_mutex);
2785}
2786
2787static int all_vcpus_paused(void)
2788{
2789 CPUState *penv = first_cpu;
2790
2791 while (penv) {
2792 if (!penv->stopped)
2793 return 0;
2794 penv = (CPUState *)penv->next_cpu;
2795 }
2796
2797 return 1;
2798}
2799
2800static void pause_all_vcpus(void)
2801{
2802 CPUState *penv = first_cpu;
2803
2804 while (penv) {
2805 penv->stop = 1;
2806 qemu_thread_signal(penv->thread, SIGUSR1);
2807 qemu_cpu_kick(penv);
2808 penv = (CPUState *)penv->next_cpu;
2809 }
2810
2811 while (!all_vcpus_paused()) {
2812 qemu_cond_timedwait(&qemu_pause_cond, &qemu_global_mutex, 100);
2813 penv = first_cpu;
2814 while (penv) {
2815 qemu_thread_signal(penv->thread, SIGUSR1);
2816 penv = (CPUState *)penv->next_cpu;
2817 }
2818 }
2819}
2820
2821static void resume_all_vcpus(void)
2822{
2823 CPUState *penv = first_cpu;
2824
2825 while (penv) {
2826 penv->stop = 0;
2827 penv->stopped = 0;
2828 qemu_thread_signal(penv->thread, SIGUSR1);
2829 qemu_cpu_kick(penv);
2830 penv = (CPUState *)penv->next_cpu;
2831 }
2832}
2833
2834static void tcg_init_vcpu(void *_env)
2835{
2836 CPUState *env = _env;
2837 /* share a single thread for all cpus with TCG */
2838 if (!tcg_cpu_thread) {
2839 env->thread = qemu_mallocz(sizeof(QemuThread));
2840 env->halt_cond = qemu_mallocz(sizeof(QemuCond));
2841 qemu_cond_init(env->halt_cond);
2842 qemu_thread_create(env->thread, tcg_cpu_thread_fn, env);
2843 while (env->created == 0)
2844 qemu_cond_timedwait(&qemu_cpu_cond, &qemu_global_mutex, 100);
2845 tcg_cpu_thread = env->thread;
2846 tcg_halt_cond = env->halt_cond;
2847 } else {
2848 env->thread = tcg_cpu_thread;
2849 env->halt_cond = tcg_halt_cond;
2850 }
2851}
2852
2853static void kvm_start_vcpu(CPUState *env)
2854{
2855#if 0
2856 kvm_init_vcpu(env);
2857 env->thread = qemu_mallocz(sizeof(QemuThread));
2858 env->halt_cond = qemu_mallocz(sizeof(QemuCond));
2859 qemu_cond_init(env->halt_cond);
2860 qemu_thread_create(env->thread, kvm_cpu_thread_fn, env);
2861 while (env->created == 0)
2862 qemu_cond_timedwait(&qemu_cpu_cond, &qemu_global_mutex, 100);
2863#endif
2864}
2865
2866void qemu_init_vcpu(void *_env)
2867{
2868 CPUState *env = _env;
2869
2870 if (kvm_enabled())
2871 kvm_start_vcpu(env);
2872 else
2873 tcg_init_vcpu(env);
2874}
2875
2876void qemu_notify_event(void)
2877{
2878 qemu_event_increment();
2879}
2880
2881void vm_stop(int reason)
2882{
2883 QemuThread me;
2884 qemu_thread_self(&me);
2885
2886 if (!qemu_thread_equal(&me, &io_thread)) {
2887 qemu_system_vmstop_request(reason);
2888 /*
2889 * FIXME: should not return to device code in case
2890 * vm_stop() has been requested.
2891 */
2892 if (cpu_single_env) {
2893 cpu_exit(cpu_single_env);
2894 cpu_single_env->stop = 1;
2895 }
2896 return;
2897 }
2898 do_vm_stop(reason);
2899}
2900
2901#endif
2902
2903
2904#ifdef _WIN32
2905static void host_main_loop_wait(int *timeout)
2906{
2907 int ret, ret2, i;
2908 PollingEntry *pe;
2909
2910
2911 /* XXX: need to suppress polling by better using win32 events */
2912 ret = 0;
2913 for(pe = first_polling_entry; pe != NULL; pe = pe->next) {
2914 ret |= pe->func(pe->opaque);
2915 }
2916 if (ret == 0) {
2917 int err;
2918 WaitObjects *w = &wait_objects;
2919
2920 ret = WaitForMultipleObjects(w->num, w->events, FALSE, *timeout);
2921 if (WAIT_OBJECT_0 + 0 <= ret && ret <= WAIT_OBJECT_0 + w->num - 1) {
2922 if (w->func[ret - WAIT_OBJECT_0])
2923 w->func[ret - WAIT_OBJECT_0](w->opaque[ret - WAIT_OBJECT_0]);
2924
2925 /* Check for additional signaled events */
2926 for(i = (ret - WAIT_OBJECT_0 + 1); i < w->num; i++) {
2927
2928 /* Check if event is signaled */
2929 ret2 = WaitForSingleObject(w->events[i], 0);
2930 if(ret2 == WAIT_OBJECT_0) {
2931 if (w->func[i])
2932 w->func[i](w->opaque[i]);
2933 } else if (ret2 == WAIT_TIMEOUT) {
2934 } else {
2935 err = GetLastError();
2936 fprintf(stderr, "WaitForSingleObject error %d %d\n", i, err);
2937 }
2938 }
2939 } else if (ret == WAIT_TIMEOUT) {
2940 } else {
2941 err = GetLastError();
2942 fprintf(stderr, "WaitForMultipleObjects error %d %d\n", ret, err);
2943 }
2944 }
2945
2946 *timeout = 0;
2947}
2948#else
2949static void host_main_loop_wait(int *timeout)
2950{
2951}
2952#endif
2953
2954void main_loop_wait(int timeout)
2955{
2956 IOHandlerRecord *ioh;
2957 fd_set rfds, wfds, xfds;
2958 int ret, nfds;
2959 struct timeval tv;
2960
2961 qemu_bh_update_timeout(&timeout);
2962
2963 host_main_loop_wait(&timeout);
2964
2965 /* poll any events */
2966 /* XXX: separate device handlers from system ones */
2967 nfds = -1;
2968 FD_ZERO(&rfds);
2969 FD_ZERO(&wfds);
2970 FD_ZERO(&xfds);
2971 for(ioh = first_io_handler; ioh != NULL; ioh = ioh->next) {
2972 if (ioh->deleted)
2973 continue;
2974 if (ioh->fd_read &&
2975 (!ioh->fd_read_poll ||
2976 ioh->fd_read_poll(ioh->opaque) != 0)) {
2977 FD_SET(ioh->fd, &rfds);
2978 if (ioh->fd > nfds)
2979 nfds = ioh->fd;
2980 }
2981 if (ioh->fd_write) {
2982 FD_SET(ioh->fd, &wfds);
2983 if (ioh->fd > nfds)
2984 nfds = ioh->fd;
2985 }
2986 }
2987
2988 tv.tv_sec = timeout / 1000;
2989 tv.tv_usec = (timeout % 1000) * 1000;
2990
2991#if defined(CONFIG_SLIRP)
2992 if (slirp_is_inited()) {
2993 slirp_select_fill(&nfds, &rfds, &wfds, &xfds);
2994 }
2995#endif
2996 qemu_mutex_unlock_iothread();
2997 ret = select(nfds + 1, &rfds, &wfds, &xfds, &tv);
2998 qemu_mutex_lock_iothread();
2999 if (ret > 0) {
3000 IOHandlerRecord **pioh;
3001
3002 for(ioh = first_io_handler; ioh != NULL; ioh = ioh->next) {
3003 if (!ioh->deleted && ioh->fd_read && FD_ISSET(ioh->fd, &rfds)) {
3004 ioh->fd_read(ioh->opaque);
3005 }
3006 if (!ioh->deleted && ioh->fd_write && FD_ISSET(ioh->fd, &wfds)) {
3007 ioh->fd_write(ioh->opaque);
3008 }
3009 }
3010
David 'Digit' Turner6b512812010-10-15 15:05:04 +02003011 /* remove deleted IO handlers */
3012 pioh = &first_io_handler;
3013 while (*pioh) {
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003014 ioh = *pioh;
3015 if (ioh->deleted) {
3016 *pioh = ioh->next;
3017 qemu_free(ioh);
3018 } else
3019 pioh = &ioh->next;
3020 }
3021 }
3022#if defined(CONFIG_SLIRP)
3023 if (slirp_is_inited()) {
3024 if (ret < 0) {
3025 FD_ZERO(&rfds);
3026 FD_ZERO(&wfds);
3027 FD_ZERO(&xfds);
3028 }
3029 slirp_select_poll(&rfds, &wfds, &xfds);
3030 }
3031#endif
3032 charpipe_poll();
3033
David Turner6a9ef172010-09-09 22:54:36 +02003034 qemu_run_all_timers();
David 'Digit' Turnera7fb77d2010-05-10 23:50:54 -07003035
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003036 /* Check bottom-halves last in case any of the earlier events triggered
3037 them. */
3038 qemu_bh_poll();
3039
3040}
3041
3042static int qemu_cpu_exec(CPUState *env)
3043{
3044 int ret;
3045#ifdef CONFIG_PROFILER
3046 int64_t ti;
3047#endif
3048
3049#ifdef CONFIG_PROFILER
3050 ti = profile_getclock();
3051#endif
3052 if (use_icount) {
3053 int64_t count;
3054 int decr;
3055 qemu_icount -= (env->icount_decr.u16.low + env->icount_extra);
3056 env->icount_decr.u16.low = 0;
3057 env->icount_extra = 0;
3058 count = qemu_next_deadline();
3059 count = (count + (1 << icount_time_shift) - 1)
3060 >> icount_time_shift;
3061 qemu_icount += count;
3062 decr = (count > 0xffff) ? 0xffff : count;
3063 count -= decr;
3064 env->icount_decr.u16.low = decr;
3065 env->icount_extra = count;
3066 }
David 'Digit' Turnera577fca2009-10-15 18:18:09 -07003067#ifdef CONFIG_TRACE
3068 if (tbflush_requested) {
3069 tbflush_requested = 0;
3070 tb_flush(env);
3071 return EXCP_INTERRUPT;
3072 }
3073#endif
3074
3075
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003076 ret = cpu_exec(env);
3077#ifdef CONFIG_PROFILER
3078 qemu_time += profile_getclock() - ti;
3079#endif
3080 if (use_icount) {
3081 /* Fold pending instructions back into the
3082 instruction counter, and clear the interrupt flag. */
3083 qemu_icount -= (env->icount_decr.u16.low
3084 + env->icount_extra);
3085 env->icount_decr.u32 = 0;
3086 env->icount_extra = 0;
3087 }
3088 return ret;
3089}
3090
3091static void tcg_cpu_exec(void)
3092{
3093 int ret = 0;
3094
3095 if (next_cpu == NULL)
3096 next_cpu = first_cpu;
3097 for (; next_cpu != NULL; next_cpu = next_cpu->next_cpu) {
3098 CPUState *env = cur_cpu = next_cpu;
3099
3100 if (!vm_running)
3101 break;
David 'Digit' Turner6b512812010-10-15 15:05:04 +02003102 if (qemu_timer_alarm_pending()) {
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003103 break;
3104 }
3105 if (cpu_can_run(env))
3106 ret = qemu_cpu_exec(env);
3107 if (ret == EXCP_DEBUG) {
3108 gdb_set_stop_cpu(env);
3109 debug_requested = 1;
3110 break;
3111 }
3112 }
3113}
3114
3115static int cpu_has_work(CPUState *env)
3116{
3117 if (env->stop)
3118 return 1;
3119 if (env->stopped)
3120 return 0;
3121 if (!env->halted)
3122 return 1;
3123 if (qemu_cpu_has_work(env))
3124 return 1;
3125 return 0;
3126}
3127
David 'Digit' Turner6b512812010-10-15 15:05:04 +02003128int tcg_has_work(void)
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003129{
3130 CPUState *env;
3131
3132 for (env = first_cpu; env != NULL; env = env->next_cpu)
3133 if (cpu_has_work(env))
3134 return 1;
3135 return 0;
3136}
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003137
3138static int vm_can_run(void)
3139{
3140 if (powerdown_requested)
3141 return 0;
3142 if (reset_requested)
3143 return 0;
3144 if (shutdown_requested)
3145 return 0;
3146 if (debug_requested)
3147 return 0;
3148 return 1;
3149}
3150
3151static void main_loop(void)
3152{
3153 int r;
3154
3155#ifdef CONFIG_IOTHREAD
3156 qemu_system_ready = 1;
3157 qemu_cond_broadcast(&qemu_system_cond);
3158#endif
3159
3160 for (;;) {
3161 do {
3162#ifdef CONFIG_PROFILER
3163 int64_t ti;
3164#endif
3165#ifndef CONFIG_IOTHREAD
3166 tcg_cpu_exec();
3167#endif
3168#ifdef CONFIG_PROFILER
3169 ti = profile_getclock();
3170#endif
3171 main_loop_wait(qemu_calculate_timeout());
3172#ifdef CONFIG_PROFILER
3173 dev_time += profile_getclock() - ti;
3174#endif
rich canningsd952f282011-03-01 15:40:09 -08003175
3176 if (rotate_logs_requested) {
3177 FILE* new_dns_log_fd = rotate_qemu_log(get_slirp_dns_log_fd(),
3178 dns_log_filename);
3179 FILE* new_drop_log_fd = rotate_qemu_log(get_slirp_drop_log_fd(),
3180 drop_log_filename);
3181 slirp_dns_log_fd(new_dns_log_fd);
3182 slirp_drop_log_fd(new_drop_log_fd);
3183 reset_rotate_qemu_logs_request();
3184 }
3185
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003186 } while (vm_can_run());
3187
3188 if (qemu_debug_requested())
3189 vm_stop(EXCP_DEBUG);
3190 if (qemu_shutdown_requested()) {
3191 if (no_shutdown) {
3192 vm_stop(0);
3193 no_shutdown = 0;
Tim Baverstock24204cc2010-11-25 11:37:43 +00003194 } else {
Tim Baverstock24204cc2010-11-25 11:37:43 +00003195 if (savevm_on_exit != NULL) {
3196 do_savevm(cur_mon, savevm_on_exit);
3197 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003198 break;
Tim Baverstock24204cc2010-11-25 11:37:43 +00003199 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003200 }
3201 if (qemu_reset_requested()) {
3202 pause_all_vcpus();
3203 qemu_system_reset();
3204 resume_all_vcpus();
3205 }
3206 if (qemu_powerdown_requested())
3207 qemu_system_powerdown();
3208 if ((r = qemu_vmstop_requested()))
3209 vm_stop(r);
3210 }
3211 pause_all_vcpus();
3212}
3213
Vladimir Chtchetkine7fbf4972010-08-11 15:30:32 -07003214void version(void)
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003215{
3216 printf("QEMU PC emulator version " QEMU_VERSION QEMU_PKGVERSION ", Copyright (c) 2003-2008 Fabrice Bellard\n");
3217}
3218
3219void qemu_help(int exitcode)
3220{
3221 version();
3222 printf("usage: %s [options] [disk_image]\n"
3223 "\n"
3224 "'disk_image' is a raw hard image image for IDE hard disk 0\n"
3225 "\n"
3226#define DEF(option, opt_arg, opt_enum, opt_help) \
3227 opt_help
3228#define DEFHEADING(text) stringify(text) "\n"
3229#include "qemu-options.h"
3230#undef DEF
3231#undef DEFHEADING
3232#undef GEN_DOCS
3233 "\n"
3234 "During emulation, the following keys are useful:\n"
3235 "ctrl-alt-f toggle full screen\n"
3236 "ctrl-alt-n switch to virtual console 'n'\n"
3237 "ctrl-alt toggle mouse and keyboard grab\n"
3238 "\n"
3239 "When using -nographic, press 'ctrl-a h' to get some help.\n"
3240 ,
3241 "qemu",
3242 DEFAULT_RAM_SIZE,
3243#ifndef _WIN32
3244 DEFAULT_NETWORK_SCRIPT,
3245 DEFAULT_NETWORK_DOWN_SCRIPT,
3246#endif
3247 DEFAULT_GDBSTUB_PORT,
3248 "/tmp/qemu.log");
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07003249 QEMU_EXIT(exitcode);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003250}
3251
3252#define HAS_ARG 0x0001
3253
3254enum {
3255#define DEF(option, opt_arg, opt_enum, opt_help) \
3256 opt_enum,
3257#define DEFHEADING(text)
3258#include "qemu-options.h"
3259#undef DEF
3260#undef DEFHEADING
3261#undef GEN_DOCS
3262};
3263
3264typedef struct QEMUOption {
3265 const char *name;
3266 int flags;
3267 int index;
3268} QEMUOption;
3269
3270static const QEMUOption qemu_options[] = {
3271 { "h", 0, QEMU_OPTION_h },
3272#define DEF(option, opt_arg, opt_enum, opt_help) \
3273 { option, opt_arg, opt_enum },
3274#define DEFHEADING(text)
3275#include "qemu-options.h"
3276#undef DEF
3277#undef DEFHEADING
3278#undef GEN_DOCS
3279 { NULL, 0, 0 },
3280};
3281
3282#ifdef HAS_AUDIO
3283struct soundhw soundhw[] = {
3284#ifdef HAS_AUDIO_CHOICE
3285#if defined(TARGET_I386) || defined(TARGET_MIPS)
3286 {
3287 "pcspk",
3288 "PC speaker",
3289 0,
3290 1,
3291 { .init_isa = pcspk_audio_init }
3292 },
3293#endif
3294
3295#ifdef CONFIG_SB16
3296 {
3297 "sb16",
3298 "Creative Sound Blaster 16",
3299 0,
3300 1,
3301 { .init_isa = SB16_init }
3302 },
3303#endif
3304
3305#ifdef CONFIG_CS4231A
3306 {
3307 "cs4231a",
3308 "CS4231A",
3309 0,
3310 1,
3311 { .init_isa = cs4231a_init }
3312 },
3313#endif
3314
3315#ifdef CONFIG_ADLIB
3316 {
3317 "adlib",
3318#ifdef HAS_YMF262
3319 "Yamaha YMF262 (OPL3)",
3320#else
3321 "Yamaha YM3812 (OPL2)",
3322#endif
3323 0,
3324 1,
3325 { .init_isa = Adlib_init }
3326 },
3327#endif
3328
3329#ifdef CONFIG_GUS
3330 {
3331 "gus",
3332 "Gravis Ultrasound GF1",
3333 0,
3334 1,
3335 { .init_isa = GUS_init }
3336 },
3337#endif
3338
3339#ifdef CONFIG_AC97
3340 {
3341 "ac97",
3342 "Intel 82801AA AC97 Audio",
3343 0,
3344 0,
3345 { .init_pci = ac97_init }
3346 },
3347#endif
3348
3349#ifdef CONFIG_ES1370
3350 {
3351 "es1370",
3352 "ENSONIQ AudioPCI ES1370",
3353 0,
3354 0,
3355 { .init_pci = es1370_init }
3356 },
3357#endif
3358
3359#endif /* HAS_AUDIO_CHOICE */
3360
3361 { NULL, NULL, 0, 0, { NULL } }
3362};
3363
3364static void select_soundhw (const char *optarg)
3365{
3366 struct soundhw *c;
3367
3368 if (*optarg == '?') {
3369 show_valid_cards:
3370
3371 printf ("Valid sound card names (comma separated):\n");
3372 for (c = soundhw; c->name; ++c) {
3373 printf ("%-11s %s\n", c->name, c->descr);
3374 }
3375 printf ("\n-soundhw all will enable all of the above\n");
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07003376 if (*optarg != '?') {
3377 PANIC("Unknown sound card name: %s", optarg);
3378 } else {
3379 QEMU_EXIT(0);
3380 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003381 }
3382 else {
3383 size_t l;
3384 const char *p;
3385 char *e;
3386 int bad_card = 0;
3387
3388 if (!strcmp (optarg, "all")) {
3389 for (c = soundhw; c->name; ++c) {
3390 c->enabled = 1;
3391 }
3392 return;
3393 }
3394
3395 p = optarg;
3396 while (*p) {
3397 e = strchr (p, ',');
3398 l = !e ? strlen (p) : (size_t) (e - p);
3399
3400 for (c = soundhw; c->name; ++c) {
3401 if (!strncmp (c->name, p, l)) {
3402 c->enabled = 1;
3403 break;
3404 }
3405 }
3406
3407 if (!c->name) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07003408#ifndef CONFIG_ANDROID
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003409 if (l > 80) {
3410 fprintf (stderr,
3411 "Unknown sound card name (too big to show)\n");
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07003412 } else {
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003413 fprintf (stderr, "Unknown sound card name `%.*s'\n",
3414 (int) l, p);
3415 }
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07003416#endif // !CONFIG_ANDROID
3417 bad_card = 1;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003418 }
3419 p += l + (e != NULL);
3420 }
3421
3422 if (bad_card)
3423 goto show_valid_cards;
3424 }
3425}
3426#endif
3427
3428static void select_vgahw (const char *p)
3429{
3430 const char *opts;
3431
3432 cirrus_vga_enabled = 0;
3433 std_vga_enabled = 0;
3434 vmsvga_enabled = 0;
3435 xenfb_enabled = 0;
3436 if (strstart(p, "std", &opts)) {
3437 std_vga_enabled = 1;
3438 } else if (strstart(p, "cirrus", &opts)) {
3439 cirrus_vga_enabled = 1;
3440 } else if (strstart(p, "vmware", &opts)) {
3441 vmsvga_enabled = 1;
3442 } else if (strstart(p, "xenfb", &opts)) {
3443 xenfb_enabled = 1;
3444 } else if (!strstart(p, "none", &opts)) {
3445 invalid_vga:
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07003446 PANIC("Unknown vga type: %s", p);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003447 }
3448 while (*opts) {
3449 const char *nextopt;
3450
3451 if (strstart(opts, ",retrace=", &nextopt)) {
3452 opts = nextopt;
3453 if (strstart(opts, "dumb", &nextopt))
3454 vga_retrace_method = VGA_RETRACE_DUMB;
3455 else if (strstart(opts, "precise", &nextopt))
3456 vga_retrace_method = VGA_RETRACE_PRECISE;
3457 else goto invalid_vga;
3458 } else goto invalid_vga;
3459 opts = nextopt;
3460 }
3461}
3462
3463#ifdef _WIN32
3464static BOOL WINAPI qemu_ctrl_handler(DWORD type)
3465{
3466 exit(STATUS_CONTROL_C_EXIT);
3467 return TRUE;
3468}
3469#endif
3470
3471int qemu_uuid_parse(const char *str, uint8_t *uuid)
3472{
3473 int ret;
3474
3475 if(strlen(str) != 36)
3476 return -1;
3477
3478 ret = sscanf(str, UUID_FMT, &uuid[0], &uuid[1], &uuid[2], &uuid[3],
3479 &uuid[4], &uuid[5], &uuid[6], &uuid[7], &uuid[8], &uuid[9],
3480 &uuid[10], &uuid[11], &uuid[12], &uuid[13], &uuid[14], &uuid[15]);
3481
3482 if(ret != 16)
3483 return -1;
3484
3485#ifdef TARGET_I386
3486 smbios_add_field(1, offsetof(struct smbios_type_1, uuid), 16, uuid);
3487#endif
3488
3489 return 0;
3490}
3491
3492#define MAX_NET_CLIENTS 32
3493
3494#ifndef _WIN32
3495
3496static void termsig_handler(int signal)
3497{
3498 qemu_system_shutdown_request();
3499}
3500
3501static void sigchld_handler(int signal)
3502{
3503 waitpid(-1, NULL, WNOHANG);
3504}
3505
3506static void sighandler_setup(void)
3507{
3508 struct sigaction act;
3509
3510 memset(&act, 0, sizeof(act));
3511 act.sa_handler = termsig_handler;
3512 sigaction(SIGINT, &act, NULL);
3513 sigaction(SIGHUP, &act, NULL);
3514 sigaction(SIGTERM, &act, NULL);
3515
3516 act.sa_handler = sigchld_handler;
3517 act.sa_flags = SA_NOCLDSTOP;
3518 sigaction(SIGCHLD, &act, NULL);
3519}
3520
3521#endif
3522
3523#ifdef _WIN32
3524/* Look for support files in the same directory as the executable. */
3525static char *find_datadir(const char *argv0)
3526{
3527 char *p;
3528 char buf[MAX_PATH];
3529 DWORD len;
3530
3531 len = GetModuleFileName(NULL, buf, sizeof(buf) - 1);
3532 if (len == 0) {
3533 return NULL;
3534 }
3535
3536 buf[len] = 0;
3537 p = buf + len - 1;
3538 while (p != buf && *p != '\\')
3539 p--;
3540 *p = 0;
3541 if (access(buf, R_OK) == 0) {
3542 return qemu_strdup(buf);
3543 }
3544 return NULL;
3545}
3546#else /* !_WIN32 */
3547
3548/* Find a likely location for support files using the location of the binary.
3549 For installed binaries this will be "$bindir/../share/qemu". When
3550 running from the build tree this will be "$bindir/../pc-bios". */
3551#define SHARE_SUFFIX "/share/qemu"
3552#define BUILD_SUFFIX "/pc-bios"
3553static char *find_datadir(const char *argv0)
3554{
3555 char *dir;
3556 char *p = NULL;
3557 char *res;
3558#ifdef PATH_MAX
3559 char buf[PATH_MAX];
3560#endif
3561 size_t max_len;
3562
3563#if defined(__linux__)
3564 {
3565 int len;
3566 len = readlink("/proc/self/exe", buf, sizeof(buf) - 1);
3567 if (len > 0) {
3568 buf[len] = 0;
3569 p = buf;
3570 }
3571 }
3572#elif defined(__FreeBSD__)
3573 {
3574 int len;
3575 len = readlink("/proc/curproc/file", buf, sizeof(buf) - 1);
3576 if (len > 0) {
3577 buf[len] = 0;
3578 p = buf;
3579 }
3580 }
3581#endif
3582 /* If we don't have any way of figuring out the actual executable
3583 location then try argv[0]. */
3584 if (!p) {
3585#ifdef PATH_MAX
3586 p = buf;
3587#endif
3588 p = realpath(argv0, p);
3589 if (!p) {
3590 return NULL;
3591 }
3592 }
3593 dir = dirname(p);
3594 dir = dirname(dir);
3595
3596 max_len = strlen(dir) +
3597 MAX(strlen(SHARE_SUFFIX), strlen(BUILD_SUFFIX)) + 1;
3598 res = qemu_mallocz(max_len);
3599 snprintf(res, max_len, "%s%s", dir, SHARE_SUFFIX);
3600 if (access(res, R_OK)) {
3601 snprintf(res, max_len, "%s%s", dir, BUILD_SUFFIX);
3602 if (access(res, R_OK)) {
3603 qemu_free(res);
3604 res = NULL;
3605 }
3606 }
3607#ifndef PATH_MAX
3608 free(p);
3609#endif
3610 return res;
3611}
3612#undef SHARE_SUFFIX
3613#undef BUILD_SUFFIX
3614#endif
3615
3616char *qemu_find_file(int type, const char *name)
3617{
3618 int len;
3619 const char *subdir;
3620 char *buf;
3621
3622 /* If name contains path separators then try it as a straight path. */
3623 if ((strchr(name, '/') || strchr(name, '\\'))
3624 && access(name, R_OK) == 0) {
3625 return strdup(name);
3626 }
3627 switch (type) {
3628 case QEMU_FILE_TYPE_BIOS:
3629 subdir = "";
3630 break;
3631 case QEMU_FILE_TYPE_KEYMAP:
3632 subdir = "keymaps/";
3633 break;
3634 default:
3635 abort();
3636 }
3637 len = strlen(data_dir) + strlen(name) + strlen(subdir) + 2;
3638 buf = qemu_mallocz(len);
3639 snprintf(buf, len, "%s/%s%s", data_dir, subdir, name);
3640 if (access(buf, R_OK)) {
3641 qemu_free(buf);
3642 return NULL;
3643 }
3644 return buf;
3645}
3646
Vladimir Chtchetkine7fbf4972010-08-11 15:30:32 -07003647static int
3648add_dns_server( const char* server_name )
3649{
3650 SockAddress addr;
3651
3652 if (sock_address_init_resolve( &addr, server_name, 55, 0 ) < 0) {
3653 fprintf(stdout,
3654 "### WARNING: can't resolve DNS server name '%s'\n",
3655 server_name );
3656 return -1;
3657 }
3658
3659 fprintf(stderr,
3660 "DNS server name '%s' resolved to %s\n", server_name, sock_address_to_string(&addr) );
3661
3662 if ( slirp_add_dns_server( &addr ) < 0 ) {
3663 fprintf(stderr,
3664 "### WARNING: could not add DNS server '%s' to the network stack\n", server_name);
3665 return -1;
3666 }
3667 return 0;
3668}
3669
rich cannings7339b552011-02-16 13:43:44 -08003670/* Parses an integer
3671 * Pararm:
3672 * str String containing a number to be parsed.
3673 * result Passes the parsed integer in this argument
3674 * returns 0 if ok, -1 if failed
3675 */
3676int
3677parse_int(const char *str, int *result)
3678{
3679 char* r;
3680 *result = strtol(str, &r, 0);
3681 if (r == NULL || *r != '\0')
3682 return -1;
3683
3684 return 0;
3685}
3686
rich canningsd952f282011-03-01 15:40:09 -08003687#ifndef _WIN32
3688/*
3689 * Initializes the SIGUSR1 signal handler to clear Qemu logs.
3690 */
3691void init_qemu_clear_logs_sig() {
3692 struct sigaction act;
3693 sigfillset(&act.sa_mask);
3694 act.sa_flags = 0;
3695 act.sa_handler = rotate_qemu_logs_handler;
3696 if (sigaction(SIGUSR1, &act, NULL) == -1) {
3697 fprintf(stderr, "Failed to setup SIGUSR1 handler to clear Qemu logs\n");
3698 exit(-1);
3699 }
3700}
3701#endif
3702
3703
rich cannings7339b552011-02-16 13:43:44 -08003704
3705/* parses a null-terminated string specifying a network port (e.g., "80") or
3706 * port range (e.g., "[6666-7000]"). In case of a single port, lport and hport
3707 * are the same. Returns 0 on success, -1 on error. */
3708
3709int parse_port_range(const char *str, unsigned short *lport,
3710 unsigned short *hport) {
3711
3712 unsigned int low = 0, high = 0;
3713 char *p, *arg = strdup(str);
3714
3715 if ((*arg == '[') && ((p = strrchr(arg, ']')) != NULL)) {
3716 p = arg + 1; /* skip '[' */
3717 low = atoi(strtok(p, "-"));
3718 high = atoi(strtok(NULL, "-"));
3719 if ((low > 0) && (high > 0) && (low < high) && (high < 65535)) {
3720 *lport = low;
3721 *hport = high;
3722 }
3723 }
3724 else {
3725 low = atoi(arg);
3726 if ((0 < low) && (low < 65535)) {
3727 *lport = low;
3728 *hport = low;
3729 }
3730 }
3731 free(arg);
3732 if (low != 0)
3733 return 0;
3734 return -1;
3735}
3736
3737/*
3738 * Implements the generic port forwarding option
3739 */
3740void
3741net_slirp_forward(const char *optarg)
3742{
3743 /*
3744 * we expect the following format:
3745 * dst_net:dst_mask:dst_port:redirect_ip:redirect_port OR
3746 * dst_net:dst_mask:[dp_range_start-dp_range_end]:redirect_ip:redirect_port
3747 */
3748 char *argument = strdup(optarg), *p = argument;
3749 char *dst_net, *dst_mask, *dst_port;
3750 char *redirect_ip, *redirect_port;
3751 uint32_t dnet, dmask, rip;
3752 unsigned short dlport, dhport, rport;
3753
3754
3755 dst_net = strtok(p, ":");
3756 dst_mask = strtok(NULL, ":");
3757 dst_port = strtok(NULL, ":");
3758 redirect_ip = strtok(NULL, ":");
3759 redirect_port = strtok(NULL, ":");
3760
3761 if (dst_net == NULL || dst_mask == NULL || dst_port == NULL ||
3762 redirect_ip == NULL || redirect_port == NULL) {
3763 fprintf(stderr,
3764 "Invalid argument for -net-forward, we expect "
3765 "dst_net:dst_mask:dst_port:redirect_ip:redirect_port or "
3766 "dst_net:dst_mask:[dp_range_start-dp_range_end]"
3767 ":redirect_ip:redirect_port: %s\n",
3768 optarg);
3769 exit(1);
3770 }
3771
3772 /* inet_strtoip converts dotted address to host byte order */
3773 if (inet_strtoip(dst_net, &dnet) == -1) {
3774 fprintf(stderr, "Invalid destination IP net: %s\n", dst_net);
3775 exit(1);
3776 }
3777 if (inet_strtoip(dst_mask, &dmask) == -1) {
3778 fprintf(stderr, "Invalid destination IP mask: %s\n", dst_mask);
3779 exit(1);
3780 }
3781 if (inet_strtoip(redirect_ip, &rip) == -1) {
3782 fprintf(stderr, "Invalid redirect IP address: %s\n", redirect_ip);
3783 exit(1);
3784 }
3785
3786 if (parse_port_range(dst_port, &dlport, &dhport) == -1) {
3787 fprintf(stderr, "Invalid destination port or port range\n");
3788 exit(1);
3789 }
3790
3791 rport = atoi(redirect_port);
3792 if (!rport) {
3793 fprintf(stderr, "Invalid redirect port: %s\n", redirect_port);
3794 exit(1);
3795 }
3796
3797 dnet &= dmask;
3798
3799 slirp_add_net_forward(dnet, dmask, dlport, dhport,
3800 rip, rport);
3801
3802 free(argument);
3803}
3804
3805
3806/* Parses an -allow-tcp or -allow-udp argument and inserts a corresponding
3807 * entry in the allows list */
3808void
3809slirp_allow(const char *optarg, u_int8_t proto)
3810{
3811 /*
3812 * we expect the following format:
3813 * dst_ip:dst_port OR dst_ip:[dst_lport-dst_hport]
3814 */
3815 char *argument = strdup(optarg), *p = argument;
3816 char *dst_ip_str, *dst_port_str;
3817 uint32_t dst_ip;
3818 unsigned short dst_lport, dst_hport;
3819
3820 dst_ip_str = strtok(p, ":");
3821 dst_port_str = strtok(NULL, ":");
3822
3823 if (dst_ip_str == NULL || dst_port_str == NULL) {
3824 fprintf(stderr,
3825 "Invalid argument %s for -allow. We expect "
3826 "dst_ip:dst_port or dst_ip:[dst_lport-dst_hport]\n",
3827 optarg);
3828 exit(1);
3829 }
3830
3831 if (inet_strtoip(dst_ip_str, &dst_ip) == -1) {
3832 fprintf(stderr, "Invalid destination IP address: %s\n", dst_ip_str);
3833 exit(1);
3834 }
3835 if (parse_port_range(dst_port_str, &dst_lport, &dst_hport) == -1) {
3836 fprintf(stderr, "Invalid destination port or port range\n");
3837 exit(1);
3838 }
3839
3840 slirp_add_allow(dst_ip, dst_lport, dst_hport, proto);
3841
3842 free(argument);
3843}
3844
David 'Digit' Turner062dd6a2011-03-01 14:50:07 +01003845/* Add a serial device at a given location in the emulated hardware table.
3846 * On failure, this function aborts the program with an error message.
3847 */
3848static void
3849serial_hds_add_at(int index, const char* devname)
3850{
3851 char label[32];
3852
3853 if (!devname || !strcmp(devname,"none"))
3854 return;
3855
3856 if (index >= MAX_SERIAL_PORTS) {
3857 PANIC("qemu: invalid serial index for %s (%d >= %d)",
3858 devname, index, MAX_SERIAL_PORTS);
3859 }
3860 if (serial_hds[index] != NULL) {
3861 PANIC("qemu: invalid serial index for %s (%d: already taken!)",
3862 devname, index);
3863 }
3864 snprintf(label, sizeof(label), "serial%d", index);
3865 serial_hds[index] = qemu_chr_open(label, devname, NULL);
3866 if (!serial_hds[index]) {
3867 PANIC("qemu: could not open serial device '%s'", devname);
3868 }
3869}
3870
3871
3872/* Find a free slot in the emulated serial device table, and register
3873 * it. Return the allocated table index.
3874 */
3875static int
3876serial_hds_add(const char* devname)
3877{
3878 int index;
3879
3880 /* Find first free slot */
3881 for (index = 0; index < MAX_SERIAL_PORTS; index++) {
3882 if (serial_hds[index] == NULL) {
3883 serial_hds_add_at(index, devname);
3884 return index;
3885 }
3886 }
3887
3888 PANIC("qemu: too many serial devices registered (%d)", index);
3889 return -1; /* shouldn't happen */
3890}
3891
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003892int main(int argc, char **argv, char **envp)
3893{
3894 const char *gdbstub_dev = NULL;
3895 uint32_t boot_devices_bitmap = 0;
3896 int i;
3897 int snapshot, linux_boot, net_boot;
David Turner6a9ef172010-09-09 22:54:36 +02003898 const char *icount_option = NULL;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003899 const char *initrd_filename;
3900 const char *kernel_filename, *kernel_cmdline;
3901 const char *boot_devices = "";
3902 DisplayState *ds;
3903 DisplayChangeListener *dcl;
3904 int cyls, heads, secs, translation;
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +01003905 QemuOpts *hda_opts = NULL;
David 'Digit' Turner5f64b872011-02-28 23:23:05 +01003906 QemuOpts *hdb_opts = NULL;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003907 const char *net_clients[MAX_NET_CLIENTS];
3908 int nb_net_clients;
3909 const char *bt_opts[MAX_BT_CMDLINE];
3910 int nb_bt_opts;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003911 int optind;
3912 const char *r, *optarg;
3913 CharDriverState *monitor_hd = NULL;
3914 const char *monitor_device;
3915 const char *serial_devices[MAX_SERIAL_PORTS];
3916 int serial_device_index;
3917 const char *parallel_devices[MAX_PARALLEL_PORTS];
3918 int parallel_device_index;
3919 const char *virtio_consoles[MAX_VIRTIO_CONSOLES];
3920 int virtio_console_index;
3921 const char *loadvm = NULL;
3922 QEMUMachine *machine;
3923 const char *cpu_model;
3924 const char *usb_devices[MAX_USB_CMDLINE];
3925 int usb_devices_index;
3926#ifndef _WIN32
3927 int fds[2];
3928#endif
3929 int tb_size;
3930 const char *pid_file = NULL;
3931 const char *incoming = NULL;
3932#ifndef _WIN32
3933 int fd = 0;
3934 struct passwd *pwd = NULL;
3935 const char *chroot_dir = NULL;
3936 const char *run_as = NULL;
3937#endif
3938 CPUState *env;
3939 int show_vnc_port = 0;
Vladimir Chtchetkine074d1f92010-08-06 09:29:50 -07003940 IniFile* hw_ini = NULL;
David 'Digit' Turner5f824112011-03-01 14:00:26 +01003941 STRALLOC_DEFINE(kernel_params);
3942 STRALLOC_DEFINE(kernel_config);
Vladimir Chtchetkine7fbf4972010-08-11 15:30:32 -07003943 int dns_count = 0;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003944
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07003945 /* Initialize sockets before anything else, so we can properly report
3946 * initialization failures back to the UI. */
3947#ifdef _WIN32
3948 socket_init();
3949#endif
3950
David 'Digit' Turnera7fb77d2010-05-10 23:50:54 -07003951 init_clocks();
3952
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003953 qemu_cache_utils_init(envp);
3954
David 'Digit' Turnera5d41202010-05-10 18:37:10 -07003955 QLIST_INIT (&vm_change_state_head);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003956#ifndef _WIN32
3957 {
3958 struct sigaction act;
3959 sigfillset(&act.sa_mask);
3960 act.sa_flags = 0;
3961 act.sa_handler = SIG_IGN;
3962 sigaction(SIGPIPE, &act, NULL);
3963 }
3964#else
3965 SetConsoleCtrlHandler(qemu_ctrl_handler, TRUE);
3966 /* Note: cpu_interrupt() is currently not SMP safe, so we force
3967 QEMU to run on a single CPU */
3968 {
3969 HANDLE h;
3970 DWORD mask, smask;
3971 int i;
3972 h = GetCurrentProcess();
3973 if (GetProcessAffinityMask(h, &mask, &smask)) {
3974 for(i = 0; i < 32; i++) {
3975 if (mask & (1 << i))
3976 break;
3977 }
3978 if (i != 32) {
3979 mask = 1 << i;
3980 SetProcessAffinityMask(h, mask);
3981 }
3982 }
3983 }
3984#endif
3985
3986 module_call_init(MODULE_INIT_MACHINE);
3987 machine = find_default_machine();
3988 cpu_model = NULL;
3989 initrd_filename = NULL;
3990 ram_size = 0;
3991 snapshot = 0;
3992 kernel_filename = NULL;
3993 kernel_cmdline = "";
David 'Digit' Turner5f824112011-03-01 14:00:26 +01003994
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07003995 cyls = heads = secs = 0;
3996 translation = BIOS_ATA_TRANSLATION_AUTO;
3997 monitor_device = "vc:80Cx24C";
3998
3999 serial_devices[0] = "vc:80Cx24C";
4000 for(i = 1; i < MAX_SERIAL_PORTS; i++)
4001 serial_devices[i] = NULL;
4002 serial_device_index = 0;
4003
4004 parallel_devices[0] = "vc:80Cx24C";
4005 for(i = 1; i < MAX_PARALLEL_PORTS; i++)
4006 parallel_devices[i] = NULL;
4007 parallel_device_index = 0;
4008
4009 for(i = 0; i < MAX_VIRTIO_CONSOLES; i++)
4010 virtio_consoles[i] = NULL;
4011 virtio_console_index = 0;
4012
4013 for (i = 0; i < MAX_NODES; i++) {
4014 node_mem[i] = 0;
4015 node_cpumask[i] = 0;
4016 }
4017
4018 usb_devices_index = 0;
4019
4020 nb_net_clients = 0;
4021 nb_bt_opts = 0;
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +01004022#ifdef MAX_DRIVES
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004023 nb_drives = 0;
4024 nb_drives_opt = 0;
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +01004025#endif
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004026 nb_numa_nodes = 0;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004027
4028 nb_nics = 0;
4029
4030 tb_size = 0;
4031 autostart= 1;
4032
4033 register_watchdogs();
4034
Vladimir Chtchetkineb25bf2a2010-09-08 11:09:23 -07004035 /* Initialize boot properties. */
4036 boot_property_init_service();
4037
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004038 optind = 1;
4039 for(;;) {
4040 if (optind >= argc)
4041 break;
4042 r = argv[optind];
4043 if (r[0] != '-') {
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +01004044 hda_opts = drive_add(argv[optind++], HD_ALIAS, 0);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004045 } else {
4046 const QEMUOption *popt;
4047
4048 optind++;
4049 /* Treat --foo the same as -foo. */
4050 if (r[1] == '-')
4051 r++;
4052 popt = qemu_options;
4053 for(;;) {
4054 if (!popt->name) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004055 PANIC("%s: invalid option -- '%s'",
4056 argv[0], r);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004057 }
4058 if (!strcmp(popt->name, r + 1))
4059 break;
4060 popt++;
4061 }
4062 if (popt->flags & HAS_ARG) {
4063 if (optind >= argc) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004064 PANIC("%s: option '%s' requires an argument",
4065 argv[0], r);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004066 }
4067 optarg = argv[optind++];
4068 } else {
4069 optarg = NULL;
4070 }
4071
4072 switch(popt->index) {
4073 case QEMU_OPTION_M:
4074 machine = find_machine(optarg);
4075 if (!machine) {
4076 QEMUMachine *m;
4077 printf("Supported machines are:\n");
4078 for(m = first_machine; m != NULL; m = m->next) {
4079 printf("%-10s %s%s\n",
4080 m->name, m->desc,
4081 m->is_default ? " (default)" : "");
4082 }
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004083 if (*optarg != '?') {
4084 PANIC("Invalid machine parameter: %s",
4085 optarg);
4086 } else {
4087 QEMU_EXIT(0);
4088 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004089 }
4090 break;
4091 case QEMU_OPTION_cpu:
4092 /* hw initialization will check this */
4093 if (*optarg == '?') {
4094/* XXX: implement xxx_cpu_list for targets that still miss it */
4095#if defined(cpu_list)
4096 cpu_list(stdout, &fprintf);
4097#endif
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004098 QEMU_EXIT(0);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004099 } else {
4100 cpu_model = optarg;
4101 }
4102 break;
4103 case QEMU_OPTION_initrd:
4104 initrd_filename = optarg;
4105 break;
4106 case QEMU_OPTION_hda:
4107 if (cyls == 0)
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +01004108 hda_opts = drive_add(optarg, HD_ALIAS, 0);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004109 else
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +01004110 hda_opts = drive_add(optarg, HD_ALIAS
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004111 ",cyls=%d,heads=%d,secs=%d%s",
4112 0, cyls, heads, secs,
4113 translation == BIOS_ATA_TRANSLATION_LBA ?
4114 ",trans=lba" :
4115 translation == BIOS_ATA_TRANSLATION_NONE ?
4116 ",trans=none" : "");
4117 break;
4118 case QEMU_OPTION_hdb:
David 'Digit' Turner5f64b872011-02-28 23:23:05 +01004119 hdb_opts = drive_add(optarg, HD_ALIAS, 1);
4120 break;
4121
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004122 case QEMU_OPTION_hdc:
4123 case QEMU_OPTION_hdd:
4124 drive_add(optarg, HD_ALIAS, popt->index - QEMU_OPTION_hda);
4125 break;
4126 case QEMU_OPTION_drive:
4127 drive_add(NULL, "%s", optarg);
4128 break;
4129 case QEMU_OPTION_mtdblock:
4130 drive_add(optarg, MTD_ALIAS);
4131 break;
4132 case QEMU_OPTION_sd:
4133 drive_add(optarg, SD_ALIAS);
4134 break;
4135 case QEMU_OPTION_pflash:
4136 drive_add(optarg, PFLASH_ALIAS);
4137 break;
4138 case QEMU_OPTION_snapshot:
4139 snapshot = 1;
4140 break;
4141 case QEMU_OPTION_hdachs:
4142 {
4143 const char *p;
4144 p = optarg;
4145 cyls = strtol(p, (char **)&p, 0);
4146 if (cyls < 1 || cyls > 16383)
4147 goto chs_fail;
4148 if (*p != ',')
4149 goto chs_fail;
4150 p++;
4151 heads = strtol(p, (char **)&p, 0);
4152 if (heads < 1 || heads > 16)
4153 goto chs_fail;
4154 if (*p != ',')
4155 goto chs_fail;
4156 p++;
4157 secs = strtol(p, (char **)&p, 0);
4158 if (secs < 1 || secs > 63)
4159 goto chs_fail;
4160 if (*p == ',') {
4161 p++;
4162 if (!strcmp(p, "none"))
4163 translation = BIOS_ATA_TRANSLATION_NONE;
4164 else if (!strcmp(p, "lba"))
4165 translation = BIOS_ATA_TRANSLATION_LBA;
4166 else if (!strcmp(p, "auto"))
4167 translation = BIOS_ATA_TRANSLATION_AUTO;
4168 else
4169 goto chs_fail;
4170 } else if (*p != '\0') {
4171 chs_fail:
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004172 PANIC("qemu: invalid physical CHS format");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004173 }
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +01004174 if (hda_opts != NULL) {
4175 char num[16];
4176 snprintf(num, sizeof(num), "%d", cyls);
4177 qemu_opt_set(hda_opts, "cyls", num);
4178 snprintf(num, sizeof(num), "%d", heads);
4179 qemu_opt_set(hda_opts, "heads", num);
4180 snprintf(num, sizeof(num), "%d", secs);
4181 qemu_opt_set(hda_opts, "secs", num);
4182 if (translation == BIOS_ATA_TRANSLATION_LBA)
4183 qemu_opt_set(hda_opts, "trans", "lba");
4184 if (translation == BIOS_ATA_TRANSLATION_NONE)
4185 qemu_opt_set(hda_opts, "trans", "none");
4186 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004187 }
4188 break;
4189 case QEMU_OPTION_numa:
4190 if (nb_numa_nodes >= MAX_NODES) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004191 PANIC("qemu: too many NUMA nodes");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004192 }
4193 numa_add(optarg);
4194 break;
4195 case QEMU_OPTION_nographic:
4196 display_type = DT_NOGRAPHIC;
4197 break;
4198#ifdef CONFIG_CURSES
4199 case QEMU_OPTION_curses:
4200 display_type = DT_CURSES;
4201 break;
4202#endif
4203 case QEMU_OPTION_portrait:
4204 graphic_rotate = 1;
4205 break;
4206 case QEMU_OPTION_kernel:
4207 kernel_filename = optarg;
4208 break;
4209 case QEMU_OPTION_append:
4210 kernel_cmdline = optarg;
4211 break;
4212 case QEMU_OPTION_cdrom:
4213 drive_add(optarg, CDROM_ALIAS);
4214 break;
4215 case QEMU_OPTION_boot:
4216 boot_devices = optarg;
4217 /* We just do some generic consistency checks */
4218 {
4219 /* Could easily be extended to 64 devices if needed */
4220 const char *p;
Vladimir Chtchetkined81e6d12010-06-15 16:46:32 -07004221
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004222 boot_devices_bitmap = 0;
4223 for (p = boot_devices; *p != '\0'; p++) {
4224 /* Allowed boot devices are:
4225 * a b : floppy disk drives
4226 * c ... f : IDE disk drives
4227 * g ... m : machine implementation dependant drives
4228 * n ... p : network devices
4229 * It's up to each machine implementation to check
4230 * if the given boot devices match the actual hardware
4231 * implementation and firmware features.
4232 */
4233 if (*p < 'a' || *p > 'q') {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004234 PANIC("Invalid boot device '%c'", *p);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004235 }
4236 if (boot_devices_bitmap & (1 << (*p - 'a'))) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004237 PANIC(
4238 "Boot device '%c' was given twice",*p);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004239 }
4240 boot_devices_bitmap |= 1 << (*p - 'a');
4241 }
4242 }
4243 break;
4244 case QEMU_OPTION_fda:
4245 case QEMU_OPTION_fdb:
4246 drive_add(optarg, FD_ALIAS, popt->index - QEMU_OPTION_fda);
4247 break;
4248#ifdef TARGET_I386
4249 case QEMU_OPTION_no_fd_bootchk:
4250 fd_bootchk = 0;
4251 break;
4252#endif
4253 case QEMU_OPTION_net:
4254 if (nb_net_clients >= MAX_NET_CLIENTS) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004255 PANIC("qemu: too many network clients");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004256 }
4257 net_clients[nb_net_clients] = optarg;
4258 nb_net_clients++;
4259 break;
4260#ifdef CONFIG_SLIRP
4261 case QEMU_OPTION_tftp:
4262 tftp_prefix = optarg;
4263 break;
4264 case QEMU_OPTION_bootp:
4265 bootp_filename = optarg;
4266 break;
4267#if 0 /* ANDROID disabled */
4268#ifndef _WIN32
4269 case QEMU_OPTION_smb:
4270 net_slirp_smb(optarg);
4271 break;
4272#endif
4273#endif /* ANDROID */
4274 case QEMU_OPTION_redir:
4275 net_slirp_redir(NULL, optarg, NULL);
4276 break;
4277#endif
4278 case QEMU_OPTION_bt:
4279 if (nb_bt_opts >= MAX_BT_CMDLINE) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004280 PANIC("qemu: too many bluetooth options");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004281 }
4282 bt_opts[nb_bt_opts++] = optarg;
4283 break;
4284#ifdef HAS_AUDIO
4285 case QEMU_OPTION_audio_help:
4286 AUD_help ();
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004287 QEMU_EXIT(0);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004288 break;
4289 case QEMU_OPTION_soundhw:
4290 select_soundhw (optarg);
4291 break;
4292#endif
4293 case QEMU_OPTION_h:
4294 qemu_help(0);
4295 break;
4296 case QEMU_OPTION_version:
4297 version();
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004298 QEMU_EXIT(0);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004299 break;
4300 case QEMU_OPTION_m: {
4301 uint64_t value;
4302 char *ptr;
4303
4304 value = strtoul(optarg, &ptr, 10);
4305 switch (*ptr) {
4306 case 0: case 'M': case 'm':
4307 value <<= 20;
4308 break;
4309 case 'G': case 'g':
4310 value <<= 30;
4311 break;
4312 default:
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004313 PANIC("qemu: invalid ram size: %s", optarg);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004314 }
4315
4316 /* On 32-bit hosts, QEMU is limited by virtual address space */
4317 if (value > (2047 << 20)
4318#ifndef CONFIG_KQEMU
4319 && HOST_LONG_BITS == 32
4320#endif
4321 ) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004322 PANIC("qemu: at most 2047 MB RAM can be simulated");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004323 }
4324 if (value != (uint64_t)(ram_addr_t)value) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004325 PANIC("qemu: ram size too large");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004326 }
4327 ram_size = value;
4328 break;
4329 }
4330 case QEMU_OPTION_d:
4331 {
4332 int mask;
4333 const CPULogItem *item;
4334
4335 mask = cpu_str_to_log_mask(optarg);
4336 if (!mask) {
4337 printf("Log items (comma separated):\n");
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004338 for(item = cpu_log_items; item->mask != 0; item++) {
4339 printf("%-10s %s\n", item->name, item->help);
4340 }
4341 PANIC("Invalid parameter -d=%s", optarg);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004342 }
4343 cpu_set_log(mask);
4344 }
4345 break;
4346 case QEMU_OPTION_s:
4347 gdbstub_dev = "tcp::" DEFAULT_GDBSTUB_PORT;
4348 break;
4349 case QEMU_OPTION_gdb:
4350 gdbstub_dev = optarg;
4351 break;
4352 case QEMU_OPTION_L:
4353 data_dir = optarg;
4354 break;
4355 case QEMU_OPTION_bios:
4356 bios_name = optarg;
4357 break;
4358 case QEMU_OPTION_singlestep:
4359 singlestep = 1;
4360 break;
4361 case QEMU_OPTION_S:
4362#if 0 /* ANDROID */
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004363 PANIC("Sorry, stopped launch is not supported in the Android emulator" );
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004364#endif
4365 autostart = 0;
4366 break;
4367#ifndef _WIN32
4368 case QEMU_OPTION_k:
4369 keyboard_layout = optarg;
4370 break;
4371#endif
4372 case QEMU_OPTION_localtime:
4373 rtc_utc = 0;
4374 break;
4375 case QEMU_OPTION_vga:
4376 select_vgahw (optarg);
4377 break;
4378#if defined(TARGET_PPC) || defined(TARGET_SPARC)
4379 case QEMU_OPTION_g:
4380 {
4381 const char *p;
4382 int w, h, depth;
4383 p = optarg;
4384 w = strtol(p, (char **)&p, 10);
4385 if (w <= 0) {
4386 graphic_error:
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004387 PANIC("qemu: invalid resolution or depth");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004388 }
4389 if (*p != 'x')
4390 goto graphic_error;
4391 p++;
4392 h = strtol(p, (char **)&p, 10);
4393 if (h <= 0)
4394 goto graphic_error;
4395 if (*p == 'x') {
4396 p++;
4397 depth = strtol(p, (char **)&p, 10);
4398 if (depth != 8 && depth != 15 && depth != 16 &&
4399 depth != 24 && depth != 32)
4400 goto graphic_error;
4401 } else if (*p == '\0') {
4402 depth = graphic_depth;
4403 } else {
4404 goto graphic_error;
4405 }
4406
4407 graphic_width = w;
4408 graphic_height = h;
4409 graphic_depth = depth;
4410 }
4411 break;
4412#endif
4413 case QEMU_OPTION_echr:
4414 {
4415 char *r;
4416 term_escape_char = strtol(optarg, &r, 0);
4417 if (r == optarg)
4418 printf("Bad argument to echr\n");
4419 break;
4420 }
4421 case QEMU_OPTION_monitor:
4422 monitor_device = optarg;
4423 break;
4424 case QEMU_OPTION_serial:
4425 if (serial_device_index >= MAX_SERIAL_PORTS) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004426 PANIC("qemu: too many serial ports");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004427 }
4428 serial_devices[serial_device_index] = optarg;
4429 serial_device_index++;
4430 break;
4431 case QEMU_OPTION_watchdog:
4432 i = select_watchdog(optarg);
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004433 if (i > 0) {
4434 if (i == 1) {
4435 PANIC("Invalid watchdog parameter: %s",
4436 optarg);
4437 } else {
4438 QEMU_EXIT(0);
4439 }
4440 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004441 break;
4442 case QEMU_OPTION_watchdog_action:
4443 if (select_watchdog_action(optarg) == -1) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004444 PANIC("Unknown -watchdog-action parameter");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004445 }
4446 break;
4447 case QEMU_OPTION_virtiocon:
4448 if (virtio_console_index >= MAX_VIRTIO_CONSOLES) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004449 PANIC("qemu: too many virtio consoles");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004450 }
4451 virtio_consoles[virtio_console_index] = optarg;
4452 virtio_console_index++;
4453 break;
4454 case QEMU_OPTION_parallel:
4455 if (parallel_device_index >= MAX_PARALLEL_PORTS) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004456 PANIC("qemu: too many parallel ports");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004457 }
4458 parallel_devices[parallel_device_index] = optarg;
4459 parallel_device_index++;
4460 break;
Tim Baverstock24204cc2010-11-25 11:37:43 +00004461 case QEMU_OPTION_loadvm:
4462 loadvm = optarg;
4463 break;
Tim Baverstock24204cc2010-11-25 11:37:43 +00004464 case QEMU_OPTION_savevm_on_exit:
4465 savevm_on_exit = optarg;
4466 break;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004467 case QEMU_OPTION_full_screen:
4468 full_screen = 1;
4469 break;
4470#ifdef CONFIG_SDL
4471 case QEMU_OPTION_no_frame:
4472 no_frame = 1;
4473 break;
4474 case QEMU_OPTION_alt_grab:
4475 alt_grab = 1;
4476 break;
4477 case QEMU_OPTION_no_quit:
4478 no_quit = 1;
4479 break;
4480 case QEMU_OPTION_sdl:
4481 display_type = DT_SDL;
4482 break;
4483#endif
4484 case QEMU_OPTION_pidfile:
4485 pid_file = optarg;
4486 break;
4487#ifdef TARGET_I386
4488 case QEMU_OPTION_win2k_hack:
4489 win2k_install_hack = 1;
4490 break;
4491 case QEMU_OPTION_rtc_td_hack:
4492 rtc_td_hack = 1;
4493 break;
Jun Nakajima334ab472011-02-02 23:49:59 -08004494#ifndef CONFIG_ANDROID
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004495 case QEMU_OPTION_acpitable:
4496 if(acpi_table_add(optarg) < 0) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004497 PANIC("Wrong acpi table provided");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004498 }
4499 break;
Jun Nakajima334ab472011-02-02 23:49:59 -08004500#endif
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004501 case QEMU_OPTION_smbios:
4502 if(smbios_entry_add(optarg) < 0) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004503 PANIC("Wrong smbios provided");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004504 }
4505 break;
4506#endif
4507#ifdef CONFIG_KQEMU
4508 case QEMU_OPTION_no_kqemu:
4509 kqemu_allowed = 0;
4510 break;
4511 case QEMU_OPTION_kernel_kqemu:
4512 kqemu_allowed = 2;
4513 break;
4514#endif
4515#ifdef CONFIG_KVM
4516 case QEMU_OPTION_enable_kvm:
4517 kvm_allowed = 1;
4518#ifdef CONFIG_KQEMU
4519 kqemu_allowed = 0;
4520#endif
4521 break;
4522#endif
4523 case QEMU_OPTION_usb:
4524 usb_enabled = 1;
4525 break;
4526 case QEMU_OPTION_usbdevice:
4527 usb_enabled = 1;
4528 if (usb_devices_index >= MAX_USB_CMDLINE) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004529 PANIC("Too many USB devices");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004530 }
4531 usb_devices[usb_devices_index] = optarg;
4532 usb_devices_index++;
4533 break;
4534 case QEMU_OPTION_smp:
4535 smp_cpus = atoi(optarg);
4536 if (smp_cpus < 1) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004537 PANIC("Invalid number of CPUs");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004538 }
4539 break;
4540 case QEMU_OPTION_vnc:
4541 display_type = DT_VNC;
4542 vnc_display = optarg;
4543 break;
4544#ifdef TARGET_I386
4545 case QEMU_OPTION_no_acpi:
4546 acpi_enabled = 0;
4547 break;
4548 case QEMU_OPTION_no_hpet:
4549 no_hpet = 1;
4550 break;
4551 case QEMU_OPTION_no_virtio_balloon:
4552 no_virtio_balloon = 1;
4553 break;
4554#endif
4555 case QEMU_OPTION_no_reboot:
4556 no_reboot = 1;
4557 break;
4558 case QEMU_OPTION_no_shutdown:
4559 no_shutdown = 1;
4560 break;
4561 case QEMU_OPTION_show_cursor:
4562 cursor_hide = 0;
4563 break;
4564 case QEMU_OPTION_uuid:
4565 if(qemu_uuid_parse(optarg, qemu_uuid) < 0) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004566 PANIC("Fail to parse UUID string. Wrong format.");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004567 }
4568 break;
4569#ifndef _WIN32
4570 case QEMU_OPTION_daemonize:
4571 daemonize = 1;
4572 break;
4573#endif
4574 case QEMU_OPTION_option_rom:
4575 if (nb_option_roms >= MAX_OPTION_ROMS) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004576 PANIC("Too many option ROMs");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004577 }
4578 option_rom[nb_option_roms] = optarg;
4579 nb_option_roms++;
4580 break;
4581#if defined(TARGET_ARM) || defined(TARGET_M68K)
4582 case QEMU_OPTION_semihosting:
4583 semihosting_enabled = 1;
4584 break;
4585#endif
4586 case QEMU_OPTION_name:
4587 qemu_name = optarg;
4588 break;
4589#if defined(TARGET_SPARC) || defined(TARGET_PPC)
4590 case QEMU_OPTION_prom_env:
4591 if (nb_prom_envs >= MAX_PROM_ENVS) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004592 PANIC("Too many prom variables");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004593 }
4594 prom_envs[nb_prom_envs] = optarg;
4595 nb_prom_envs++;
4596 break;
4597#endif
4598#ifdef TARGET_ARM
4599 case QEMU_OPTION_old_param:
4600 old_param = 1;
4601 break;
4602#endif
4603 case QEMU_OPTION_clock:
4604 configure_alarms(optarg);
4605 break;
4606 case QEMU_OPTION_startdate:
4607 {
4608 struct tm tm;
David 'Digit' Turnerdc468202010-10-27 02:34:46 +02004609 time_t rtc_start_date = 0;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004610 if (!strcmp(optarg, "now")) {
4611 rtc_date_offset = -1;
4612 } else {
4613 if (sscanf(optarg, "%d-%d-%dT%d:%d:%d",
4614 &tm.tm_year,
4615 &tm.tm_mon,
4616 &tm.tm_mday,
4617 &tm.tm_hour,
4618 &tm.tm_min,
4619 &tm.tm_sec) == 6) {
4620 /* OK */
4621 } else if (sscanf(optarg, "%d-%d-%d",
4622 &tm.tm_year,
4623 &tm.tm_mon,
4624 &tm.tm_mday) == 3) {
4625 tm.tm_hour = 0;
4626 tm.tm_min = 0;
4627 tm.tm_sec = 0;
4628 } else {
4629 goto date_fail;
4630 }
4631 tm.tm_year -= 1900;
4632 tm.tm_mon--;
4633 rtc_start_date = mktimegm(&tm);
4634 if (rtc_start_date == -1) {
4635 date_fail:
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004636 PANIC("Invalid date format. Valid format are:\n"
4637 "'now' or '2006-06-17T16:01:21' or '2006-06-17'");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004638 }
4639 rtc_date_offset = time(NULL) - rtc_start_date;
4640 }
4641 }
4642 break;
rich cannings7339b552011-02-16 13:43:44 -08004643
4644 /* -------------------------------------------------------*/
4645 /* User mode network stack restrictions */
4646 case QEMU_OPTION_drop_udp:
4647 slirp_drop_udp();
4648 break;
4649 case QEMU_OPTION_drop_tcp:
4650 slirp_drop_tcp();
4651 break;
4652 case QEMU_OPTION_allow_tcp:
4653 slirp_allow(optarg, IPPROTO_TCP);
4654 break;
4655 case QEMU_OPTION_allow_udp:
4656 slirp_allow(optarg, IPPROTO_UDP);
4657 break;
4658 case QEMU_OPTION_drop_log:
4659 {
4660 FILE* drop_log_fd;
rich canningsd952f282011-03-01 15:40:09 -08004661 drop_log_filename = optarg;
4662 drop_log_fd = fopen(optarg, "w+");
rich cannings7339b552011-02-16 13:43:44 -08004663
4664 if (!drop_log_fd) {
4665 fprintf(stderr, "Cannot open drop log: %s\n", optarg);
4666 exit(1);
4667 }
4668
4669 slirp_drop_log_fd(drop_log_fd);
4670 }
4671 break;
4672
4673 case QEMU_OPTION_dns_log:
4674 {
4675 FILE* dns_log_fd;
rich canningsd952f282011-03-01 15:40:09 -08004676 dns_log_filename = optarg;
4677 dns_log_fd = fopen(optarg, "wb+");
rich cannings7339b552011-02-16 13:43:44 -08004678
4679 if (dns_log_fd == NULL) {
4680 fprintf(stderr, "Cannot open dns log: %s\n", optarg);
4681 exit(1);
4682 }
4683
4684 slirp_dns_log_fd(dns_log_fd);
4685 }
4686 break;
4687
4688
4689 case QEMU_OPTION_max_dns_conns:
4690 {
4691 int max_dns_conns = 0;
4692 if (parse_int(optarg, &max_dns_conns)) {
4693 fprintf(stderr,
4694 "qemu: syntax: -max-dns-conns max_connections\n");
4695 exit(1);
4696 }
4697 if (max_dns_conns <= 0 || max_dns_conns == LONG_MAX) {
4698 fprintf(stderr,
4699 "Invalid arg for max dns connections: %s\n",
4700 optarg);
4701 exit(1);
4702 }
4703 slirp_set_max_dns_conns(max_dns_conns);
4704 }
4705 break;
4706
4707 case QEMU_OPTION_net_forward:
4708 net_slirp_forward(optarg);
4709 break;
4710 case QEMU_OPTION_net_forward_tcp2sink:
4711 {
4712 SockAddress saddr;
4713
4714 if (parse_host_port(&saddr, optarg)) {
4715 fprintf(stderr,
4716 "Invalid ip/port %s for "
4717 "-forward-dropped-tcp2sink. "
4718 "We expect 'sink_ip:sink_port'\n",
4719 optarg);
4720 exit(1);
4721 }
4722 slirp_forward_dropped_tcp2sink(saddr.u.inet.address,
4723 saddr.u.inet.port);
4724 }
4725 break;
4726 /* -------------------------------------------------------*/
4727
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004728 case QEMU_OPTION_tb_size:
4729 tb_size = strtol(optarg, NULL, 0);
4730 if (tb_size < 0)
4731 tb_size = 0;
4732 break;
4733 case QEMU_OPTION_icount:
David Turner6a9ef172010-09-09 22:54:36 +02004734 icount_option = optarg;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004735 break;
4736 case QEMU_OPTION_incoming:
4737 incoming = optarg;
4738 break;
4739#ifndef _WIN32
4740 case QEMU_OPTION_chroot:
4741 chroot_dir = optarg;
4742 break;
4743 case QEMU_OPTION_runas:
4744 run_as = optarg;
4745 break;
4746#endif
4747#ifdef CONFIG_XEN
4748 case QEMU_OPTION_xen_domid:
4749 xen_domid = atoi(optarg);
4750 break;
4751 case QEMU_OPTION_xen_create:
4752 xen_mode = XEN_CREATE;
4753 break;
4754 case QEMU_OPTION_xen_attach:
4755 xen_mode = XEN_ATTACH;
4756 break;
4757#endif
4758
4759
4760 case QEMU_OPTION_mic:
4761 audio_input_source = (char*)optarg;
4762 break;
4763#ifdef CONFIG_TRACE
David 'Digit' Turnera577fca2009-10-15 18:18:09 -07004764 case QEMU_OPTION_trace:
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004765 trace_filename = optarg;
4766 tracing = 1;
4767 break;
4768#if 0
4769 case QEMU_OPTION_trace_miss:
4770 trace_cache_miss = 1;
4771 break;
4772 case QEMU_OPTION_trace_addr:
4773 trace_all_addr = 1;
4774 break;
4775#endif
4776 case QEMU_OPTION_tracing:
4777 if (strcmp(optarg, "off") == 0)
4778 tracing = 0;
4779 else if (strcmp(optarg, "on") == 0 && trace_filename)
4780 tracing = 1;
4781 else {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004782 PANIC("Unexpected option to -tracing ('%s')",
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004783 optarg);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004784 }
4785 break;
4786#if 0
4787 case QEMU_OPTION_dcache_load_miss:
4788 dcache_load_miss_penalty = atoi(optarg);
4789 break;
4790 case QEMU_OPTION_dcache_store_miss:
4791 dcache_store_miss_penalty = atoi(optarg);
4792 break;
4793#endif
4794#endif
4795#ifdef CONFIG_NAND
4796 case QEMU_OPTION_nand:
4797 nand_add_dev(optarg);
4798 break;
4799#endif
Vladimir Chtchetkined81e6d12010-06-15 16:46:32 -07004800 case QEMU_OPTION_android_ports:
4801 android_op_ports = (char*)optarg;
4802 break;
4803
4804 case QEMU_OPTION_android_port:
4805 android_op_port = (char*)optarg;
4806 break;
4807
4808 case QEMU_OPTION_android_report_console:
4809 android_op_report_console = (char*)optarg;
4810 break;
4811
4812 case QEMU_OPTION_http_proxy:
4813 op_http_proxy = (char*)optarg;
4814 break;
Vladimir Chtchetkine43552dc2010-07-22 11:23:19 -07004815
4816 case QEMU_OPTION_charmap:
4817 op_charmap_file = (char*)optarg;
4818 break;
Vladimir Chtchetkinedd50f7d2010-07-30 09:16:41 -07004819
Vladimir Chtchetkine074d1f92010-08-06 09:29:50 -07004820 case QEMU_OPTION_android_hw:
4821 android_op_hwini = (char*)optarg;
4822 break;
Vladimir Chtchetkine13f3b6c2010-08-25 09:49:25 -07004823
Vladimir Chtchetkine7fbf4972010-08-11 15:30:32 -07004824 case QEMU_OPTION_dns_server:
4825 android_op_dns_server = (char*)optarg;
4826 break;
4827
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -07004828 case QEMU_OPTION_radio:
4829 android_op_radio = (char*)optarg;
4830 break;
4831
4832 case QEMU_OPTION_gps:
4833 android_op_gps = (char*)optarg;
4834 break;
4835
4836 case QEMU_OPTION_audio:
4837 android_op_audio = (char*)optarg;
4838 break;
4839
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -07004840 case QEMU_OPTION_cpu_delay:
4841 android_op_cpu_delay = (char*)optarg;
4842 break;
4843
Vladimir Chtchetkine13f3b6c2010-08-25 09:49:25 -07004844 case QEMU_OPTION_show_kernel:
4845 android_kmsg_init(ANDROID_KMSG_PRINT_MESSAGES);
4846 break;
4847
Vladimir Chtchetkinee1316862010-08-26 09:03:54 -07004848#ifdef CONFIG_NAND_LIMITS
4849 case QEMU_OPTION_nand_limits:
4850 android_op_nand_limits = (char*)optarg;
4851 break;
4852#endif // CONFIG_NAND_LIMITS
4853
4854 case QEMU_OPTION_netspeed:
4855 android_op_netspeed = (char*)optarg;
4856 break;
4857
4858 case QEMU_OPTION_netdelay:
4859 android_op_netdelay = (char*)optarg;
4860 break;
4861
4862 case QEMU_OPTION_netfast:
4863 android_op_netfast = 1;
4864 break;
4865
Vladimir Chtchetkine318f17a2010-08-27 09:09:45 -07004866 case QEMU_OPTION_tcpdump:
4867 android_op_tcpdump = (char*)optarg;
4868 break;
Vladimir Chtchetkinee1316862010-08-26 09:03:54 -07004869
Vladimir Chtchetkineb25bf2a2010-09-08 11:09:23 -07004870 case QEMU_OPTION_boot_property:
4871 boot_property_parse_option((char*)optarg);
4872 break;
4873
4874 case QEMU_OPTION_lcd_density:
4875 android_op_lcd_density = (char*)optarg;
4876 break;
4877
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004878 case QEMU_OPTION_ui_port:
4879 android_op_ui_port = (char*)optarg;
4880 break;
4881
4882 case QEMU_OPTION_ui_settings:
4883 android_op_ui_settings = (char*)optarg;
4884 break;
4885
David 'Digit' Turnerca29fbb2011-01-02 13:17:22 +01004886 case QEMU_OPTION_audio_test_out:
4887 android_audio_test_start_out();
4888 break;
4889
Vladimir Chtchetkine90c62352011-01-13 11:24:07 -08004890 case QEMU_OPTION_android_avdname:
4891 android_op_avd_name = (char*)optarg;
4892 break;
4893
4894 case QEMU_OPTION_timezone:
4895 if (timezone_set((char*)optarg)) {
4896 fprintf(stderr, "emulator: it seems the timezone '%s' is not in zoneinfo format\n",
4897 (char*)optarg);
4898 }
4899 break;
4900
Vladimir Chtchetkineb5365f32010-08-09 13:33:57 -07004901#ifdef CONFIG_MEMCHECK
4902 case QEMU_OPTION_android_memcheck:
4903 android_op_memcheck = (char*)optarg;
Vladimir Chtchetkine7fbf4972010-08-11 15:30:32 -07004904 /* This will set ro.kernel.memcheck system property
4905 * to memcheck's tracing flags. */
David 'Digit' Turner5f824112011-03-01 14:00:26 +01004906 stralloc_add_format(kernel_config, " memcheck=%s", android_op_memcheck);
Vladimir Chtchetkineb5365f32010-08-09 13:33:57 -07004907 break;
4908#endif // CONFIG_MEMCHECK
David 'Digit' Turnerbdb6f2d2011-02-23 15:57:25 +01004909
4910 case QEMU_OPTION_snapshot_no_time_update:
4911 android_snapshot_update_time = 0;
4912 break;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004913 }
4914 }
4915 }
4916
Vladimir Chtchetkine43552dc2010-07-22 11:23:19 -07004917 /* Initialize character map. */
4918 if (android_charmap_setup(op_charmap_file)) {
4919 if (op_charmap_file) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004920 PANIC(
4921 "Unable to initialize character map from file %s.",
Vladimir Chtchetkine43552dc2010-07-22 11:23:19 -07004922 op_charmap_file);
4923 } else {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07004924 PANIC(
4925 "Unable to initialize default character map.");
Vladimir Chtchetkine43552dc2010-07-22 11:23:19 -07004926 }
Vladimir Chtchetkine43552dc2010-07-22 11:23:19 -07004927 }
4928
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07004929 /* If no data_dir is specified then try to find it relative to the
4930 executable path. */
4931 if (!data_dir) {
4932 data_dir = find_datadir(argv[0]);
4933 }
4934 /* If all else fails use the install patch specified when building. */
4935 if (!data_dir) {
4936 data_dir = CONFIG_QEMU_SHAREDIR;
4937 }
4938
David 'Digit' Turner2507cab2011-02-10 16:29:17 +01004939 if (!android_op_hwini) {
4940 PANIC("Missing -android-hw <file> option!");
Vladimir Chtchetkine074d1f92010-08-06 09:29:50 -07004941 }
David 'Digit' Turner2507cab2011-02-10 16:29:17 +01004942 hw_ini = iniFile_newFromFile(android_op_hwini);
4943 if (hw_ini == NULL) {
4944 PANIC("Could not find %s file.", android_op_hwini);
4945 }
Vladimir Chtchetkine074d1f92010-08-06 09:29:50 -07004946 androidHwConfig_read(android_hw, hw_ini);
4947 iniFile_free(hw_ini);
David 'Digit' Turner2507cab2011-02-10 16:29:17 +01004948
4949 {
4950 int width = android_hw->hw_lcd_width;
4951 int height = android_hw->hw_lcd_height;
4952 int depth = android_hw->hw_lcd_depth;
4953
4954 /* A bit of sanity checking */
4955 if (width <= 0 || height <= 0 ||
4956 (depth != 16 && depth != 32) ||
4957 (((width|height) & 3) != 0) )
4958 {
4959 PANIC("Invalid display configuration (%d,%d,%d)",
4960 width, height, depth);
4961 }
4962 android_display_width = width;
4963 android_display_height = height;
4964 android_display_bpp = depth;
4965 }
Vladimir Chtchetkine074d1f92010-08-06 09:29:50 -07004966
Vladimir Chtchetkinee1316862010-08-26 09:03:54 -07004967#ifdef CONFIG_NAND_LIMITS
4968 /* Init nand stuff. */
4969 if (android_op_nand_limits) {
4970 parse_nand_limits(android_op_nand_limits);
4971 }
4972#endif // CONFIG_NAND_LIMITS
4973
David 'Digit' Turner53eb66d2011-03-01 14:58:23 +01004974 /* Initialize AVD name from hardware configuration if needed */
4975 if (!android_op_avd_name) {
4976 if (android_hw->avd_name && *android_hw->avd_name) {
4977 android_op_avd_name = android_hw->avd_name;
4978 VERBOSE_PRINT(init,"AVD Name: %s", android_op_avd_name);
4979 }
4980 }
4981
David 'Digit' Turner40841b22011-03-01 14:04:00 +01004982 /* Initialize system partition image */
4983 {
4984 char tmp[PATH_MAX+32];
4985 const char* sysImage = android_hw->disk_systemPartition_path;
4986 const char* initImage = android_hw->disk_systemPartition_initPath;
4987 uint64_t sysBytes = android_hw->disk_systemPartition_size;
4988
4989 if (sysBytes == 0) {
4990 PANIC("Invalid system partition size: %" PRUd64, sysBytes);
4991 }
4992
4993 snprintf(tmp,sizeof(tmp),"system,size=0x%" PRUx64, sysBytes);
4994
4995 if (sysImage && *sysImage) {
4996 if (filelock_create(sysImage) == NULL) {
4997 fprintf(stderr,"WARNING: System image already in use, changes will not persist!\n");
4998 /* If there is no file= parameters, nand_add_dev will create
4999 * a temporary file to back the partition image. */
5000 } else {
5001 pstrcat(tmp,sizeof(tmp),",file=");
5002 pstrcat(tmp,sizeof(tmp),sysImage);
5003 }
5004 }
5005 if (initImage && *initImage) {
5006 if (!path_exists(initImage)) {
5007 PANIC("Invalid initial system image path: %s", initImage);
5008 }
5009 pstrcat(tmp,sizeof(tmp),",initfile=");
5010 pstrcat(tmp,sizeof(tmp),initImage);
5011 } else {
5012 PANIC("Missing initial system image path!");
5013 }
5014 nand_add_dev(tmp);
5015 }
5016
David 'Digit' Turnerfd59c332011-03-01 00:48:52 +01005017 /* Initialize data partition image */
5018 {
5019 char tmp[PATH_MAX+32];
5020 const char* dataImage = android_hw->disk_dataPartition_path;
5021 const char* initImage = android_hw->disk_dataPartition_initPath;
5022 uint64_t dataBytes = android_hw->disk_dataPartition_size;
5023
5024 if (dataBytes == 0) {
5025 PANIC("Invalid data partition size: %" PRUd64, dataBytes);
5026 }
5027
5028 snprintf(tmp,sizeof(tmp),"userdata,size=0x%" PRUx64, dataBytes);
5029
5030 if (dataImage && *dataImage) {
5031 if (filelock_create(dataImage) == NULL) {
5032 fprintf(stderr, "WARNING: Data partition already in use. Changes will not persist!\n");
5033 /* Note: if there is no file= parameters, nand_add_dev() will
5034 * create a temporary file to back the partition image. */
5035 } else {
5036 /* Create the file if needed */
5037 if (!path_exists(dataImage)) {
5038 path_empty_file(dataImage);
5039 }
5040 pstrcat(tmp, sizeof(tmp), ",file=");
5041 pstrcat(tmp, sizeof(tmp), dataImage);
5042 }
5043 }
5044 if (initImage && *initImage) {
5045 pstrcat(tmp, sizeof(tmp), ",initfile=");
5046 pstrcat(tmp, sizeof(tmp), initImage);
5047 }
5048 nand_add_dev(tmp);
5049 }
5050
David 'Digit' Turner48a3c662011-03-01 14:03:20 +01005051 /* Init SD-Card stuff. For Android, it is always hda */
5052 /* If the -hda option was used, ignore the Android-provided one */
5053 if (hda_opts == NULL) {
5054 const char* sdPath = android_hw->hw_sdCard_path;
5055 if (sdPath && *sdPath) {
5056 if (!path_exists(sdPath)) {
5057 fprintf(stderr, "WARNING: SD Card image is missing: %s\n", sdPath);
5058 } else if (filelock_create(sdPath) == NULL) {
5059 fprintf(stderr, "WARNING: SD Card image already in use: %s\n", sdPath);
5060 } else {
5061 /* Successful locking */
5062 hda_opts = drive_add(sdPath, HD_ALIAS, 0);
5063 }
5064 }
5065 }
5066
David 'Digit' Turner5f64b872011-02-28 23:23:05 +01005067 if (hdb_opts == NULL) {
5068 const char* spath = android_hw->disk_snapStorage_path;
5069 if (spath && *spath) {
5070 if (!path_exists(spath)) {
5071 PANIC("Snapshot storage file does not exist: %s", spath);
5072 }
5073 if (filelock_create(spath) == NULL) {
5074 PANIC("Snapshot storag already in use: %s", spath);
5075 }
5076 hdb_opts = drive_add(spath, HD_ALIAS, 1);
5077 }
5078 }
5079
Vladimir Chtchetkineb25bf2a2010-09-08 11:09:23 -07005080 /* Set the VM's max heap size, passed as a boot property */
5081 if (android_hw->vm_heapSize > 0) {
5082 char tmp[64];
5083 snprintf(tmp, sizeof(tmp), "%dm", android_hw->vm_heapSize);
5084 boot_property_add("dalvik.vm.heapsize",tmp);
5085 }
5086
Vladimir Chtchetkinee1316862010-08-26 09:03:54 -07005087 /* Initialize net speed and delays stuff. */
5088 if (android_parse_network_speed(android_op_netspeed) < 0 ) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005089 PANIC("invalid -netspeed parameter '%s'",
Vladimir Chtchetkinee1316862010-08-26 09:03:54 -07005090 android_op_netspeed);
Vladimir Chtchetkinee1316862010-08-26 09:03:54 -07005091 }
5092
5093 if ( android_parse_network_latency(android_op_netdelay) < 0 ) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005094 PANIC("invalid -netdelay parameter '%s'",
Vladimir Chtchetkinee1316862010-08-26 09:03:54 -07005095 android_op_netdelay);
Vladimir Chtchetkinee1316862010-08-26 09:03:54 -07005096 }
5097
5098 if (android_op_netfast) {
5099 qemu_net_download_speed = 0;
5100 qemu_net_upload_speed = 0;
5101 qemu_net_min_latency = 0;
5102 qemu_net_max_latency = 0;
5103 }
5104
Vladimir Chtchetkineb25bf2a2010-09-08 11:09:23 -07005105 /* Initialize LCD density */
David 'Digit' Turner5377c5b2011-02-10 16:52:19 +01005106 if (android_hw->hw_lcd_density) {
5107 long density = android_hw->hw_lcd_density;
5108 if (density <= 0) {
5109 PANIC("Invalid hw.lcd.density value: %ld", density);
Vladimir Chtchetkineb25bf2a2010-09-08 11:09:23 -07005110 }
5111 hwLcd_setBootProperty(density);
5112 }
5113
Vladimir Chtchetkine318f17a2010-08-27 09:09:45 -07005114 /* Initialize TCP dump */
5115 if (android_op_tcpdump) {
5116 if (qemu_tcpdump_start(android_op_tcpdump) < 0) {
5117 fprintf(stdout, "could not start packet capture: %s\n", strerror(errno));
5118 }
5119 }
5120
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -07005121 /* Initialize modem */
5122 if (android_op_radio) {
5123 CharDriverState* cs = qemu_chr_open("radio", android_op_radio, NULL);
5124 if (cs == NULL) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005125 PANIC("unsupported character device specification: %s\n"
5126 "used -help-char-devices for list of available formats",
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -07005127 android_op_radio);
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -07005128 }
5129 android_qemud_set_channel( ANDROID_QEMUD_GSM, cs);
5130 } else if (android_hw->hw_gsmModem != 0 ) {
5131 if ( android_qemud_get_channel( ANDROID_QEMUD_GSM, &android_modem_cs ) < 0 ) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005132 PANIC("could not initialize qemud 'gsm' channel");
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -07005133 }
5134 }
5135
5136 /* Initialize GPS */
5137 if (android_op_gps) {
5138 CharDriverState* cs = qemu_chr_open("gps", android_op_gps, NULL);
5139 if (cs == NULL) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005140 PANIC("unsupported character device specification: %s\n"
5141 "used -help-char-devices for list of available formats",
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -07005142 android_op_gps);
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -07005143 }
5144 android_qemud_set_channel( ANDROID_QEMUD_GPS, cs);
5145 } else if (android_hw->hw_gps != 0) {
5146 if ( android_qemud_get_channel( "gps", &android_gps_cs ) < 0 ) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005147 PANIC("could not initialize qemud 'gps' channel");
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -07005148 }
5149 }
5150
5151 /* Initialize audio. */
5152 if (android_op_audio) {
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -07005153 if ( !audio_check_backend_name( 0, android_op_audio ) ) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005154 PANIC("'%s' is not a valid audio output backend. see -help-audio-out",
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -07005155 android_op_audio);
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -07005156 }
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -07005157 }
5158
5159 if (android_op_cpu_delay) {
5160 char* end;
5161 long delay = strtol(android_op_cpu_delay, &end, 0);
5162 if (end == NULL || *end || delay < 0 || delay > 1000 ) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005163 PANIC("option -cpu-delay must be an integer between 0 and 1000" );
Vladimir Chtchetkineb2438402010-08-24 08:55:33 -07005164 }
5165 if (delay > 0)
5166 delay = (1000-delay);
5167
5168 qemu_cpu_delay = (int) delay;
5169 }
5170
Vladimir Chtchetkine7fbf4972010-08-11 15:30:32 -07005171 if (android_op_dns_server) {
5172 char* x = strchr(android_op_dns_server, ',');
5173 dns_count = 0;
5174 if (x == NULL)
5175 {
5176 if ( add_dns_server( android_op_dns_server ) == 0 )
5177 dns_count = 1;
5178 }
5179 else
5180 {
5181 x = android_op_dns_server;
5182 while (*x) {
5183 char* y = strchr(x, ',');
5184
5185 if (y != NULL) {
5186 *y = 0;
5187 y++;
5188 } else {
5189 y = x + strlen(x);
5190 }
5191
5192 if (y > x && add_dns_server( x ) == 0) {
5193 dns_count += 1;
5194 }
5195 x = y;
5196 }
5197 }
5198 if (dns_count == 0)
5199 fprintf( stdout, "### WARNING: will use system default DNS server\n" );
5200 }
5201
5202 if (dns_count == 0)
5203 dns_count = slirp_get_system_dns_servers();
5204 if (dns_count) {
David 'Digit' Turner5f824112011-03-01 14:00:26 +01005205 stralloc_add_format(kernel_config, " ndns=%d", dns_count);
Vladimir Chtchetkine7fbf4972010-08-11 15:30:32 -07005206 }
5207
Vladimir Chtchetkineb5365f32010-08-09 13:33:57 -07005208#ifdef CONFIG_MEMCHECK
5209 if (android_op_memcheck) {
5210 memcheck_init(android_op_memcheck);
5211 }
5212#endif // CONFIG_MEMCHECK
5213
David 'Digit' Turnerc480cca2011-02-25 16:43:34 +01005214 /* Initialize cache partition, if any */
5215 if (android_hw->disk_cachePartition != 0) {
5216 char tmp[PATH_MAX+32];
5217 const char* partPath = android_hw->disk_cachePartition_path;
5218 uint32_t partSize = android_hw->disk_cachePartition_size;
5219
5220 if (!partPath || !*partPath || !strcmp(partPath, "<temp>"))
5221 {
5222 /* Use temporary cache partition */
5223 snprintf(tmp, sizeof(tmp), "cache,size=0x%x", partSize);
5224 }
5225 else
5226 {
5227 /* Use specific cache partition */
5228 snprintf(tmp, sizeof(tmp), "cache,size=0x%x,file=%s", partSize, partPath);
5229 }
5230 nand_add_dev(tmp);
5231 }
5232
David 'Digit' Turner062dd6a2011-03-01 14:50:07 +01005233 /* We always force qemu=1 when running inside QEMU */
5234 stralloc_add_str(kernel_params, " qemu=1");
5235
5236 /* We always initialize the first serial port for the android-kmsg
5237 * character device (used to send kernel messages) */
5238 serial_hds_add_at(0, "android-kmsg");
5239 stralloc_add_str(kernel_params, " console=ttyS0");
5240
5241 /* We always initialize the second serial port for the android-qemud
5242 * character device as well */
5243 serial_hds_add_at(1, "android-qemud");
5244 stralloc_add_str(kernel_params, " android.qemud=ttyS1");
5245
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005246#if defined(CONFIG_KVM) && defined(CONFIG_KQEMU)
5247 if (kvm_allowed && kqemu_allowed) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005248 PANIC(
5249 "You can not enable both KVM and kqemu at the same time");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005250 }
5251#endif
5252
5253 machine->max_cpus = machine->max_cpus ?: 1; /* Default to UP */
5254 if (smp_cpus > machine->max_cpus) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005255 PANIC("Number of SMP cpus requested (%d), exceeds max cpus "
5256 "supported by machine `%s' (%d)", smp_cpus, machine->name,
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005257 machine->max_cpus);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005258 }
5259
5260 if (display_type == DT_NOGRAPHIC) {
5261 if (serial_device_index == 0)
5262 serial_devices[0] = "stdio";
5263 if (parallel_device_index == 0)
5264 parallel_devices[0] = "null";
5265 if (strncmp(monitor_device, "vc", 2) == 0)
5266 monitor_device = "stdio";
5267 }
5268
5269#ifndef _WIN32
5270 if (daemonize) {
5271 pid_t pid;
5272
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005273 if (pipe(fds) == -1) {
5274 PANIC("Unable to aquire pidfile");
5275 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005276
5277 pid = fork();
5278 if (pid > 0) {
5279 uint8_t status;
5280 ssize_t len;
5281
5282 close(fds[1]);
5283
5284 again:
5285 len = read(fds[0], &status, 1);
5286 if (len == -1 && (errno == EINTR))
5287 goto again;
5288
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005289 if (len != 1) {
5290 PANIC("Error when aquiring pidfile");
5291 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005292 else if (status == 1) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005293 PANIC("Could not acquire pidfile");
5294 } else {
5295 QEMU_EXIT(0);
5296 }
5297 } else if (pid < 0) {
5298 PANIC("Unable to daemonize");
5299 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005300
5301 setsid();
5302
5303 pid = fork();
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005304 if (pid > 0) {
5305 QEMU_EXIT(0);
5306 } else if (pid < 0) {
5307 PANIC("Could not acquire pid file");
5308 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005309
5310 umask(027);
5311
5312 signal(SIGTSTP, SIG_IGN);
5313 signal(SIGTTOU, SIG_IGN);
5314 signal(SIGTTIN, SIG_IGN);
5315 }
5316
5317 if (pid_file && qemu_create_pidfile(pid_file) != 0) {
5318 if (daemonize) {
5319 uint8_t status = 1;
David 'Digit' Turner4e024bb2010-09-22 14:19:28 +02005320 int ret;
5321 do {
5322 ret = write(fds[1], &status, 1);
5323 } while (ret < 0 && errno == EINTR);
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005324 PANIC("Could not acquire pid file");
5325 } else {
5326 PANIC("Could not acquire pid file");
5327 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005328 }
5329#endif
5330
5331#ifdef CONFIG_KQEMU
5332 if (smp_cpus > 1)
5333 kqemu_allowed = 0;
5334#endif
5335 if (qemu_init_main_loop()) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005336 PANIC("qemu_init_main_loop failed");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005337 }
David 'Digit' Turner0b019492011-03-01 14:02:42 +01005338
5339 if (kernel_filename == NULL) {
5340 kernel_filename = android_hw->kernel_path;
5341 }
5342 if (initrd_filename == NULL) {
5343 initrd_filename = android_hw->disk_ramdisk_path;
5344 }
5345
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005346 linux_boot = (kernel_filename != NULL);
5347 net_boot = (boot_devices_bitmap >> ('n' - 'a')) & 0xF;
5348
5349 if (!linux_boot && *kernel_cmdline != '\0') {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005350 PANIC("-append only allowed with -kernel option");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005351 }
5352
5353 if (!linux_boot && initrd_filename != NULL) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005354 PANIC("-initrd only allowed with -kernel option");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005355 }
5356
5357 /* boot to floppy or the default cd if no hard disk defined yet */
5358 if (!boot_devices[0]) {
5359 boot_devices = "cad";
5360 }
5361 setvbuf(stdout, NULL, _IOLBF, 0);
5362
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005363 if (init_timer_alarm() < 0) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005364 PANIC("could not initialize alarm timer");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005365 }
David Turner6a9ef172010-09-09 22:54:36 +02005366 configure_icount(icount_option);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005367
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005368 /* init network clients */
5369 if (nb_net_clients == 0) {
5370 /* if no clients, we use a default config */
5371 net_clients[nb_net_clients++] = "nic";
5372#ifdef CONFIG_SLIRP
5373 net_clients[nb_net_clients++] = "user";
5374#endif
5375 }
5376
5377 for(i = 0;i < nb_net_clients; i++) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005378 if (net_client_parse(net_clients[i]) < 0) {
5379 PANIC("Unable to parse net clients");
5380 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005381 }
5382 net_client_check();
5383
5384#ifdef TARGET_I386
5385 /* XXX: this should be moved in the PC machine instantiation code */
5386 if (net_boot != 0) {
5387 int netroms = 0;
5388 for (i = 0; i < nb_nics && i < 4; i++) {
5389 const char *model = nd_table[i].model;
5390 char buf[1024];
5391 char *filename;
5392 if (net_boot & (1 << i)) {
5393 if (model == NULL)
5394 model = "ne2k_pci";
5395 snprintf(buf, sizeof(buf), "pxe-%s.bin", model);
5396 filename = qemu_find_file(QEMU_FILE_TYPE_BIOS, buf);
5397 if (filename && get_image_size(filename) > 0) {
5398 if (nb_option_roms >= MAX_OPTION_ROMS) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005399 PANIC("Too many option ROMs");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005400 }
5401 option_rom[nb_option_roms] = qemu_strdup(buf);
5402 nb_option_roms++;
5403 netroms++;
5404 }
5405 if (filename) {
5406 qemu_free(filename);
5407 }
5408 }
5409 }
5410 if (netroms == 0) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005411 PANIC("No valid PXE rom found for network device");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005412 }
5413 }
5414#endif
5415
5416 /* init the bluetooth world */
5417 for (i = 0; i < nb_bt_opts; i++)
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005418 if (bt_parse(bt_opts[i])) {
5419 PANIC("Unable to parse bluetooth options");
5420 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005421
5422 /* init the memory */
David 'Digit' Turner5377c5b2011-02-10 16:52:19 +01005423 if (ram_size == 0) {
5424 ram_size = android_hw->hw_ramSize * 1024LL * 1024;
5425 if (ram_size == 0) {
5426 ram_size = DEFAULT_RAM_SIZE * 1024 * 1024;
5427 }
5428 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005429
5430#ifdef CONFIG_KQEMU
5431 /* FIXME: This is a nasty hack because kqemu can't cope with dynamic
5432 guest ram allocation. It needs to go away. */
5433 if (kqemu_allowed) {
5434 kqemu_phys_ram_size = ram_size + 8 * 1024 * 1024 + 4 * 1024 * 1024;
5435 kqemu_phys_ram_base = qemu_vmalloc(kqemu_phys_ram_size);
5436 if (!kqemu_phys_ram_base) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005437 PANIC("Could not allocate physical memory");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005438 }
5439 }
5440#endif
5441
rich canningsd952f282011-03-01 15:40:09 -08005442#ifndef _WIN32
5443 init_qemu_clear_logs_sig();
5444#endif
5445
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005446 /* init the dynamic translator */
5447 cpu_exec_init_all(tb_size * 1024 * 1024);
5448
5449 bdrv_init();
5450
5451 /* we always create the cdrom drive, even if no disk is there */
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +01005452#if 0
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005453 if (nb_drives_opt < MAX_DRIVES)
5454 drive_add(NULL, CDROM_ALIAS);
5455
5456 /* we always create at least one floppy */
5457
5458 if (nb_drives_opt < MAX_DRIVES)
5459 drive_add(NULL, FD_ALIAS, 0);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005460 /* we always create one sd slot, even if no card is in it */
5461
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +01005462 if (1) {
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005463 drive_add(NULL, SD_ALIAS);
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +01005464 }
5465#endif
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005466
5467 /* open the virtual block devices */
David 'Digit' Turnercb42a1b2010-12-23 02:54:08 +01005468 if (snapshot)
5469 qemu_opts_foreach(qemu_find_opts("drive"), drive_enable_snapshot, NULL, 0);
5470 if (qemu_opts_foreach(qemu_find_opts("drive"), drive_init_func, &machine->use_scsi, 1) != 0)
5471 exit(1);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005472
David Turner6a9ef172010-09-09 22:54:36 +02005473 //register_savevm("timer", 0, 2, timer_save, timer_load, &timers_state);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005474 register_savevm_live("ram", 0, 3, ram_save_live, NULL, ram_load, NULL);
5475
5476#ifndef _WIN32
5477 /* must be after terminal init, SDL library changes signal handlers */
5478 sighandler_setup();
5479#endif
5480
5481 /* Maintain compatibility with multiple stdio monitors */
5482 if (!strcmp(monitor_device,"stdio")) {
5483 for (i = 0; i < MAX_SERIAL_PORTS; i++) {
5484 const char *devname = serial_devices[i];
5485 if (devname && !strcmp(devname,"mon:stdio")) {
5486 monitor_device = NULL;
5487 break;
5488 } else if (devname && !strcmp(devname,"stdio")) {
5489 monitor_device = NULL;
5490 serial_devices[i] = "mon:stdio";
5491 break;
5492 }
5493 }
5494 }
5495
5496 if (nb_numa_nodes > 0) {
5497 int i;
5498
5499 if (nb_numa_nodes > smp_cpus) {
5500 nb_numa_nodes = smp_cpus;
5501 }
5502
5503 /* If no memory size if given for any node, assume the default case
5504 * and distribute the available memory equally across all nodes
5505 */
5506 for (i = 0; i < nb_numa_nodes; i++) {
5507 if (node_mem[i] != 0)
5508 break;
5509 }
5510 if (i == nb_numa_nodes) {
5511 uint64_t usedmem = 0;
5512
5513 /* On Linux, the each node's border has to be 8MB aligned,
5514 * the final node gets the rest.
5515 */
5516 for (i = 0; i < nb_numa_nodes - 1; i++) {
5517 node_mem[i] = (ram_size / nb_numa_nodes) & ~((1 << 23UL) - 1);
5518 usedmem += node_mem[i];
5519 }
5520 node_mem[i] = ram_size - usedmem;
5521 }
5522
5523 for (i = 0; i < nb_numa_nodes; i++) {
5524 if (node_cpumask[i] != 0)
5525 break;
5526 }
5527 /* assigning the VCPUs round-robin is easier to implement, guest OSes
5528 * must cope with this anyway, because there are BIOSes out there in
5529 * real machines which also use this scheme.
5530 */
5531 if (i == nb_numa_nodes) {
5532 for (i = 0; i < smp_cpus; i++) {
5533 node_cpumask[i % nb_numa_nodes] |= 1 << i;
5534 }
5535 }
5536 }
5537
5538 if (kvm_enabled()) {
5539 int ret;
5540
5541 ret = kvm_init(smp_cpus);
5542 if (ret < 0) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005543 PANIC("failed to initialize KVM");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005544 }
5545 }
5546
5547 if (monitor_device) {
5548 monitor_hd = qemu_chr_open("monitor", monitor_device, NULL);
5549 if (!monitor_hd) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005550 PANIC("qemu: could not open monitor device '%s'",
5551 monitor_device);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005552 }
5553 }
5554
5555 for(i = 0; i < MAX_SERIAL_PORTS; i++) {
David 'Digit' Turner062dd6a2011-03-01 14:50:07 +01005556 serial_hds_add(serial_devices[i]);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005557 }
5558
5559 for(i = 0; i < MAX_PARALLEL_PORTS; i++) {
5560 const char *devname = parallel_devices[i];
5561 if (devname && strcmp(devname, "none")) {
5562 char label[32];
5563 snprintf(label, sizeof(label), "parallel%d", i);
5564 parallel_hds[i] = qemu_chr_open(label, devname, NULL);
5565 if (!parallel_hds[i]) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005566 PANIC("qemu: could not open parallel device '%s'",
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005567 devname);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005568 }
5569 }
5570 }
5571
5572 for(i = 0; i < MAX_VIRTIO_CONSOLES; i++) {
5573 const char *devname = virtio_consoles[i];
5574 if (devname && strcmp(devname, "none")) {
5575 char label[32];
5576 snprintf(label, sizeof(label), "virtcon%d", i);
5577 virtcon_hds[i] = qemu_chr_open(label, devname, NULL);
5578 if (!virtcon_hds[i]) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005579 PANIC("qemu: could not open virtio console '%s'",
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005580 devname);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005581 }
5582 }
5583 }
5584
5585 module_call_init(MODULE_INIT_DEVICE);
5586
5587
5588#ifdef CONFIG_TRACE
5589 if (trace_filename) {
5590 trace_init(trace_filename);
5591#if 0
5592 // We don't need the dcache code until we can get load and store tracing
5593 // working again.
5594 dcache_init(dcache_size, dcache_ways, dcache_line_size,
5595 dcache_replace_policy, dcache_load_miss_penalty,
5596 dcache_store_miss_penalty);
5597#endif
5598 fprintf(stderr, "-- When done tracing, exit the emulator. --\n");
5599 }
5600#endif
5601
Vladimir Chtchetkine7fbf4972010-08-11 15:30:32 -07005602 /* Combine kernel command line passed from the UI with parameters
David 'Digit' Turner5f824112011-03-01 14:00:26 +01005603 * collected during initialization.
5604 *
5605 * The order is the following:
5606 * - parameters from the hw configuration (kernel.parameters)
5607 * - additionnal parameters from options (e.g. -memcheck)
5608 * - the -append parameters.
5609 */
5610 {
5611 const char* kernel_parameters;
Vladimir Chtchetkine7fbf4972010-08-11 15:30:32 -07005612
David 'Digit' Turner0b019492011-03-01 14:02:42 +01005613 if (android_hw->kernel_parameters) {
5614 stralloc_add_str(kernel_params, android_hw->kernel_parameters);
5615 }
5616
David 'Digit' Turner5f824112011-03-01 14:00:26 +01005617 /* If not empty, kernel_config always contains a leading space */
5618 stralloc_append(kernel_params, kernel_config);
5619
5620 if (*kernel_cmdline) {
5621 stralloc_add_c(kernel_params, ' ');
5622 stralloc_add_str(kernel_params, kernel_cmdline);
5623 }
5624
David 'Digit' Turner062dd6a2011-03-01 14:50:07 +01005625 /* Remove any leading/trailing spaces */
5626 stralloc_strip(kernel_params);
5627
David 'Digit' Turner5f824112011-03-01 14:00:26 +01005628 kernel_parameters = stralloc_cstr(kernel_params);
5629 VERBOSE_PRINT(init, "Kernel parameters: %s", kernel_parameters);
5630
5631 machine->init(ram_size,
5632 boot_devices,
5633 kernel_filename,
5634 kernel_parameters,
5635 initrd_filename,
5636 cpu_model);
5637
5638 stralloc_reset(kernel_params);
5639 stralloc_reset(kernel_config);
5640 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005641
5642
5643 for (env = first_cpu; env != NULL; env = env->next_cpu) {
5644 for (i = 0; i < nb_numa_nodes; i++) {
5645 if (node_cpumask[i] & (1 << env->cpu_index)) {
5646 env->numa_node = i;
5647 }
5648 }
5649 }
5650
5651 current_machine = machine;
5652
5653 /* Set KVM's vcpu state to qemu's initial CPUState. */
5654 if (kvm_enabled()) {
5655 int ret;
5656
5657 ret = kvm_sync_vcpus();
5658 if (ret < 0) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005659 PANIC("failed to initialize vcpus");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005660 }
5661 }
5662
5663 /* init USB devices */
5664 if (usb_enabled) {
5665 for(i = 0; i < usb_devices_index; i++) {
5666 if (usb_device_add(usb_devices[i], 0) < 0) {
5667 fprintf(stderr, "Warning: could not add USB device %s\n",
5668 usb_devices[i]);
5669 }
5670 }
5671 }
5672
Vladimir Chtchetkinecf755ea2011-01-12 14:38:19 -08005673 /* just use the first displaystate for the moment */
David 'Digit' Turner94702b02011-01-20 02:46:33 +01005674 ds = get_displaystate();
Vladimir Chtchetkinecf755ea2011-01-12 14:38:19 -08005675
David 'Digit' Turner2507cab2011-02-10 16:29:17 +01005676 /* Initialize display from the command line parameters. */
5677 android_display_reset(ds,
5678 android_display_width,
5679 android_display_height,
5680 android_display_bpp);
Vladimir Chtchetkinedd50f7d2010-07-30 09:16:41 -07005681
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005682 if (display_type == DT_DEFAULT) {
5683#if defined(CONFIG_SDL) || defined(CONFIG_COCOA)
5684 display_type = DT_SDL;
5685#else
5686 display_type = DT_VNC;
5687 vnc_display = "localhost:0,to=99";
5688 show_vnc_port = 1;
5689#endif
5690 }
Vladimir Chtchetkined81e6d12010-06-15 16:46:32 -07005691
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005692
5693 switch (display_type) {
5694 case DT_NOGRAPHIC:
5695 break;
5696#if defined(CONFIG_CURSES)
5697 case DT_CURSES:
5698 curses_display_init(ds, full_screen);
5699 break;
5700#endif
Vladimir Chtchetkineeb838252010-07-15 12:27:56 -07005701#if defined(CONFIG_SDL) && !defined(CONFIG_STANDALONE_CORE)
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005702 case DT_SDL:
5703 sdl_display_init(ds, full_screen, no_frame);
5704 break;
5705#elif defined(CONFIG_COCOA)
5706 case DT_SDL:
5707 cocoa_display_init(ds, full_screen);
5708 break;
Vladimir Chtchetkine72d83df2010-12-14 09:24:02 -08005709#elif defined(CONFIG_STANDALONE_CORE)
5710 case DT_SDL:
Vladimir Chtchetkinee95660a2010-12-20 08:28:03 -08005711 coredisplay_init(ds);
Vladimir Chtchetkine72d83df2010-12-14 09:24:02 -08005712 break;
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005713#endif
5714 case DT_VNC:
5715 vnc_display_init(ds);
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005716 if (vnc_display_open(ds, vnc_display) < 0) {
5717 PANIC("Unable to initialize VNC display");
5718 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005719
5720 if (show_vnc_port) {
5721 printf("VNC server running on `%s'\n", vnc_display_local_addr(ds));
5722 }
5723 break;
5724 default:
5725 break;
5726 }
5727 dpy_resize(ds);
5728
5729 dcl = ds->listeners;
5730 while (dcl != NULL) {
5731 if (dcl->dpy_refresh != NULL) {
5732 ds->gui_timer = qemu_new_timer(rt_clock, gui_update, ds);
5733 qemu_mod_timer(ds->gui_timer, qemu_get_clock(rt_clock));
5734 }
5735 dcl = dcl->next;
5736 }
5737
5738 if (display_type == DT_NOGRAPHIC || display_type == DT_VNC) {
5739 nographic_timer = qemu_new_timer(rt_clock, nographic_update, NULL);
5740 qemu_mod_timer(nographic_timer, qemu_get_clock(rt_clock));
5741 }
5742
David 'Digit' Turner94702b02011-01-20 02:46:33 +01005743 text_consoles_set_display(ds);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005744 qemu_chr_initial_reset();
5745
5746 if (monitor_device && monitor_hd)
5747 monitor_init(monitor_hd, MONITOR_USE_READLINE | MONITOR_IS_DEFAULT);
5748
5749 for(i = 0; i < MAX_SERIAL_PORTS; i++) {
5750 const char *devname = serial_devices[i];
5751 if (devname && strcmp(devname, "none")) {
5752 if (strstart(devname, "vc", 0))
5753 qemu_chr_printf(serial_hds[i], "serial%d console\r\n", i);
5754 }
5755 }
5756
5757 for(i = 0; i < MAX_PARALLEL_PORTS; i++) {
5758 const char *devname = parallel_devices[i];
5759 if (devname && strcmp(devname, "none")) {
5760 if (strstart(devname, "vc", 0))
5761 qemu_chr_printf(parallel_hds[i], "parallel%d console\r\n", i);
5762 }
5763 }
5764
5765 for(i = 0; i < MAX_VIRTIO_CONSOLES; i++) {
5766 const char *devname = virtio_consoles[i];
5767 if (virtcon_hds[i] && devname) {
5768 if (strstart(devname, "vc", 0))
5769 qemu_chr_printf(virtcon_hds[i], "virtio console%d\r\n", i);
5770 }
5771 }
5772
5773 if (gdbstub_dev && gdbserver_start(gdbstub_dev) < 0) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005774 PANIC("qemu: could not open gdbserver on device '%s'",
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005775 gdbstub_dev);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005776 }
5777
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005778 /* call android-specific setup function */
5779 android_emulation_setup();
5780
Vladimir Chtchetkine57584042011-01-20 16:15:30 -08005781#if !defined(CONFIG_STANDALONE_CORE)
5782 // For the standalone emulator (UI+core in one executable) we need to
5783 // set the window title here.
5784 android_emulator_set_base_port(android_base_port);
5785#endif
5786
Ot ten Thije871da2a2010-09-20 10:29:22 +01005787 if (loadvm)
5788 do_loadvm(cur_mon, loadvm);
5789
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005790 if (incoming) {
5791 autostart = 0; /* fixme how to deal with -daemonize */
5792 qemu_start_incoming_migration(incoming);
5793 }
5794
5795 if (autostart)
5796 vm_start();
5797
5798#ifndef _WIN32
5799 if (daemonize) {
5800 uint8_t status = 0;
5801 ssize_t len;
5802
5803 again1:
5804 len = write(fds[1], &status, 1);
5805 if (len == -1 && (errno == EINTR))
5806 goto again1;
5807
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005808 if (len != 1) {
5809 PANIC("Unable to daemonize");
5810 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005811
David 'Digit' Turnera7fb77d2010-05-10 23:50:54 -07005812 if (chdir("/")) {
5813 perror("not able to chdir to /");
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005814 PANIC("not able to chdir to /");
David 'Digit' Turnera7fb77d2010-05-10 23:50:54 -07005815 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005816 TFR(fd = open("/dev/null", O_RDWR));
5817 if (fd == -1)
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005818 PANIC("open(\"/dev/null\") failed: %s", errno_str);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005819 }
5820
5821 if (run_as) {
5822 pwd = getpwnam(run_as);
5823 if (!pwd) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005824 PANIC("User \"%s\" doesn't exist", run_as);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005825 }
5826 }
5827
5828 if (chroot_dir) {
5829 if (chroot(chroot_dir) < 0) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005830 PANIC("chroot failed");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005831 }
David 'Digit' Turnera7fb77d2010-05-10 23:50:54 -07005832 if (chdir("/")) {
5833 perror("not able to chdir to /");
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005834 PANIC("not able to chdir to /");
David 'Digit' Turnera7fb77d2010-05-10 23:50:54 -07005835 }
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005836 }
5837
5838 if (run_as) {
5839 if (setgid(pwd->pw_gid) < 0) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005840 PANIC("Failed to setgid(%d)", pwd->pw_gid);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005841 }
5842 if (setuid(pwd->pw_uid) < 0) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005843 PANIC("Failed to setuid(%d)", pwd->pw_uid);
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005844 }
5845 if (setuid(0) != -1) {
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005846 PANIC("Dropping privileges failed");
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005847 }
5848 }
5849
5850 if (daemonize) {
5851 dup2(fd, 0);
5852 dup2(fd, 1);
5853 dup2(fd, 2);
5854
5855 close(fd);
5856 }
5857#endif
5858
Vladimir Chtchetkine7746af02010-10-07 05:40:39 -07005859#ifdef CONFIG_ANDROID
5860 // This will notify the UI that the core is successfuly initialized
5861 android_core_init_completed();
5862#endif // CONFIG_ANDROID
5863
David 'Digit' Turner5d8f37a2009-09-14 14:32:27 -07005864 main_loop();
5865 quit_timers();
5866 net_cleanup();
5867 android_emulation_teardown();
5868 return 0;
5869}
Vladimir Chtchetkineeb838252010-07-15 12:27:56 -07005870
5871void
5872android_emulation_teardown(void)
5873{
5874 android_charmap_done();
5875}